diff --git a/game/client/src/main/java/net/betterthanadventure/utils/DataDumper.java b/game/client/src/main/java/net/betterthanadventure/utils/DataDumper.java
index 18eb91e5d..a5002e1af 100644
--- a/game/client/src/main/java/net/betterthanadventure/utils/DataDumper.java
+++ b/game/client/src/main/java/net/betterthanadventure/utils/DataDumper.java
@@ -149,7 +149,8 @@ public class DataDumper implements MinecraftAccessor {
                 .append(String.format("0x%06X", biome.color)).append(",")
                 .append(Blocks.blocksList[biome.topBlock].getKey()).append(",")
                 .append(Blocks.blocksList[biome.fillerBlock].getKey()).append(",")
-                .append(biome.hasSurfaceSnow()).append(",");
+                .append(biome.hasSurfaceSnow()).append(",")
+                .append(biome.hasSurfaceIce()).append(",");
 
         builder.append("\"");
 
diff --git a/game/client/src/main/java/net/minecraft/client/GLAllocation.java b/game/client/src/main/java/net/minecraft/client/GLAllocation.java
index 167988eb1..9c33e6719 100644
--- a/game/client/src/main/java/net/minecraft/client/GLAllocation.java
+++ b/game/client/src/main/java/net/minecraft/client/GLAllocation.java
@@ -1,35 +1,28 @@
 package net.minecraft.client;
 
 import java.nio.*;
-import java.util.ArrayList;
-import java.util.List;
 
 import it.unimi.dsi.fastutil.ints.IntArrayList;
 import it.unimi.dsi.fastutil.ints.IntList;
+import org.lwjgl.BufferUtils;
 import org.lwjgl.opengl.GL11;
 
 public class GLAllocation {
 
-	public static IntList displayLists = new IntArrayList();
+//	public static IntList displayLists = new IntArrayList();
 	public static IntList textureNames = new IntArrayList();
 
 	public GLAllocation() {}
 
+	@Deprecated
 	public static synchronized int generateDisplayLists(int range) {
-		int list = GL11.glGenLists(range);
-		displayLists.add(list);
-		displayLists.add(range);
-		return list;
+//		int list = GL11.glGenLists(range);
+//		displayLists.add(list);
+//		displayLists.add(range);
+//		return list;
+		return 0;
 	}
 
-	public static synchronized void generateTextureNames(IntBuffer intbuffer) {
-		GL11.glGenTextures(intbuffer);
-		for (int i = intbuffer.position(); i < intbuffer.limit(); i++) {
-			textureNames.add(intbuffer.get(i));
-		}
-
-	}
-	
 	public static synchronized int generateTexture() {
 		int tex = GL11.glGenTextures();
 		textureNames.add(tex);
@@ -46,42 +39,29 @@ public class GLAllocation {
 		}
 	}
 
+	@Deprecated
 	public static synchronized void deleteDisplayList(int displayList)
 	{
-		int displayListIndex = displayLists.indexOf(displayList);
-		if (displayListIndex < 0) return;
-		GL11.glDeleteLists(displayLists.getInt(displayListIndex), displayLists.getInt(displayListIndex + 1));
-		displayLists.removeInt(displayListIndex);
-		displayLists.removeInt(displayListIndex);
+//		int displayListIndex = displayLists.indexOf(displayList);
+//		if (displayListIndex < 0) return;
+//		GL11.glDeleteLists(displayLists.getInt(displayListIndex), displayLists.getInt(displayListIndex + 1));
+//		displayLists.removeInt(displayListIndex);
+//		displayLists.removeInt(displayListIndex);
 	}
 
 	public static synchronized void deleteTexturesAndDisplayLists() {
-		for (int i = 0; i < displayLists.size(); i += 2) {
-			GL11.glDeleteLists(displayLists.getInt(i), displayLists.getInt(i + 1));
-		}
+//		for (int i = 0; i < displayLists.size(); i += 2) {
+//			GL11.glDeleteLists(displayLists.getInt(i), displayLists.getInt(i + 1));
+//		}
 
-		IntBuffer intbuffer = createDirectIntBuffer(textureNames.size());
+		IntBuffer intbuffer = BufferUtils.createIntBuffer(textureNames.size());
 		for (Integer textureName : textureNames) {
 			intbuffer.put(textureName);
 		}
 
 		intbuffer.flip();
 		GL11.glDeleteTextures(intbuffer);
-		displayLists.clear();
+//		displayLists.clear();
 		textureNames.clear();
 	}
-
-	public static synchronized ByteBuffer createDirectByteBuffer(int i) {
-		ByteBuffer bytebuffer = ByteBuffer.allocateDirect(i).order(ByteOrder.nativeOrder());
-		return bytebuffer;
-	}
-
-	public static IntBuffer createDirectIntBuffer(int i) {
-		return createDirectByteBuffer(i << 2).asIntBuffer();
-	}
-
-	public static FloatBuffer createDirectFloatBuffer(int i) {
-		return createDirectByteBuffer(i << 2).asFloatBuffer();
-	}
-
 }
diff --git a/game/client/src/main/java/net/minecraft/client/Minecraft.java b/game/client/src/main/java/net/minecraft/client/Minecraft.java
index c29583770..0031d1dff 100644
--- a/game/client/src/main/java/net/minecraft/client/Minecraft.java
+++ b/game/client/src/main/java/net/minecraft/client/Minecraft.java
@@ -1,7 +1,5 @@
 package net.minecraft.client;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.awt.Cursor;
 import java.awt.event.MouseAdapter;
 import java.awt.event.MouseEvent;
@@ -34,10 +32,14 @@ import net.minecraft.client.gui.server.ScreenSelectServer;
 import net.minecraft.client.gui.toasts.GuiElementToastsHud;
 import net.minecraft.client.holiday.Holidays;
 import net.minecraft.client.player.controller.PlayerControllerSP;
+import net.minecraft.client.render.renderer.CompareFunc;
+import net.minecraft.client.render.renderer.CullFace;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.world.chunk.provider.ChunkProviderDynamic;
 import net.minecraft.client.world.chunk.provider.ChunkProviderThreadedClient;
 import net.minecraft.client.world.save.SaveHandlerClientSP;
-import net.minecraft.core.net.CertificateHelper;
 import net.minecraft.client.net.handler.PacketHandlerClient;
 import net.minecraft.client.render.TileEntityRenderDispatcher;
 import net.minecraft.client.render.block.model.BlockModelGrass;
@@ -102,13 +104,13 @@ import net.minecraft.client.sound.SoundRepository;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 
+import org.joml.Matrix4f;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
 import org.lwjgl.LWJGLException;
 import org.lwjgl.glfw.GLFW;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.discord.RichPresenceHandlerThread;
 import net.minecraft.client.entity.player.PlayerLocalMultiplayer;
@@ -130,8 +132,6 @@ import net.minecraft.client.option.KeyBinding;
 import net.minecraft.client.option.enums.LightmapStyle;
 import net.minecraft.client.player.controller.PlayerController;
 import net.minecraft.client.render.ParticleEngine;
-import net.minecraft.client.render.FallbackRenderer;
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.LoadingScreenRenderer;
 import net.minecraft.client.render.OpenGLHelper;
 import net.minecraft.client.render.PostProcessingManager;
@@ -144,12 +144,10 @@ import net.minecraft.client.render.camera.EntityCameraFirstPerson;
 import net.minecraft.client.render.camera.ICamera;
 import net.minecraft.client.render.colorizer.Colorizers;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.shader.Shaders;
 import net.minecraft.client.render.shader.ShadersRenderer;
 import net.minecraft.client.render.terrain.ChunkRenderer;
 import net.minecraft.client.render.terrain.TerrainRenderer;
-import net.minecraft.client.render.terrain.TerrainRendererLegacy;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.render.texturepack.TexturePackList;
 import net.minecraft.client.render.window.GameWindow;
@@ -204,6 +202,7 @@ import net.minecraft.core.world.save.LevelStorage;
 import net.minecraft.core.world.save.SaveConverters;
 import net.minecraft.core.world.save.SaveFormats;
 import net.minecraft.core.world.save.mcregion.SaveFormat19134;
+import org.lwjgl.opengl.GL41;
 import org.lwjgl.system.Configuration;
 import org.slf4j.Logger;
 import org.useless.dragonfly.data.entity.mojang.EntityGeometryMojangData;
@@ -222,7 +221,7 @@ public class Minecraft
     public PlayerController playerController;
     public boolean hasCrashed;
     public UnexpectedThrowable lastCrash;
-    private final Timer timer;
+    public final Timer timer;
     public WorldClient currentWorld;
     public RenderGlobal renderGlobal;
     public PlayerLocal thePlayer;
@@ -344,11 +343,11 @@ public class Minecraft
         this.guiToasts = new GuiElementToastsHud(this);
         this.sndManager = new SoundEngine();
 
-        try {
-            CertificateHelper.installCertificates();
-        } catch (Exception e) {
-            LOGGER.error("Failed to install certificates!", e);
-        }
+//        try {
+//            CertificateHelper.installCertificates();
+//        } catch (Exception e) {
+//            LOGGER.error("Failed to install certificates!", e);
+//        }
 
         new Thread("Timer hack thread") {
             {
@@ -505,14 +504,11 @@ public class Minecraft
         printWrongJavaVersionInfo();
 
         this.gameWindow.init(this, this.overrideWidth != null ? this.overrideWidth : this.gameSettings.windowWidth.value, this.overrideHeight != null ? this.overrideHeight : this.gameSettings.windowHeight.value);
+        this.font.init();
 
-        final @Nullable String vendorString = GL11.glGetString(GL_VENDOR);
+        final @Nullable String vendorString = GL41.glGetString(GL41.GL_VENDOR);
         if (vendorString != null) {
             GPU_VENDOR = EnumGPUVendor.getVendorFromString(vendorString);
-            if (GPU_VENDOR == EnumGPUVendor.INTEL) {
-                // Intel cannot handle the sheer complexity of drawing the lightmap texture upon a quad
-                this.gameSettings.lightmapStyle.set(LightmapStyle.DISABLED);
-            }
         }
 
         LOGGER.info("Resolution: {} x {}", this.gameWindow.getWidthPixels(), this.gameWindow.getHeightPixels());
@@ -530,26 +526,10 @@ public class Minecraft
 
         this.resolution.setScale(this.gameSettings.guiScale.value);
 
-        OpenGLHelper.testCapabilities(this);
-
-        if (this.gameSettings.enableMultiDrawRendering.value) {
-            if (OpenGLHelper.gl20) {
-                LOGGER.info("Using MultiDraw terrain renderer");
-                this.terrainRenderer = new TerrainRendererMultiDraw(this);
-            } else {
-                LOGGER.info("MultiDraw not supported, using legacy terrain renderer");
-                this.terrainRenderer = new TerrainRendererLegacy(this);
-            }
-        } else {
-            LOGGER.info("MultiDraw disabled, using legacy terrain renderer");
-            this.terrainRenderer = new TerrainRendererLegacy(this);
-        }
+        this.terrainRenderer = new TerrainRendererMultiDraw(this);
 
-        if (Shaders.enableShaders) {
-            setRenderer(new ShadersRenderer(this));
-        } else {
-            setRenderer(new FallbackRenderer(this));
-        }
+        setRenderer(new ShadersRenderer(this));
+        Shaders.init();
 
         this.texturePackList.init();
         EntityGeometryMojangData.Cache.reload(this.texturePackList);
@@ -557,6 +537,8 @@ public class Minecraft
         TooltipElement.reloadStyles(this.texturePackList);
         SoundRepository.initialize(this);
 
+        GLRenderer.init();
+
         // Show load screen as early as possible
         // Do not put stuff that takes a while to load before this,
         // otherwise the loading time will happen while the window is black
@@ -589,17 +571,16 @@ public class Minecraft
         LOGGER.info("Setting up OpenGL values...");
 
         OpenGLHelper.checkError("pre startup");
-        glEnable(GL11.GL_TEXTURE_2D);
-        glShadeModel(GL11.GL_SMOOTH);
-        glClearDepth(1.0D);
-        glEnable(GL11.GL_DEPTH_TEST);
-        glDepthFunc(515);
-        glEnable(GL11.GL_ALPHA_TEST);
-        glAlphaFunc(516, 0.1F);
-        glCullFace(GL11.GL_BACK);
-        glMatrixMode(GL11.GL_PROJECTION);
-        glLoadIdentity();
-        glMatrixMode(GL11.GL_MODELVIEW);
+//        glEnable(GL11.GL_TEXTURE_2D);
+//        glShadeModel(GL11.GL_SMOOTH);
+        GL41.glClearDepth(1.0D);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.setDepthFunc(CompareFunc.LESS_EQUAL);
+//        glEnable(GL11.GL_ALPHA_TEST);
+//        glAlphaFunc(GL11.GL_GREATER, 0.1F);
+        GLRenderer.setCullFace(CullFace.BACK);
+        GLRenderer.projectionM4f().identity();
+        GLRenderer.viewM4f().identity();
         OpenGLHelper.checkError("startup");
         this.sndManager.init(this.gameSettings);
 
@@ -615,9 +596,9 @@ public class Minecraft
 
         LOGGER.info("Initializing Renderer...");
 
-        TextureRegistry.blockAtlas.bind();
+        TextureRegistry.worldAtlas.bind();
         this.renderGlobal = new RenderGlobal(this, this.textureManager);
-        glViewport(0, 0, this.gameWindow.getWidthPixels(), this.gameWindow.getHeightPixels());
+        GL41.glViewport(0, 0, this.gameWindow.getWidthPixels(), this.gameWindow.getHeightPixels());
         this.particleEngine = new ParticleEngine(this.currentWorld);
         try {
             LOGGER.info("Starting Resource Download Thread...");
@@ -646,8 +627,8 @@ public class Minecraft
         int groups = Registries.RECIPES.getAllGroups().size();
         int namespaces = Registries.RECIPES.size();
         int itemGroups = Registries.ITEM_GROUPS.size();
-        LOGGER.info(String.format("%d item groups.", itemGroups));
-        LOGGER.info(String.format("%d recipes in %d groups in %d namespaces.", recipes, groups, namespaces));
+        LOGGER.info("{} item groups.", itemGroups);
+        LOGGER.info("{} recipes in {} groups in {} namespaces.", recipes, groups, namespaces);
 
         StatList.init();
         this.statsCounter = new StatsCounter(this.session, this.mcDataDir);
@@ -761,60 +742,66 @@ public class Minecraft
         }
     }
 
+    public @NotNull Matrix4f getGuiProjectionMatrix(@NotNull Matrix4f dest) {
+        return dest.identity().ortho(0.0f, (float) this.resolution.getExactScaledWidthScreenCoords(), (float) this.resolution.getExactScaledHeightScreenCoords(), 0.0f, 1000f, 3000f);
+    }
+
+    public @NotNull Matrix4f getGuiViewMatrix(@NotNull Matrix4f dest) {
+        return dest.identity().translate(0, 0, -2000);
+    }
+
     private void loadScreen() throws LWJGLException {
-        LOGGER.info("Drawing Loading Screen...");
-        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
-        glMatrixMode(GL11.GL_PROJECTION);
-        glLoadIdentity();
-        glOrtho(0.0D, this.resolution.getExactScaledWidthScreenCoords(), this.resolution.getExactScaledHeightScreenCoords(), 0.0D, 1000D, 3000D);
-        glMatrixMode(GL11.GL_MODELVIEW);
-        glLoadIdentity();
-        glTranslatef(0.0F, 0.0F, -2000F);
-        glViewport(0, 0, this.gameWindow.getWidthPixels(), this.gameWindow.getHeightPixels());
-        glClearColor(0.0F, 0.0F, 0.0F, 0.0F);
-        Tessellator tessellator = Tessellator.instance;
-        glDisable(GL11.GL_LIGHTING);
-        glEnable(GL11.GL_TEXTURE_2D);
-        glDisable(GL11.GL_FOG);
-
-        if (this.mojrand == 0)
+//        LOGGER.info("Drawing Loading Screen...");
+        GL41.glClear(GL41.GL_COLOR_BUFFER_BIT | GL41.GL_DEPTH_BUFFER_BIT);
+        getGuiProjectionMatrix(GLRenderer.projectionM4f());
+        getGuiViewMatrix(GLRenderer.viewM4f());
+        GL41.glViewport(0, 0, this.gameWindow.getWidthPixels(), this.gameWindow.getHeightPixels());
+        GL41.glClearColor(0.0F, 0.0F, 0.0F, 0.0F);
+
+//        glDisable(GL11.GL_LIGHTING);
+//        glEnable(GL11.GL_TEXTURE_2D);
+//        glDisable(GL11.GL_FOG);
+
+        if (this.mojrand == 0) {
             this.textureManager.loadTexture("/assets/minecraft/textures/gui/title/majonk.png").bind();
-        else
+        }
+        else {
             this.textureManager.loadTexture("/assets/minecraft/textures/gui/title/mojang.png").bind();
+        }
 
-        tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0xffffff);
-        tessellator.addVertexWithUV(0.0D, this.gameWindow.getHeightPixels(), 0.0D, 0.0D, 0.0D);
-        tessellator.addVertexWithUV(this.gameWindow.getWidthPixels(), this.gameWindow.getHeightPixels(), 0.0D, 0.0D, 0.0D);
-        tessellator.addVertexWithUV(this.gameWindow.getWidthPixels(), 0.0D, 0.0D, 0.0D, 0.0D);
-        tessellator.addVertexWithUV(0.0D, 0.0D, 0.0D, 0.0D, 0.0D);
-        tessellator.draw();
+        TessellatorGeneral t = GLRenderer.getTessellator();
+        t.startDrawingQuads();
+        t.setColorOpaque1i(0xffffff);
+        t.addVertex(0.0D, this.gameWindow.getHeightPixels(), 0.0D);
+        t.addVertex(0.0D, 0.0D, 0.0D);
+        t.addVertex(this.gameWindow.getWidthPixels(), 0.0D, 0.0D);
+        t.addVertex(this.gameWindow.getWidthPixels(), this.gameWindow.getHeightPixels(), 0.0D);
+        t.draw();
 
         int width = 256;
         int height = 256;
 
-        glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
 
-        drawMojangLogoVertices((this.resolution.getScaledWidthScreenCoords() - width) / 2, (this.resolution.getScaledHeightScreenCoords() - height) / 2, 0, 0, width, height);
+        drawMojangLogoVertices(t, (this.resolution.getScaledWidthScreenCoords() - width) / 2, (this.resolution.getScaledHeightScreenCoords() - height) / 2, 0, 0, width, height);
 
-        glDisable(GL11.GL_LIGHTING);
-        glDisable(GL11.GL_FOG);
-        glEnable(GL11.GL_ALPHA_TEST);
-        glAlphaFunc(GL_GREATER, 0.1F);
+//        glDisable(GL11.GL_LIGHTING);
+//        glDisable(GL11.GL_FOG);
+//        glEnable(GL11.GL_ALPHA_TEST);
+//        glAlphaFunc(GL_GREATER, 0.1F);
         this.gameWindow.update();
     }
 
-    public void drawMojangLogoVertices(int minX, int minY, int minU, int minV, int width, int height) {
+    public void drawMojangLogoVertices(@NotNull TessellatorGeneral t, int minX, int minY, int minU, int minV, int width, int height) {
         float scaleX = 0.00390625F;
         float scaleY = 0.00390625F;
-        Tessellator tessellator = Tessellator.instance;
-        tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0xffffff);
-        tessellator.addVertexWithUV(minX, minY + height, 0.0D, (float) (minU) * scaleX, (float) (minV + height) * scaleY);
-        tessellator.addVertexWithUV(minX + width, minY + height, 0.0D, (float) (minU + width) * scaleX, (float) (minV + height) * scaleY);
-        tessellator.addVertexWithUV(minX + width, minY, 0.0D, (float) (minU + width) * scaleX, (float) (minV) * scaleY);
-        tessellator.addVertexWithUV(minX, minY, 0.0D, (float) (minU) * scaleX, (float) (minV) * scaleY);
-        tessellator.draw();
+        t.startDrawingQuads();
+        t.setColorOpaque1i(0xffffff);
+        t.addVertexWithUV(minX, minY + height, 0.0D, (float) (minU) * scaleX, (float) (minV + height) * scaleY);
+        t.addVertexWithUV(minX, minY, 0.0D, (float) (minU) * scaleX, (float) (minV) * scaleY);
+        t.addVertexWithUV(minX + width, minY, 0.0D, (float) (minU + width) * scaleX, (float) (minV) * scaleY);
+        t.addVertexWithUV(minX + width, minY + height, 0.0D, (float) (minU + width) * scaleX, (float) (minV + height) * scaleY);
+        t.draw();
     }
 
     public File getMinecraftDir() {
@@ -890,16 +877,7 @@ public class Minecraft
         return this.saveFormat;
     }
 
-    private Screen lastScreen;
-
     public void displayScreen(@Nullable Screen screen) {
-        // Big sir's mouse fix, clearly the legacy lwjgl dependency is fucked in some way, may we hopefully fully replace it one day
-        if (screen == null && this.lastScreen != null) {
-            Mouse.setGrabbed(false);
-            Mouse.setGrabbed(true);
-        }
-        this.lastScreen = screen;
-
         if (this.currentScreen == null && screen != null) {
             if (this.controllerInput != null) {
                 this.controllerInput.cursorX = this.resolution.getScaledWidthScreenCoords() / 2D;
@@ -1004,8 +982,8 @@ public class Minecraft
 
                     Debug.pop();            // 2
                     Debug.change("tick");    // 1
-                    if (this.currentWorld instanceof WorldClientMP) {
-                        ((WorldClientMP) this.currentWorld).processPackets();
+                    if (this.currentWorld instanceof WorldClientMP clientMP) {
+                        clientMP.processPackets();
                     }
 
                     if (this.currentScreen instanceof ScreenSelectServer) {
@@ -1033,7 +1011,7 @@ public class Minecraft
                     EntityItem.enableItemClumping = this.gameSettings.enableItemClumping.value;
                     BlockLogicLeavesBase.enableTreeShadowing = this.gameSettings.treeShadows.value;
                     this.sndManager.updateListener(this.thePlayer, this.timer.partialTicks);
-                    glEnable(GL_TEXTURE_2D);
+//                    glEnable(GL_TEXTURE_2D);
                     if (this.currentWorld != null) {
                         Debug.change("updatelight");
                         try {
@@ -1058,7 +1036,7 @@ public class Minecraft
                     Debug.push("post"); // 3
 
                     this.renderer.beginRenderGame(this.timer.partialTicks);
-                    glEnable(GL_ALPHA_TEST);
+//                    glEnable(GL_ALPHA_TEST);
 
                     Debug.change("misc");  // 3
                     if (!this.skipRenderWorld) {
@@ -1153,8 +1131,8 @@ public class Minecraft
                             while (currentSleep < sleepTime - 1) {
                                 Thread.sleep(1L);
                                 currentSleep += 1L;
-                                if (this.currentWorld instanceof WorldClientMP) {
-                                    ((WorldClientMP) this.currentWorld).processPackets();
+                                if (this.currentWorld instanceof WorldClientMP worldClientMP) {
+                                    worldClientMP.processPackets();
                                 }
 
                                 if (this.currentScreen instanceof ScreenSelectServer) {
@@ -1198,10 +1176,6 @@ public class Minecraft
     }
 
     public void freeUpMemory() {
-        try {
-            this.renderGlobal.deleteChunkLists();
-        } catch (Throwable ignored) {
-        }
         try {
             System.gc();
             ObjectPool.freeAllPools();
@@ -1224,13 +1198,11 @@ public class Minecraft
 
                 Debug.push("screenshot");
                 if (ctrl) {
-                    if (Shaders.enableShaders) {
-                        try {
-                            this.screenshotHelper.takePanoramaScreenshot();
-                            this.hudIngame.addChatMessage("Saved panorama screenshot!");
-                        } catch (Exception e) {
-                            LOGGER.error("Exception occurred while taking panoramic screenshot!", e);
-                        }
+                    try {
+                        this.screenshotHelper.takePanoramaScreenshot();
+                        this.hudIngame.addChatMessage("Saved panorama screenshot!");
+                    } catch (Exception e) {
+                        LOGGER.error("Exception occurred while taking panoramic screenshot!", e);
                     }
                 } else {
                     this.hudIngame.addChatMessage(ScreenShot.saveScreenshot(getMinecraftDir(), this.gameWindow.getWidthPixels(), this.gameWindow.getHeightPixels()));
@@ -1461,7 +1433,7 @@ public class Minecraft
             this.playerController.tick();
         }
         Debug.change("textureTick");
-        TextureRegistry.blockAtlas.bind();
+        TextureRegistry.worldAtlas.bind();
         this.textureManager.updateDynamicTextures(this.isGamePaused && this.currentScreen instanceof ScreenPause);
         Debug.change("misc");
         if (this.currentScreen == null && this.thePlayer != null) {
@@ -1601,28 +1573,20 @@ public class Minecraft
                                     PlayerProfile profile = queue.getPlayer(this.thePlayer.username);
                                     if (profile != null && profile.isOperator) {
                                         this.fullbright = !this.fullbright;
-                                        if (!LightmapHelper.isLightmapEnabled()) {
-                                            this.renderGlobal.allChanged();
-                                        }
                                     }
                                 } else {
                                     if (this.currentWorld.getLevelData().getCheatsEnabled()) {
                                         this.fullbright = !this.fullbright;
-                                        if (!LightmapHelper.isLightmapEnabled()) {
-                                            this.renderGlobal.allChanged();
-                                        }
                                     }
                                 }
                                 this.hudIngame.heldItemTooltipElement.setString("Fullbright: " + (this.fullbright ? "On" : "Off"));
                             } else if (this.gameSettings.keyLightmaps.isPressEvent()) {
-                                if (this.gameSettings.lightmapStyle.value == LightmapStyle.DISABLED) {
+                                if (this.gameSettings.lightmapStyle.value == LightmapStyle.COLORIZED) {
                                     this.gameSettings.lightmapStyle.value = LightmapStyle.GRAY;
-                                    this.hudIngame.heldItemTooltipElement.setString("Lightmap: On");
-                                    this.renderGlobal.allChanged();
+                                    this.hudIngame.heldItemTooltipElement.setString("Lightmap: Gray");
                                 } else {
-                                    this.gameSettings.lightmapStyle.value = LightmapStyle.DISABLED;
-                                    this.hudIngame.heldItemTooltipElement.setString("Lightmap: Off");
-                                    this.renderGlobal.allChanged();
+                                    this.gameSettings.lightmapStyle.value = LightmapStyle.COLORIZED;
+                                    this.hudIngame.heldItemTooltipElement.setString("Lightmap: Colored");
                                 }
                             } else if (this.gameSettings.keyCollisionBoxes.isPressEvent()) {
                                 this.gameSettings.showCollisionBoxes.toggle();
@@ -2095,6 +2059,7 @@ public class Minecraft
         this.sndManager.init(this.gameSettings);
         this.texturePackList.refresh();
         this.renderer.reload();
+        Shaders.reload();
         if (this.renderGlobal != null) {
             this.renderGlobal.allChanged();
         }
@@ -2281,9 +2246,6 @@ public class Minecraft
                 this.playerController.initPlayer(this.thePlayer);
             }
             this.thePlayer.input = new PlayerInput(this);
-            if (this.renderGlobal != null) {
-                this.renderGlobal.setWorld(world);
-            }
             if (this.particleEngine != null) {
                 this.particleEngine.setWorld(world);
             }
@@ -2298,6 +2260,9 @@ public class Minecraft
             }
             this.activeCamera = new EntityCameraFirstPerson(this, this.thePlayer);
             this.thePlayer.syncPlacementMode();
+            if (this.renderGlobal != null) {
+                this.renderGlobal.setWorld(world);
+            }
         } else {
             this.thePlayer = null;
         }
diff --git a/game/client/src/main/java/net/minecraft/client/entity/player/PlayerLocal.java b/game/client/src/main/java/net/minecraft/client/entity/player/PlayerLocal.java
index 1cdc6fd7b..3acee0969 100644
--- a/game/client/src/main/java/net/minecraft/client/entity/player/PlayerLocal.java
+++ b/game/client/src/main/java/net/minecraft/client/entity/player/PlayerLocal.java
@@ -49,15 +49,13 @@ import org.slf4j.Logger;
 
 import java.util.function.Function;
 
-public class PlayerLocal extends Player
-{
+public class PlayerLocal extends Player {
     private static final Logger LOGGER = LogUtils.getLogger();
     public PlayerInput input;
     protected Minecraft mc;
     protected int sprintTimer;
 
-    public PlayerLocal(Minecraft minecraft, World world, Session session, int dimension)
-    {
+    public PlayerLocal(Minecraft minecraft, World world, Session session, int dimension) {
         super(world);
         this.mc = minecraft;
         this.dimension = dimension;
@@ -84,18 +82,16 @@ public class PlayerLocal extends Player
         return f;
     }
 
-    public @Nullable AABBdc getCollisionAABB()
-    {
+    public @Nullable AABBdc getCollisionAABB() {
         if (this.noPhysics) {
             return null;
         } else {
             return super.getCollisionAABB();
         }
     }
-    
+
     @Override
-    public void updateAI()
-    {
+    public void updateAI() {
         super.updateAI();
         this.moveStrafing = this.input.moveStrafe;
         this.moveForward = this.input.moveForward;
@@ -103,18 +99,15 @@ public class PlayerLocal extends Player
     }
 
     @Override
-    public void setGamemode(Gamemode gamemode)
-    {
+    public void setGamemode(Gamemode gamemode) {
         this.gamemode = gamemode;
 
         MenuInventory newContainer = gamemode.getContainer(this.inventory, !this.world.isClientSide);
-        if (this.craftingInventory == this.inventorySlots)
-        {
+        if (this.craftingInventory == this.inventorySlots) {
             this.craftingInventory = newContainer;
         }
         this.inventorySlots = newContainer;
-        if (!gamemode.canPlayerFly())
-        {
+        if (!gamemode.canPlayerFly()) {
             this.noPhysics = false;
         }
 
@@ -122,77 +115,61 @@ public class PlayerLocal extends Player
     }
 
     @Override
-    public void onLivingUpdate()
-    {
-        if (this.sprintTimer > 0)
-        {
+    public void onLivingUpdate() {
+        if (this.sprintTimer > 0) {
             this.sprintTimer--;
         }
 
         AchievementToast invToast = new AchievementToast(Achievements.OPEN_INVENTORY, true);
         AchievementToast guideToast = new AchievementToast(Achievements.OPEN_GUIDEBOOK, true);
 
-        if (!this.mc.statsCounter.isUnlocked(Achievements.OPEN_INVENTORY) && !this.mc.guiToasts.isDisplayingToast(invToast))
-        {
+        if (!this.mc.statsCounter.isUnlocked(Achievements.OPEN_INVENTORY) && !this.mc.guiToasts.isDisplayingToast(invToast)) {
             this.mc.guiToasts.addToast(invToast);
         }
         if (/*this.mc.statsCounter.isUnlocked(Achievements.OPEN_INVENTORY) &&*/
-                !this.mc.statsCounter.isUnlocked(Achievements.OPEN_GUIDEBOOK) &&
+            !this.mc.statsCounter.isUnlocked(Achievements.OPEN_GUIDEBOOK) &&
 //                !this.mc.guiAchievementToast.isDisplayingToast(invToast) &&
                 !this.mc.guiToasts.isDisplayingToast(guideToast)
-        )
-        {
+        ) {
             this.mc.guiToasts.addToast(guideToast);
         }
 
         this.prevTimeInPortal = this.timeInPortal;
-        if(this.inPortal && !this.noPhysics)
-        {
-            if(!this.world.isClientSide && this.vehicle != null)
-            {
+        if (this.inPortal && !this.noPhysics) {
+            if (!this.world.isClientSide && this.vehicle != null) {
                 startRiding(null);
             }
-            if(this.mc.currentScreen instanceof ScreenContainerAbstract) // Close out of containers like the inventory
+            if (this.mc.currentScreen instanceof ScreenContainerAbstract) // Close out of containers like the inventory
             {
                 this.mc.displayScreen(null);
             }
-            if(this.timeInPortal == 0.0F)
-            {
+            if (this.timeInPortal == 0.0F) {
                 this.mc.sndManager.playSound("portal.trigger", SoundCategory.WORLD_SOUNDS, 1.0F, this.random.nextFloat() * 0.4F + 0.8F);
             }
             this.timeInPortal += 0.0125F;
-            if(this.timeInPortal >= 1.0F || getGamemode().instantPortalTravel())
-            {
+            if (this.timeInPortal >= 1.0F || getGamemode().instantPortalTravel()) {
                 this.timeInPortal = 1.0F;
-                if(!this.world.isClientSide)
-                {
+                if (!this.world.isClientSide) {
                     this.timeUntilPortal = 10;
                     this.mc.sndManager.playSound("portal.travel", SoundCategory.WORLD_SOUNDS, 1.0F, this.random.nextFloat() * 0.4F + 0.8F);
                     Dimension targetDim = ((BlockLogicPortal) Blocks.blocksList[this.portalID].getLogic()).targetDimension;
-                    if (this.dimension == targetDim.id)
-                    {
+                    if (this.dimension == targetDim.id) {
                         this.mc.usePortal(0, this.portalColor);
-                    }
-                    else
-                    {
+                    } else {
                         this.mc.usePortal(targetDim.id, this.portalColor);
                     }
                 }
             }
             this.inPortal = false;
-        } else
-        {
-            if(this.timeInPortal > 0.0F)
-            {
+        } else {
+            if (this.timeInPortal > 0.0F) {
                 this.timeInPortal -= 0.05F;
             }
-            if(this.timeInPortal < 0.0F)
-            {
+            if (this.timeInPortal < 0.0F) {
                 this.timeInPortal = 0.0F;
             }
         }
-        if(this.timeUntilPortal > 0)
-        {
+        if (this.timeUntilPortal > 0) {
             this.timeUntilPortal--;
         }
         float f = 0.8f;
@@ -202,83 +179,70 @@ public class PlayerLocal extends Player
 //        {
 //            ySlideOffset = 0.45F;
 //        }
-        checkInTile(this.x - (double) this.bbWidth * 0.35D, this.bb.minY + 0.5D, this.z + (double) this.bbWidth * 0.35D);
-        checkInTile(this.x - (double) this.bbWidth * 0.35D, this.bb.minY + 0.5D, this.z - (double) this.bbWidth * 0.35D);
-        checkInTile(this.x + (double) this.bbWidth * 0.35D, this.bb.minY + 0.5D, this.z - (double) this.bbWidth * 0.35D);
-        checkInTile(this.x + (double) this.bbWidth * 0.35D, this.bb.minY + 0.5D, this.z + (double) this.bbWidth * 0.35D);
+        checkAndPushInTile(this.x - (double) this.bbWidth * 0.35D, this.bb.minY + 0.5D, this.z + (double) this.bbWidth * 0.35D);
+        checkAndPushInTile(this.x - (double) this.bbWidth * 0.35D, this.bb.minY + 0.5D, this.z - (double) this.bbWidth * 0.35D);
+        checkAndPushInTile(this.x + (double) this.bbWidth * 0.35D, this.bb.minY + 0.5D, this.z - (double) this.bbWidth * 0.35D);
+        checkAndPushInTile(this.x + (double) this.bbWidth * 0.35D, this.bb.minY + 0.5D, this.z + (double) this.bbWidth * 0.35D);
         boolean canSprint = this.world.getGameRuleValue(GameRules.ALLOW_SPRINTING) && !this.noPhysics;
-        if (this.onGround && !forwardInput && this.input.moveForward >= f && !isSprinting() && canSprint)
-        {
-            if (this.sprintTimer == 0)
-            {
+        if (this.onGround && !forwardInput && this.input.moveForward >= f && !isSprinting() && canSprint) {
+            if (this.sprintTimer == 0) {
                 this.sprintTimer = 7;
-            }
-            else
-            {
+            } else {
                 setSprinting(true);
                 this.sprintTimer = 0;
             }
         }
-        if (this.onGround && canSprint && this.mc.gameSettings.keySprint.isPressed())
-        {
+        if (this.onGround && canSprint && this.mc.gameSettings.keySprint.isPressed()) {
             setSprinting(true);
         }
-        if (isSprinting() && (this.input.moveForward < f || this.horizontalCollision || !canSprint))
-        {
+        if (isSprinting() && (this.input.moveForward < f || this.horizontalCollision || !canSprint)) {
             setSprinting(false);
         }
         super.onLivingUpdate();
 
         WorldTypeFXDispatcher.getInstance().getDispatch(this.world.getWorldType()).playerAnimationTick(this.world, this);
     }
-    
+
     @Override
     public void wakeUpPlayer(boolean flag, boolean flag1) {
         super.wakeUpPlayer(flag, flag1);
         this.mc.displayScreen(null);
     }
-    
+
     @Override
-    public void addAdditionalSaveData(@NotNull CompoundTag tag)
-    {
+    public void addAdditionalSaveData(@NotNull CompoundTag tag) {
         super.addAdditionalSaveData(tag);
         tag.putInt("Score", this.score);
     }
 
     @Override
-    public void readAdditionalSaveData(@NotNull CompoundTag tag)
-    {
+    public void readAdditionalSaveData(@NotNull CompoundTag tag) {
         super.readAdditionalSaveData(tag);
         this.score = tag.getInteger("Score");
     }
 
     @Override
-    public void closeScreen()
-    {
+    public void closeScreen() {
         super.closeScreen();
         this.mc.displayScreen(null);
     }
 
     @Override
-    public void displaySignEditorScreen(TileEntitySign tileEntity)
-    {
+    public void displaySignEditorScreen(TileEntitySign tileEntity) {
         this.mc.displayScreen(new ScreenSignEditor(tileEntity));
     }
 
     @Override
-    public void displayFlagEditorScreen(TileEntityFlag tileEntity)
-    {
+    public void displayFlagEditorScreen(TileEntityFlag tileEntity) {
         this.mc.displayScreen(new ScreenFlagEditor(this, tileEntity));
     }
 
     @Override
-    public void displayContainerScreen(Container container)
-    {
+    public void displayContainerScreen(Container container) {
         this.mc.displayScreen(new ScreenContainer(this.inventory, container));
     }
 
-    public void displayChestScreen(Container container, double x, double y, double z)
-    {
+    public void displayChestScreen(Container container, double x, double y, double z) {
         displayContainerScreen(container);
     }
 
@@ -288,20 +252,17 @@ public class PlayerLocal extends Player
     }
 
     @Override
-    public void displayWorkbenchScreen(@NotNull TilePosc tilePos)
-    {
+    public void displayWorkbenchScreen(@NotNull TilePosc tilePos) {
         this.mc.displayScreen(new ScreenCrafting(this.inventory, this.world, tilePos));
     }
 
     @Override
-    public void displayLabelEditorScreen(ItemStack itemStack, int slot)
-    {
+    public void displayLabelEditorScreen(ItemStack itemStack, int slot) {
         this.mc.displayScreen(new ScreenLabelEditor(itemStack, slot));
     }
 
     @Override
-    public void displayPaintingPickerScreen()
-    {
+    public void displayPaintingPickerScreen() {
         this.mc.displayScreen(new ScreenPaintingPicker(this));
     }
 
@@ -310,6 +271,7 @@ public class PlayerLocal extends Player
         String currentMobId = ((TileEntityMobSpawner) this.world.getTileEntity(tilePos)).getMobId();
         this.mc.displayScreen(new ScreenMobPicker(currentMobId, tilePos));
     }
+
     @Override
     public void displayWandMobPickerScreen(ItemStack itemStack) {
         String currentMobId = itemStack.getData().getStringOrDefault("monster", "Pig");
@@ -317,8 +279,7 @@ public class PlayerLocal extends Player
     }
 
     @Override
-    public void displayFurnaceScreen(TileEntityFurnace tileEntity)
-    {
+    public void displayFurnaceScreen(TileEntityFurnace tileEntity) {
         this.mc.displayScreen(new ScreenFurnace(this.inventory, tileEntity));
     }
 
@@ -328,20 +289,17 @@ public class PlayerLocal extends Player
     }
 
     @Override
-    public void displayTrommelScreen(TileEntityTrommel tileEntity)
-    {
+    public void displayTrommelScreen(TileEntityTrommel tileEntity) {
         this.mc.displayScreen(new ScreenTrommel(this.inventory, tileEntity));
     }
 
     @Override
-    public void displayDispenserScreen(TileEntityDispenser tileEntity)
-    {
+    public void displayDispenserScreen(TileEntityDispenser tileEntity) {
         this.mc.displayScreen(new ScreenDispenser(this.inventory, tileEntity));
     }
 
     @Override
-    public void displayActivatorScreen(TileEntityActivator tileEntity)
-    {
+    public void displayActivatorScreen(TileEntityActivator tileEntity) {
         this.mc.displayScreen(new ScreenActivator(this.inventory, tileEntity));
     }
 
@@ -351,19 +309,17 @@ public class PlayerLocal extends Player
     }
 
     @Override
-    public void onItemPickup(Entity entity, ItemStack item)
-    {
+    public void onItemPickup(Entity entity, ItemStack item) {
         addStat(item.getItem().getStat(StatList.STAT_PICKED_UP), 1);
         this.mc.particleEngine.add(new ParticlePickupAnimation(this.mc.currentWorld, entity, this, -0.5F));
     }
 
-    public int getPlayerProtectionAmount()
-    {
+    public int getPlayerProtectionAmount() {
         return this.inventory.getTotalArmourPoints();
     }
 
     public void sendChatMessage(String s) {
-    	addToSendHistory(s);
+        addToSendHistory(s);
         if (s.startsWith("/")) {
             String command = s.substring(1);
             ClientCommandSource clientCommandSource = new ClientCommandSource(this.mc);
@@ -376,40 +332,35 @@ public class PlayerLocal extends Player
             this.mc.hudIngame.addChatMessage("<" + getDisplayName() + TextFormatting.RESET + "> " + TextFormatting.WHITE + s);
         }
     }
-    
+
     public void addToSendHistory(String msg) {
-    	if(msg == null || msg.isEmpty()) {
-    		return;
-    	}
-    	for(int i = 0; i < this.messageHistory.size(); i++) {
-    		if(this.messageHistory.get(i).equals(msg)) {
+        if (msg == null || msg.isEmpty()) {
+            return;
+        }
+        for (int i = 0; i < this.messageHistory.size(); i++) {
+            if (this.messageHistory.get(i).equals(msg)) {
                 this.messageHistory.remove(i--);
-    		}
-    	}
+            }
+        }
         this.messageHistory.add(msg);
-        if(this.messageHistory.size() > 100) {
+        if (this.messageHistory.size() > 100) {
             this.messageHistory.remove(0);
         }
     }
-    
+
     @Override
-    public boolean wantSneak()
-    {
+    public boolean wantSneak() {
         return (this.input != null && this.input.sneak) && !this.sleeping;
     }
 
-    public void setHealth(int i)
-    {
+    public void setHealth(int i) {
         int j = getHealth() - i;
-        if(j <= 0)
-        {
+        if (j <= 0) {
             setHealthRaw(i);
-            if(j < 0)
-            {
+            if (j < 0) {
                 this.heartsFlashTime = this.heartsHalvesLife / 2;
             }
-        } else
-        {
+        } else {
             this.lastDamage = j;
             this.prevHealth = getHealth();
             this.heartsFlashTime = this.heartsHalvesLife;
@@ -419,79 +370,66 @@ public class PlayerLocal extends Player
     }
 
     @Override
-    public void respawnPlayer()
-    {
+    public void respawnPlayer() {
         this.mc.respawn(false, 0);
     }
 
     @Override
-    public void animate4()
-    {
+    public void animate4() {
     }
-    
+
     @Override
-    public void addStat(Stat stat, int i)
-    {
-        if(stat == null) {
+    public void addStat(Stat stat, int i) {
+        if (stat == null) {
             return;
         }
-        if(stat.isAchievement()) {
-            Achievement achievement = (Achievement)stat;
-            if(achievement.parent == null || this.mc.statsCounter.isUnlocked(achievement.parent))
-            {
-                if(!this.mc.statsCounter.isUnlocked(achievement))
-                {
+        if (stat.isAchievement()) {
+            Achievement achievement = (Achievement) stat;
+            if (achievement.parent == null || this.mc.statsCounter.isUnlocked(achievement.parent)) {
+                if (!this.mc.statsCounter.isUnlocked(achievement)) {
                     this.mc.guiToasts.addToast(new AchievementToast(achievement, false));
                 }
                 this.mc.statsCounter.add(stat, i);
             }
-        } else
-        {
+        } else {
             this.mc.statsCounter.add(stat, i);
         }
     }
-    
+
     @Override
-    public int getStat(Stat stat)
-    {
+    public int getStat(Stat stat) {
         return this.mc.statsCounter.readStat(stat);
     }
 
     @Override
-    protected boolean checkInTile(double x, double y, double z)
-    {
+    protected boolean checkAndPushInTile(double x, double y, double z) {
         if (this.noPhysics) return false;
         final boolean isShort = this.isDwarf || this.isSneaking();
         final int blockX = MathHelper.floor(x);
         final int blockY = MathHelper.floor(y);
         final int blockZ = MathHelper.floor(z);
-        final double dX = x - (double)blockX;
-        final double dZ = z - (double)blockZ;
-        if(doesBlockPushOut(blockX, blockY, blockZ) || (doesBlockPushOut(blockX, blockY + 1, blockZ) && !isShort))
-        {
+        final double dX = x - (double) blockX;
+        final double dZ = z - (double) blockZ;
+        if (doesBlockPushOut(blockX, blockY, blockZ) || (doesBlockPushOut(blockX, blockY + 1, blockZ) && !isShort)) {
             final boolean flagWest = !doesBlockPushOut(blockX - 1, blockY, blockZ) && (isShort || !doesBlockPushOut(blockX - 1, blockY + 1, blockZ));
             final boolean flagEast = !doesBlockPushOut(blockX + 1, blockY, blockZ) && (isShort || !doesBlockPushOut(blockX + 1, blockY + 1, blockZ));
             final boolean flagNorth = !doesBlockPushOut(blockX, blockY, blockZ - 1) && (isShort || !doesBlockPushOut(blockX, blockY + 1, blockZ - 1));
             final boolean flagSouth = !doesBlockPushOut(blockX, blockY, blockZ + 1) && (isShort || !doesBlockPushOut(blockX, blockY + 1, blockZ + 1));
             Direction pushDirection = Direction.NONE;
             double minLength = Double.MAX_VALUE;
-            if(flagWest && dX < minLength)
-            {
+            if (flagWest && dX < minLength) {
                 minLength = dX;
                 pushDirection = Direction.WEST;
             }
-            if(flagEast && 1.0D - dX < minLength)
-            {
+            if (flagEast && 1.0D - dX < minLength) {
                 minLength = 1.0D - dX;
                 pushDirection = Direction.EAST;
             }
-            if(flagNorth && dZ < minLength)
-            {
+            if (flagNorth && dZ < minLength) {
                 minLength = dZ;
                 pushDirection = Direction.NORTH;
             }
-            if(flagSouth && 1.0D - dZ < minLength)
-            {
+            if (flagSouth && 1.0D - dZ < minLength) {
 //                minLength = 1.0D - dZ;
                 pushDirection = Direction.SOUTH;
             }
@@ -506,16 +444,16 @@ public class PlayerLocal extends Player
     public void syncPlacementMode() {
         this.placementModeOverride = this.mc.gameSettings.placementMode.value;
     }
-    
-	@Override
-	public void sendMessage(String message) {
+
+    @Override
+    public void sendMessage(String message) {
         this.mc.hudIngame.addChatMessage(message);
-	}
+    }
 
-	@Override
-	public void sendStatusMessage(String message) {
+    @Override
+    public void sendStatusMessage(String message) {
         this.mc.hudIngame.heldItemTooltipElement.setString(message);
-	}
+    }
 
     @Override
     public boolean lerpVehicleMotion() {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ButtonElement.java b/game/client/src/main/java/net/minecraft/client/gui/ButtonElement.java
index 4d18331c1..a5a4beb6e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ButtonElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ButtonElement.java
@@ -1,11 +1,11 @@
 package net.minecraft.client.gui;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.render.window.CursorShape;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.core.util.helper.Listener;
@@ -37,21 +37,21 @@ public class ButtonElement extends Gui implements GuiElement
 
     public ButtonElement(int id, int xPosition, int yPosition, int width, int height, String text)
     {
-        enabled = true;
-        visible = true;
+        this.enabled = true;
+        this.visible = true;
         this.id = id;
         this.xPosition = xPosition;
         this.yPosition = yPosition;
         this.width = width;
         this.height = height;
-        displayString = text;
+        this.displayString = text;
         setDefaultTextures();
     }
 
     protected void setDefaultTextures() {
-        defaultTexture = TextureRegistry.getTexture("minecraft:gui/widgets/button/button");
-        hoveredTexture = TextureRegistry.getTexture("minecraft:gui/widgets/button/button_highlighted");
-        disabledTexture = TextureRegistry.getTexture("minecraft:gui/widgets/button/button_disabled");
+        this.defaultTexture = TextureRegistry.getTexture("minecraft:gui/widgets/button/button");
+        this.hoveredTexture = TextureRegistry.getTexture("minecraft:gui/widgets/button/button_highlighted");
+        this.disabledTexture = TextureRegistry.getTexture("minecraft:gui/widgets/button/button_disabled");
     }
 
     public @NotNull ButtonElement setTextures(@Nullable String defaultTexture, @Nullable String hoveredTexture, @Nullable String disabledTexture) {
@@ -70,7 +70,7 @@ public class ButtonElement extends Gui implements GuiElement
     protected int getButtonState(boolean hovered)
     {
         int state = STATE_DEFAULT;
-        if(!enabled)
+        if(!this.enabled)
         {
             state = STATE_DISABLED;
         }
@@ -83,51 +83,36 @@ public class ButtonElement extends Gui implements GuiElement
 
     public void drawButton(Minecraft mc, int mouseX, int mouseY)
     {
-        if (!visible) return;
+        if (!this.visible) return;
 
-        boolean mouseOver = mouseX >= xPosition && mouseY >= yPosition && mouseX < xPosition + width && mouseY < yPosition + height;
+        boolean mouseOver = mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height;
         int state = getButtonState(mouseOver);
 
-        if (mouseOver && visible && enabled) {
+        if (mouseOver && this.visible && this.enabled) {
             mc.currentScreen.setDesiredCursor(CursorShape.HAND);
         }
 
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        IconCoordinate tex;
-        switch (state) {
-            case STATE_DISABLED:
-                tex = disabledTexture;
-                break;
-            case STATE_HOVERED:
-                tex = hoveredTexture;
-                break;
-            case STATE_DEFAULT:
-            default:
-                tex = defaultTexture;
-        }
-        drawGuiIcon(xPosition, yPosition, width, height, tex);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+        IconCoordinate tex = switch (state) {
+            case STATE_DISABLED -> this.disabledTexture;
+            case STATE_HOVERED -> this.hoveredTexture;
+            default -> this.defaultTexture;
+        };
+        drawGuiIcon(this.xPosition, this.yPosition, this.width, this.height, tex);
 
         mouseDragged(mc, mouseX, mouseY);
 
-        int textColor;
-        switch (state) {
-            case STATE_DISABLED:
-                textColor = 0xA0A0A0;
-                break;
-            case STATE_DEFAULT:
-                textColor = 0xE0E0E0;
-                break;
-            case STATE_HOVERED:
-            default:
-                textColor = 0xFFFFA0;
-                break;
-        }
-        drawStringCenteredShadow(mc.font, displayString, xPosition + width / 2, yPosition + (height - 8) / 2, textColor);
+        int textColor = switch (state) {
+            case STATE_DISABLED -> 0xA0A0A0;
+            case STATE_DEFAULT -> 0xE0E0E0;
+            default -> 0xFFFFA0;
+        };
+        drawStringCenteredShadow(mc.font, this.displayString, this.xPosition + this.width / 2, this.yPosition + (this.height - 8) / 2, textColor);
     }
 
     public boolean isHovered(int mouseX, int mouseY)
     {
-        return mouseX >= xPosition && mouseY >= yPosition && mouseX < xPosition + width && mouseY < yPosition + height;
+        return mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height;
     }
 
     public void mouseDragged(Minecraft mc, int mouseX, int mouseY)
@@ -140,7 +125,7 @@ public class ButtonElement extends Gui implements GuiElement
 
     public boolean mouseClicked(Minecraft mc, int mouseX, int mouseY)
     {
-        return enabled && mouseX >= xPosition && mouseY >= yPosition && mouseX < xPosition + width && mouseY < yPosition + height;
+        return this.enabled && mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height;
     }
     
     public ButtonElement setListener(Listener<ButtonElement> listener) {
@@ -180,22 +165,22 @@ public class ButtonElement extends Gui implements GuiElement
 
 	@Override
 	public int getX() {
-		return xPosition;
+		return this.xPosition;
 	}
 
 	@Override
 	public int getY() {
-		return yPosition;
+		return this.yPosition;
 	}
 
 	@Override
 	public int getWidth() {
-		return width;
+		return this.width;
 	}
 
 	@Override
 	public int getHeight() {
-		return height;
+		return this.height;
 	}
     
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ClickableLabelElement.java b/game/client/src/main/java/net/minecraft/client/gui/ClickableLabelElement.java
index 8f833c0d6..004a75558 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ClickableLabelElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ClickableLabelElement.java
@@ -1,14 +1,13 @@
 package net.minecraft.client.gui;
 
 import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.render.window.CursorShape;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
-
-import static net.minecraft.client.render.OpenGLHelper.glColor1i;
 
 public class ClickableLabelElement extends ButtonElement {
     private int textColor;
@@ -43,7 +42,7 @@ public class ClickableLabelElement extends ButtonElement {
     }
 
     public int getTextColor() {
-        return textColor;
+        return this.textColor;
     }
 
     public void setTextColor(int textColor) {
@@ -51,7 +50,7 @@ public class ClickableLabelElement extends ButtonElement {
     }
 
     public int getBgColor() {
-        return bgColor;
+        return this.bgColor;
     }
 
     public void setBgColor(int bgColor) {
@@ -59,7 +58,7 @@ public class ClickableLabelElement extends ButtonElement {
     }
 
     public boolean isShadow() {
-        return shadow;
+        return this.shadow;
     }
 
     public void setShadow(boolean shadow) {
@@ -68,56 +67,57 @@ public class ClickableLabelElement extends ButtonElement {
 
     @Override
     public void drawButton(Minecraft mc, int mouseX, int mouseY) {
-        if (!visible) {
+        if (!this.visible) {
             return;
         }
+        GLRenderer.enableState(State.BLEND);
 
-        boolean hovered = mouseX >= xPosition && mouseY >= yPosition && mouseX < xPosition + width && mouseY < yPosition + height;
-        if (hovered && enabled) {
+        boolean hovered = mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height;
+        if (hovered && this.enabled) {
             mc.currentScreen.setDesiredCursor(CursorShape.HAND);
         }
 
         if (this.icon != null) {
-            if (hovered && enabled) {
-                this.width = 2 + this.icon.width + 4 + MathHelper.ceil(mc.font.stringWidthDouble(displayString)) + 2;
+            if (hovered && this.enabled) {
+                this.width = 2 + this.icon.width + 4 + MathHelper.ceil(mc.font.stringWidthDouble(this.displayString)) + 2;
             } else {
                 this.width = 2 + this.icon.width + 2;
             }
         } else {
-            width = MathHelper.ceil(mc.font.stringWidthDouble(displayString)) + 4;
+            this.width = MathHelper.ceil(mc.font.stringWidthDouble(this.displayString)) + 4;
         }
 
-        drawRect(xPosition, yPosition, xPosition + width, yPosition + height, enabled ? (hovered ? 0x7F8080C0 : bgColor) : 0x00000000);
+        drawRect(this.xPosition, this.yPosition, this.xPosition + this.width, this.yPosition + this.height, this.enabled ? (hovered ? 0x7F8080C0 : this.bgColor) : 0x00000000);
 
         if (this.icon != null) {
             if (hovered) {
-                if (shadow) {
-                    glColor1i(makeShadow(0xFFFFFFA0));
-                    drawGuiIcon(xPosition + 3, yPosition + 2, icon.width, icon.height, icon);
-                    glColor1i(0xFFFFFFA0);
-                    drawGuiIcon(xPosition + 2, yPosition + 1, icon.width, icon.height, icon);
-                    drawStringShadow(mc.font, displayString, xPosition + 4 + icon.width + 2, yPosition + 2, 0xFFFFFFA0);
+                if (this.shadow) {
+                    GLRenderer.setColor1i(makeShadow(0xFFFFFFA0));
+                    drawGuiIcon(this.xPosition + 3, this.yPosition + 2, this.icon.width, this.icon.height, this.icon);
+                    GLRenderer.setColor1i(0xFFFFFFA0);
+                    drawGuiIcon(this.xPosition + 2, this.yPosition + 1, this.icon.width, this.icon.height, this.icon);
+                    drawStringShadow(mc.font, this.displayString, this.xPosition + 4 + this.icon.width + 2, this.yPosition + 2, 0xFFFFFFA0);
                 } else {
-                    glColor1i(0xFFFFFFA0);
-                    drawGuiIcon(xPosition + 2, yPosition + 1, icon.width, icon.height, icon);
-                    drawStringNoShadow(mc.font, displayString, xPosition + 4 + icon.width + 2, yPosition + 2, 0xFFFFFFA0);
+                    GLRenderer.setColor1i(0xFFFFFFA0);
+                    drawGuiIcon(this.xPosition + 2, this.yPosition + 1, this.icon.width, this.icon.height, this.icon);
+                    drawStringNoShadow(mc.font, this.displayString, this.xPosition + 4 + this.icon.width + 2, this.yPosition + 2, 0xFFFFFFA0);
                 }
             } else {
-                if (shadow) {
-                    glColor1i(makeShadow(textColor));
-                    drawGuiIcon(xPosition + 3, yPosition + 2, icon.width, icon.height, icon);
-                    glColor1i(textColor);
-                    drawGuiIcon(xPosition + 2, yPosition + 1, icon.width, icon.height, icon);
+                if (this.shadow) {
+                    GLRenderer.setColor1i(makeShadow(this.textColor));
+                    drawGuiIcon(this.xPosition + 3, this.yPosition + 2, this.icon.width, this.icon.height, this.icon);
+                    GLRenderer.setColor1i(this.textColor);
+                    drawGuiIcon(this.xPosition + 2, this.yPosition + 1, this.icon.width, this.icon.height, this.icon);
                 } else {
-                    glColor1i(textColor);
-                    drawGuiIcon(xPosition + 2, yPosition + 1, icon.width, icon.height, icon);
+                    GLRenderer.setColor1i(this.textColor);
+                    drawGuiIcon(this.xPosition + 2, this.yPosition + 1, this.icon.width, this.icon.height, this.icon);
                 }
             }
         } else {
-            if (enabled && (shadow || hovered)) {
-                drawStringShadow(mc.font, displayString, xPosition + 4, yPosition + 2, hovered ? 0xFFFFFFA0 : textColor);
+            if (this.enabled && (this.shadow || hovered)) {
+                drawStringShadow(mc.font, this.displayString, this.xPosition + 4, this.yPosition + 2, hovered ? 0xFFFFFFA0 : this.textColor);
             } else {
-                drawStringNoShadow(mc.font, displayString, xPosition + 4, yPosition + 2, 0xFF7F7F7F);
+                drawStringNoShadow(mc.font, this.displayString, this.xPosition + 4, this.yPosition + 2, 0xFF7F7F7F);
             }
         }
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ControllerGlyphElement.java b/game/client/src/main/java/net/minecraft/client/gui/ControllerGlyphElement.java
index b63e5c2bf..bcdeb7118 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ControllerGlyphElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ControllerGlyphElement.java
@@ -4,7 +4,6 @@ import net.minecraft.client.Minecraft;
 import net.minecraft.client.input.controller.ControllerInput;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 public class ControllerGlyphElement extends Gui {
     public static final int GLYPH_WIDTH = 15;
@@ -69,7 +68,7 @@ public class ControllerGlyphElement extends Gui {
             this.minecraft.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/" + controller.getType().getAssetName() + ".png").bind();
         }
 
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
+//        GL11.glEnable(GL11.GL_TEXTURE_2D);
 
         drawTexturedModalRect(x, y, glyph.getU(), glyph.getV(), GLYPH_WIDTH, GLYPH_HEIGHT);
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ExceptionPopupElement.java b/game/client/src/main/java/net/minecraft/client/gui/ExceptionPopupElement.java
index 7131acf16..8401570ee 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ExceptionPopupElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ExceptionPopupElement.java
@@ -8,7 +8,7 @@ import net.minecraft.core.Global;
 import net.minecraft.core.net.command.TextFormatting;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.Sys;
-import org.lwjgl.opengl.GL11;
+import org.lwjgl.opengl.GL41;
 
 import java.text.SimpleDateFormat;
 import java.util.Date;
@@ -16,27 +16,24 @@ import java.util.Map;
 
 public class ExceptionPopupElement {
 
-    public static PopupScreen create(Screen parent, Throwable e, Minecraft mc){
-        int scale = Math.max(mc.resolution.getScale(),1);
+    public static PopupScreen create(Screen parent, Throwable e, Minecraft mc) {
+        int scale = Math.max(mc.resolution.getScale(), 1);
         StringBuilder s = new StringBuilder("Minecraft ran into an unexpected problem!\n\n");
         s.append("To prevent more problems, the current game has quit, but you can try to keep playing.\n\n");
         s.append("If you wish to report this, please copy this entire text and post it on the support portal at")
-                .append(TextFormatting.LIGHT_BLUE)
-                .append(" https://bugs.betterthanadventure.net/")
-                .append(TextFormatting.WHITE).append("\n\n");
-        try
-        {
+            .append(TextFormatting.LIGHT_BLUE)
+            .append(" https://bugs.betterthanadventure.net/")
+            .append(TextFormatting.WHITE).append("\n\n");
+        try {
             s.append(TextFormatting.WHITE).append("Generated ").append((new SimpleDateFormat()).format(new Date())).append("\n\n");
             s.append("Minecraft: Better than Adventure! ").append(Minecraft.VERSION).append("\n");
             s.append("OS: ").append(System.getProperty("os.name")).append(" (").append(System.getProperty("os.arch")).append(") version ").append(System.getProperty("os.version")).append("\n");
             s.append("Java: ").append(System.getProperty("java.version")).append(", ").append(System.getProperty("java.vendor")).append("\n");
             s.append("VM: ").append(System.getProperty("java.vm.name")).append(" (").append(System.getProperty("java.vm.info")).append("), ").append(System.getProperty("java.vm.vendor")).append("\n");
             s.append("LWJGL: ").append(Sys.getVersion()).append("\n");
-            //s1 = GL11.glGetString(7936 /*GL_VENDOR*/);
-            s.append("OpenGL: ").append(GL11.glGetString(GL11.GL_RENDERER)).append(" version ").append(GL11.glGetString(7938 /*GL_VERSION*/)).append(", ").append(GL11.glGetString(7936 /*GL_VENDOR*/)).append("\n\n");
-        }
-        catch(Throwable throwable)
-        {
+            //s1 = GL11.glGetString(GL41.GL_VENDOR);
+            s.append("OpenGL: ").append(GL41.glGetString(GL41.GL_RENDERER)).append(" version ").append(GL41.glGetString(GL41.GL_VERSION)).append(", ").append(GL41.glGetString(GL41.GL_VENDOR)).append("\n\n");
+        } catch (Throwable throwable) {
             s.append("[failed to get system properties (").append(throwable).append(")]\n\n");
         }
         s.append(TextFormatting.RED).append(e);
@@ -47,35 +44,31 @@ public class ExceptionPopupElement {
         s.append(TextFormatting.WHITE);
 
 
-        PopupScreen popup = new PopupBuilder(parent,860/scale).withLabel("gui.exception.label.exception_occurred")
-                .withMessageBox("gui.exception.list",400/scale,s.toString(),(860/scale) / mc.font.getFont().charWidth('m'))
-                .withButtonGroup("gui.exception.choice",new String[]{"gui.exception.button.back","gui.exception.button.copy_error"},new int[]{0,1})
-                .withOnCloseListener(new PopupListener(mc,s.toString().replaceAll("§[0-9a-f|klmnor]","")))
-                .build();
-        return popup;
+        return new PopupBuilder(parent, 860 / scale).withLabel("gui.exception.label.exception_occurred")
+            .withMessageBox("gui.exception.list", 400 / scale, s.toString(), (860 / scale) / mc.font.getFont().charWidth('m'))
+            .withButtonGroup("gui.exception.choice", new String[]{"gui.exception.button.back", "gui.exception.button.copy_error"}, new int[]{0, 1})
+            .withOnCloseListener(new PopupListener(mc, s.toString().replaceAll("§[0-9a-f|klmnor]", "")))
+            .build();
     }
 
-    public static PopupScreen createFatal(Throwable e, Minecraft mc){
-        int scale = Math.max(mc.resolution.getScale(),1);
+    public static PopupScreen createFatal(Throwable e, Minecraft mc) {
+        int scale = Math.max(mc.resolution.getScale(), 1);
         StringBuilder s = new StringBuilder("Minecraft ran into an unexpected problem that it cannot recover from!\n\n");
         s.append("The current game has quit, please restart the game.\n\n");
         s.append("If you wish to report this, please copy this entire text and post it on the support portal at")
-                .append(TextFormatting.LIGHT_BLUE)
-                .append(" https://bugs.betterthanadventure.net/")
-                .append(TextFormatting.WHITE).append("\n\n");
-        try
-        {
+            .append(TextFormatting.LIGHT_BLUE)
+            .append(" https://bugs.betterthanadventure.net/")
+            .append(TextFormatting.WHITE).append("\n\n");
+        try {
             s.append(TextFormatting.WHITE).append("Generated ").append((new SimpleDateFormat()).format(new Date())).append("\n\n");
             s.append("Minecraft: Better than Adventure! ").append(Minecraft.VERSION).append("\n");
             s.append("OS: ").append(System.getProperty("os.name")).append(" (").append(System.getProperty("os.arch")).append(") version ").append(System.getProperty("os.version")).append("\n");
             s.append("Java: ").append(System.getProperty("java.version")).append(", ").append(System.getProperty("java.vendor")).append("\n");
             s.append("VM: ").append(System.getProperty("java.vm.name")).append(" (").append(System.getProperty("java.vm.info")).append("), ").append(System.getProperty("java.vm.vendor")).append("\n");
             s.append("LWJGL: ").append(Sys.getVersion()).append("\n");
-            //s1 = GL11.glGetString(7936 /*GL_VENDOR*/);
-            s.append("OpenGL: ").append(GL11.glGetString(7937 /*GL_RENDERER*/)).append(" version ").append(GL11.glGetString(7938 /*GL_VERSION*/)).append(", ").append(GL11.glGetString(7936 /*GL_VENDOR*/)).append("\n\n");
-        }
-        catch(Throwable throwable)
-        {
+            //s1 = GL11.glGetString(GL41.GL_VENDOR);
+            s.append("OpenGL: ").append(GL41.glGetString(GL41.GL_RENDERER)).append(" version ").append(GL41.glGetString(GL41.GL_VERSION)).append(", ").append(GL41.glGetString(GL41.GL_VENDOR)).append("\n\n");
+        } catch (Throwable throwable) {
             s.append("[failed to get system properties (").append(throwable).append(")]\n\n");
         }
         s.append(TextFormatting.RED).append(e);
@@ -87,36 +80,32 @@ public class ExceptionPopupElement {
 
         ScreenBlank screen = new ScreenBlank();
         mc.displayScreen(screen);
-        PopupScreen popup = new PopupBuilder(screen,860/scale).withLabel("gui.exception.label.fatal_error")
-                .withMessageBox("gui.exception.list",400/scale,s.toString(),(860/scale) / mc.font.getFont().charWidth('m'))
-                .withButtonGroup("gui.exception.choice",new String[]{"gui.exception.button.copy_error","gui.exception.button.copy_error_and_quit"},new int[]{0,2},new boolean[]{false,true})
-                .withBackgroundColor(0xff402020, 0xff501010)
-                .withOnCloseListener(new PopupListener(mc,s.toString().replaceAll("§[0-9a-f|klmnor]","")))
-                .build();
-        return popup;
+        return new PopupBuilder(screen, 860 / scale).withLabel("gui.exception.label.fatal_error")
+            .withMessageBox("gui.exception.list", 400 / scale, s.toString(), (860 / scale) / mc.font.getFont().charWidth('m'))
+            .withButtonGroup("gui.exception.choice", new String[]{"gui.exception.button.copy_error", "gui.exception.button.copy_error_and_quit"}, new int[]{0, 2}, new boolean[]{false, true})
+            .withBackgroundColor(0xff402020, 0xff501010)
+            .withOnCloseListener(new PopupListener(mc, s.toString().replaceAll("§[0-9a-f|klmnor]", "")))
+            .build();
     }
 
-    public static PopupScreen createStartupError(Throwable e, Minecraft mc){
-        int scale = Math.max(mc.resolution.getScale(),1);
+    public static PopupScreen createStartupError(Throwable e, Minecraft mc) {
+        int scale = Math.max(mc.resolution.getScale(), 1);
         StringBuilder s = new StringBuilder("An error has prevented Minecraft from starting up correctly!\n\n");
         s.append("The game cannot continue, please restart the game.\n\n");
         s.append("If you wish to report this, please copy this entire text and post it on the support portal at")
-                .append(TextFormatting.LIGHT_BLUE)
-                .append(" https://bugs.betterthanadventure.net/")
-                .append(TextFormatting.WHITE).append("\n\n");
-        try
-        {
+            .append(TextFormatting.LIGHT_BLUE)
+            .append(" https://bugs.betterthanadventure.net/")
+            .append(TextFormatting.WHITE).append("\n\n");
+        try {
             s.append(TextFormatting.WHITE).append("Generated ").append((new SimpleDateFormat()).format(new Date())).append("\n\n");
             s.append("Minecraft: Better than Adventure! ").append(Minecraft.VERSION).append("\n");
             s.append("OS: ").append(System.getProperty("os.name")).append(" (").append(System.getProperty("os.arch")).append(") version ").append(System.getProperty("os.version")).append("\n");
             s.append("Java: ").append(System.getProperty("java.version")).append(", ").append(System.getProperty("java.vendor")).append("\n");
             s.append("VM: ").append(System.getProperty("java.vm.name")).append(" (").append(System.getProperty("java.vm.info")).append("), ").append(System.getProperty("java.vm.vendor")).append("\n");
             s.append("LWJGL: ").append(Sys.getVersion()).append("\n");
-            //s1 = GL11.glGetString(7936 /*GL_VENDOR*/);
-            s.append("OpenGL: ").append(GL11.glGetString(GL11.GL_RENDERER)).append(" version ").append(GL11.glGetString(7938 /*GL_VERSION*/)).append(", ").append(GL11.glGetString(7936 /*GL_VENDOR*/)).append("\n\n");
-        }
-        catch(Throwable throwable)
-        {
+            //s1 = GL41.glGetString(GL41.GL_VENDOR);
+            s.append("OpenGL: ").append(GL41.glGetString(GL41.GL_RENDERER)).append(" version ").append(GL41.glGetString(GL41.GL_VERSION)).append(", ").append(GL41.glGetString(GL41.GL_VENDOR)).append("\n\n");
+        } catch (Throwable throwable) {
             s.append("[failed to get system properties (").append(throwable).append(")]\n\n");
         }
         s.append(TextFormatting.RED).append(e);
@@ -128,13 +117,12 @@ public class ExceptionPopupElement {
 
         ScreenBlank screen = new ScreenBlank();
         mc.displayScreen(screen);
-        PopupScreen popup = new PopupBuilder(screen,860/scale).withLabel("gui.exception.label.startup_error")
-                .withMessageBox("gui.exception.list",400/scale,s.toString(),(860/scale) / mc.font.getFont().charWidth('m'))
-                .withButtonGroup("gui.exception.choice",new String[]{"gui.exception.button.copy_error","gui.exception.button.copy_error_and_quit"},new int[]{0,2},new boolean[]{false,true})
-                .withBackgroundColor(0xff402020, 0xff501010)
-                .withOnCloseListener(new PopupListener(mc,s.toString().replaceAll("§[0-9a-f|klmnor]","")))
-                .build();
-        return popup;
+        return new PopupBuilder(screen, 860 / scale).withLabel("gui.exception.label.startup_error")
+            .withMessageBox("gui.exception.list", 400 / scale, s.toString(), (860 / scale) / mc.font.getFont().charWidth('m'))
+            .withButtonGroup("gui.exception.choice", new String[]{"gui.exception.button.copy_error", "gui.exception.button.copy_error_and_quit"}, new int[]{0, 2}, new boolean[]{false, true})
+            .withBackgroundColor(0xff402020, 0xff501010)
+            .withOnCloseListener(new PopupListener(mc, s.toString().replaceAll("§[0-9a-f|klmnor]", "")))
+            .build();
     }
 
     private static class PopupListener implements PopupCloseListener {
@@ -142,25 +130,23 @@ public class ExceptionPopupElement {
         private final Minecraft mc;
         private final String message;
 
-        private PopupListener(Minecraft mc, String message){
+        private PopupListener(Minecraft mc, String message) {
             this.mc = mc;
             this.message = message;
         }
 
         @Override
         public void onClosed(int statusCode, @NotNull Map<String, ?> results) {
-            switch (statusCode){
-                case 0:
-                    mc.hasCrashed = false;
-                    break;
-                case 1:
-                    Global.accessor.copyToClipboard(message);
-                    mc.hasCrashed = false;
-                    break;
-                case 2:
-                    Global.accessor.copyToClipboard(message);
-                    mc.shutdownMinecraftApplet();
-                    break;
+            switch (statusCode) {
+                case 0 -> this.mc.hasCrashed = false;
+                case 1 -> {
+                    Global.accessor.copyToClipboard(this.message);
+                    this.mc.hasCrashed = false;
+                }
+                case 2 -> {
+                    Global.accessor.copyToClipboard(this.message);
+                    this.mc.shutdownMinecraftApplet();
+                }
             }
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/Gui.java b/game/client/src/main/java/net/minecraft/client/gui/Gui.java
index 765af2463..a32fcd029 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/Gui.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/Gui.java
@@ -1,32 +1,29 @@
 package net.minecraft.client.gui;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.client.render.texture.meta.gui.GuiTextureProperties;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 import java.util.Objects;
 
-public class Gui
-{
-
-    public Gui()
-    {
+public class Gui {
+    public float zLevel;
+    public Gui() {
         this.zLevel = 0.0F;
     }
 
-    public void drawLineHorizontal(int minX, int maxX, final int minY, final int argb)
-    {
-        if(maxX < minX)
-        {
+    public void drawLineHorizontal(int minX, int maxX, final int minY, final int argb) {
+        if (maxX < minX) {
             final int temp = minX;
             minX = maxX;
             maxX = temp;
@@ -34,10 +31,8 @@ public class Gui
         drawRect(minX, minY, maxX + 1, minY + 1, argb);
     }
 
-    public void drawLineHorizontalDouble(double minX, double maxX, final double minY, final int argb)
-    {
-        if(maxX < minX)
-        {
+    public void drawLineHorizontalDouble(double minX, double maxX, final double minY, final int argb) {
+        if (maxX < minX) {
             final double temp = minX;
             minX = maxX;
             maxX = temp;
@@ -45,10 +40,8 @@ public class Gui
         drawRectDouble(minX, minY, maxX + 1, minY + 1, argb);
     }
 
-    public void drawLineVertical(final int minX, int minY, int maxY, final int argb)
-    {
-        if(maxY < minY)
-        {
+    public void drawLineVertical(final int minX, int minY, int maxY, final int argb) {
+        if (maxY < minY) {
             final int temp = minY;
             minY = maxY;
             maxY = temp;
@@ -56,10 +49,8 @@ public class Gui
         drawRect(minX, minY + 1, minX + 1, maxY, argb);
     }
 
-    public void drawLineVerticalDouble(final double minX, double minY, double maxY, final int argb)
-    {
-        if(maxY < minY)
-        {
+    public void drawLineVerticalDouble(final double minX, double minY, double maxY, final int argb) {
+        if (maxY < minY) {
             final double temp = minY;
             minY = maxY;
             maxY = temp;
@@ -67,69 +58,57 @@ public class Gui
         drawRectDouble(minX, minY + 1, minX + 1, maxY, argb);
     }
 
-    public void drawRect(int minX, int minY, int maxX, int maxY, final int argb)
-    {
-        if(minX < maxX)
-        {
+    public void drawRect(int minX, int minY, int maxX, int maxY, final int argb) {
+        if (minX < maxX) {
             final int temp = minX;
             minX = maxX;
             maxX = temp;
         }
-        if(minY < maxY)
-        {
+        if (minY < maxY) {
             final int temp = minY;
             minY = maxY;
             maxY = temp;
         }
-        final float a = (float)(argb >> 24 & 0xff) / 255F;
-        final float r = (float)(argb >> 16 & 0xff) / 255F;
-        final float g = (float)(argb >> 8 & 0xff) / 255F;
-        final float b = (float)(argb & 0xff) / 255F;
-        final Tessellator tessellator = Tessellator.instance;
-        GL11.glEnable(GL_BLEND);
-        GL11.glDisable(GL_TEXTURE_2D);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glColor4f(r, g, b, a);
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setColor1i(argb);
         tessellator.startDrawingQuads();
         tessellator.addVertex(minX, maxY, this.zLevel);
         tessellator.addVertex(maxX, maxY, this.zLevel);
         tessellator.addVertex(maxX, minY, this.zLevel);
         tessellator.addVertex(minX, minY, this.zLevel);
         tessellator.draw();
-        GL11.glEnable(GL_TEXTURE_2D);
-        GL11.glDisable(GL_BLEND);
+        GLRenderer.popFrame();
     }
-    public void drawRectDouble(double minX, double minY, double maxX, double maxY, final int argb)
-    {
-        if(minX < maxX)
-        {
+
+    public void drawRectDouble(double minX, double minY, double maxX, double maxY, final int argb) {
+        if (minX < maxX) {
             final double temp = minX;
             minX = maxX;
             maxX = temp;
         }
-        if(minY < maxY)
-        {
+        if (minY < maxY) {
             final double temp = minY;
             minY = maxY;
             maxY = temp;
         }
-        final float a = (float)(argb >> 24 & 0xff) / 255F;
-        final float r = (float)(argb >> 16 & 0xff) / 255F;
-        final float g = (float)(argb >> 8 & 0xff) / 255F;
-        final float b = (float)(argb & 0xff) / 255F;
-        final Tessellator tessellator = Tessellator.instance;
-        GL11.glEnable(GL_BLEND);
-        GL11.glDisable(GL_TEXTURE_2D);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glColor4f(r, g, b, a);
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setColor1i(argb);
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertex(minX, maxY, this.zLevel);
         tessellator.addVertex(maxX, maxY, this.zLevel);
         tessellator.addVertex(maxX, minY, this.zLevel);
         tessellator.addVertex(minX, minY, this.zLevel);
         tessellator.draw();
-        GL11.glEnable(GL_TEXTURE_2D);
-        GL11.glDisable(GL_BLEND);
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.popFrame();
     }
 
     public void drawBox(final int minX, final int minY, final int maxX, final int maxY, final int argb, final int lineThickness) {
@@ -139,108 +118,98 @@ public class Gui
         drawRect(maxX - lineThickness, minY + lineThickness, maxX, maxY - lineThickness, argb);
     }
 
-    public void drawRectNoBlend(int minX, int minY, int maxX, int maxY, final int argb)
-    {
-        if(minX < maxX)
-        {
+    public void drawRectNoBlend(int minX, int minY, int maxX, int maxY, final int argb) {
+        if (minX < maxX) {
             final int temp = minX;
             minX = maxX;
             maxX = temp;
         }
-        if(minY < maxY)
-        {
+        if (minY < maxY) {
             final int temp = minY;
             minY = maxY;
             maxY = temp;
         }
-        final float a = (float)(argb >> 24 & 0xff) / 255F;
-        final float r = (float)(argb >> 16 & 0xff) / 255F;
-        final float g = (float)(argb >> 8 & 0xff) / 255F;
-        final float b = (float)(argb & 0xff) / 255F;
-        final Tessellator tessellator = Tessellator.instance;
-        GL11.glDisable(GL_TEXTURE_2D);
-        GL11.glColor4f(r, g, b, a);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.setColor1i(argb);
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertex(minX, maxY, 0.0D);
         tessellator.addVertex(maxX, maxY, 0.0D);
         tessellator.addVertex(maxX, minY, 0.0D);
         tessellator.addVertex(minX, minY, 0.0D);
         tessellator.draw();
-        GL11.glEnable(GL_TEXTURE_2D);
+        GLRenderer.popFrame();
     }
-    
+
     public void drawRectWidthHeight(final int x, final int y, final int width, final int height, final int argb) {
-    	final float a = ((argb >> 24) & 0xFF) / 255f;
-    	final float r = ((argb >> 16) & 0xFF) / 255f;
-    	final float g = ((argb >>  8) & 0xFF) / 255f;
-    	final float b = ((argb >>  0) & 0xFF) / 255f;
-    	glColor4f(r, g, b, a);
-    	glDisable(GL_TEXTURE_2D);
-        final Tessellator tessellator = Tessellator.instance;
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.setColor1i(argb);
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertex(x, y, 0);
-        tessellator.addVertex(x, y+height, 0);
-        tessellator.addVertex(x+width, y+height, 0);
-        tessellator.addVertex(x+width, y, 0);
+        tessellator.addVertex(x, y + height, 0);
+        tessellator.addVertex(x + width, y + height, 0);
+        tessellator.addVertex(x + width, y, 0);
         tessellator.draw();
-        glEnable(GL_TEXTURE_2D);
-    }
-
-    public void drawGradientRect(final int minX, final int minY, final int maxX, final int maxY, final int argb1, final int argb2)
-    {
-        final float a1 = (float)(argb1 >> 24 & 0xff) / 255F;
-        final float r1 = (float)(argb1 >> 16 & 0xff) / 255F;
-        final float g1 = (float)(argb1 >> 8 & 0xff) / 255F;
-        final float b1 = (float)(argb1 & 0xff) / 255F;
-        final float a2 = (float)(argb2 >> 24 & 0xff) / 255F;
-        final float r2 = (float)(argb2 >> 16 & 0xff) / 255F;
-        final float g2 = (float)(argb2 >> 8 & 0xff) / 255F;
-        final float b2 = (float)(argb2 & 0xff) / 255F;
-        GL11.glDisable(GL_TEXTURE_2D);
-        GL11.glEnable(GL_BLEND);
-        GL11.glDisable(GL_ALPHA_TEST);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glShadeModel(GL_SMOOTH);
-        final Tessellator tessellator = Tessellator.instance;
+        GLRenderer.popFrame();
+    }
+
+    public void drawGradientRect(final int minX, final int minY, final int maxX, final int maxY, final int argb1, final int argb2) {
+        final float a1 = (float) (argb1 >> 24 & 0xff) / 255F;
+        final float r1 = (float) (argb1 >> 16 & 0xff) / 255F;
+        final float g1 = (float) (argb1 >> 8 & 0xff) / 255F;
+        final float b1 = (float) (argb1 & 0xff) / 255F;
+        final float a2 = (float) (argb2 >> 24 & 0xff) / 255F;
+        final float r2 = (float) (argb2 >> 16 & 0xff) / 255F;
+        final float g2 = (float) (argb2 >> 8 & 0xff) / 255F;
+        final float b2 = (float) (argb2 & 0xff) / 255F;
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.enableState(State.BLEND);
+//        GL11.glDisable(GL_ALPHA_TEST);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+//        GL11.glShadeModel(GL_SMOOTH);
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_F(r1, g1, b1, a1);
+        tessellator.setColor4f(r1, g1, b1, a1);
         tessellator.addVertex(maxX, minY, 0.0D);
         tessellator.addVertex(minX, minY, 0.0D);
-        tessellator.setColorRGBA_F(r2, g2, b2, a2);
+        tessellator.setColor4f(r2, g2, b2, a2);
         tessellator.addVertex(minX, maxY, 0.0D);
         tessellator.addVertex(maxX, maxY, 0.0D);
         tessellator.draw();
-        GL11.glShadeModel(GL_FLAT);
-        GL11.glDisable(GL_BLEND);
-        GL11.glEnable(GL_ALPHA_TEST);
-        GL11.glEnable(GL_TEXTURE_2D);
+//        GL11.glShadeModel(GL_FLAT);
+        GLRenderer.disableState(State.BLEND);
+//        GL11.glEnable(GL_ALPHA_TEST);
+        GLRenderer.popFrame();
     }
 
     public void drawStringCenteredShadow(final @NotNull FontRenderer fontRenderer, final @NotNull CharSequence chars, final int x, final int y, final int argb) {
-        fontRenderer.renderCentered(Tessellator.instance, chars, x, y).setZ(this.zLevel).setShadow().setColor(argb).call();
+        fontRenderer.renderCentered(chars, x, y).setZ(this.zLevel).setShadow().setColor(argb).call();
     }
 
     public void drawStringCenteredNoShadow(final @NotNull FontRenderer fontRenderer, final @NotNull CharSequence chars, final int x, final int y, final int argb) {
-        fontRenderer.renderCentered(Tessellator.instance, chars, x, y).setZ(this.zLevel).setColor(argb).call();
+        fontRenderer.renderCentered(chars, x, y).setZ(this.zLevel).setColor(argb).call();
     }
 
     public void drawStringShadow(final @NotNull FontRenderer fontRenderer, final @NotNull CharSequence chars, final int x, final int y, final int argb) {
-        fontRenderer.render(Tessellator.instance, chars, x, y).setZ(this.zLevel).setShadow().setColor(argb).call();
+        fontRenderer.render(chars, x, y).setZ(this.zLevel).setShadow().setColor(argb).call();
     }
-    
+
     public void drawStringNoShadow(final @NotNull FontRenderer fontRenderer, final @NotNull CharSequence chars, final int x, final int y, final int argb) {
-        fontRenderer.render(Tessellator.instance, chars, x, y).setZ(this.zLevel).setColor(argb).call();
+        fontRenderer.render(chars, x, y).setZ(this.zLevel).setColor(argb).call();
     }
 
     public void drawStringConstrained(final @NotNull FontRenderer fontRenderer, final @NotNull CharSequence chars, final int x, final int y, final int maxWidth, final int argb) {
-        fontRenderer.renderWidthConstrained(Tessellator.instance, chars, x, y, maxWidth).setZ(this.zLevel).setColor(argb).call();
+        fontRenderer.renderWidthConstrained(chars, x, y, maxWidth).setZ(this.zLevel).setColor(argb).call();
     }
 
-    public void drawTexturedModalRect(final int x, final int y, final int u, final int v, final int width, final int height)
-    {
+    public void drawTexturedModalRect(final int x, final int y, final int u, final int v, final int width, final int height) {
         final float uScale = 0.00390625F;
         final float vScale = 0.00390625F;
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertexWithUV(x, y + height, this.zLevel, (u) * uScale, (v + height) * vScale);
         tessellator.addVertexWithUV(x + width, y + height, this.zLevel, (u + width) * uScale, (v + height) * vScale);
@@ -248,73 +217,69 @@ public class Gui
         tessellator.addVertexWithUV(x, y, this.zLevel, (u) * uScale, (v) * vScale);
         tessellator.draw();
     }
-    public void drawTexturedModalRect(final int x, final int y, final int u, final int v, final int width, final int height, final double uScale, final double vScale)
-    {
+
+    public void drawTexturedModalRect(final int x, final int y, final int u, final int v, final int width, final int height, final double uScale, final double vScale) {
         final double off = 0.05d;
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(x - off,        y + height + off, this.zLevel, (u) * uScale,        (v + height) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y + height + off, this.zLevel, (u + width) * uScale,    (v + height) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y - off, this.zLevel, (u + width) * uScale,    (v) * vScale);
-        tessellator.addVertexWithUV(x - off,        y - off, this.zLevel, (u) * uScale,        (v) * vScale);
+        tessellator.addVertexWithUV(x - off, y + height + off, this.zLevel, (u) * uScale, (v + height) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y + height + off, this.zLevel, (u + width) * uScale, (v + height) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y - off, this.zLevel, (u + width) * uScale, (v) * vScale);
+        tessellator.addVertexWithUV(x - off, y - off, this.zLevel, (u) * uScale, (v) * vScale);
         tessellator.draw();
     }
-    public void drawTexturedModalRectDouble(final double x, final double y, final double u, final double v, final double width, final double height, final double uScale, final double vScale)
-    {
+
+    public void drawTexturedModalRectDouble(final double x, final double y, final double u, final double v, final double width, final double height, final double uScale, final double vScale) {
         final double off = 0.05d;
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(x - off,        y + height + off, this.zLevel, (u + 0) * uScale,        (v + height) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y + height + off, this.zLevel, (u + width) * uScale,    (v + height) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y - off, this.zLevel, (u + width) * uScale,    (v + 0) * vScale);
-        tessellator.addVertexWithUV(x - off,        y - off, this.zLevel, (u + 0) * uScale,        (v + 0) * vScale);
+        tessellator.addVertexWithUV(x - off, y + height + off, this.zLevel, (u + 0) * uScale, (v + height) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y + height + off, this.zLevel, (u + width) * uScale, (v + height) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y - off, this.zLevel, (u + width) * uScale, (v + 0) * vScale);
+        tessellator.addVertexWithUV(x - off, y - off, this.zLevel, (u + 0) * uScale, (v + 0) * vScale);
         tessellator.draw();
     }
 
-    public void drawTexturedModalRect(final int x, final int y, final int u, final int v, final int width, final int height, final double uScale, final double vScale, final double off)
-    {
-        final Tessellator tessellator = Tessellator.instance;
+    public void drawTexturedModalRect(final int x, final int y, final int u, final int v, final int width, final int height, final double uScale, final double vScale, final double off) {
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(x - off,        y + height + off, this.zLevel, (u) * uScale,        (v + height) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y + height + off, this.zLevel, (u + width) * uScale,    (v + height) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y - off, this.zLevel, (u + width) * uScale,    (v) * vScale);
-        tessellator.addVertexWithUV(x - off,        y - off, this.zLevel, (u) * uScale,        (v) * vScale);
+        tessellator.addVertexWithUV(x - off, y + height + off, this.zLevel, (u) * uScale, (v + height) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y + height + off, this.zLevel, (u + width) * uScale, (v + height) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y - off, this.zLevel, (u + width) * uScale, (v) * vScale);
+        tessellator.addVertexWithUV(x - off, y - off, this.zLevel, (u) * uScale, (v) * vScale);
         tessellator.draw();
     }
 
-    public void drawTexturedModalRectDouble(final double x, final double y, final double u, final double v, final double width, final double height, final double uScale, final double vScale, final double off)
-    {
+    public void drawTexturedModalRectDouble(final double x, final double y, final double u, final double v, final double width, final double height, final double uScale, final double vScale, final double off) {
         final double foon = /*(0.25d * uScale)*/0;
         final double goon = /*(0.25d * vScale)*/0;
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(x - off,        y + height + off, this.zLevel, (u + 0.5) * uScale,       (v + height) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y + height + off, this.zLevel, (u + width - 0.5) * uScale,   (v + height) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y - off, this.zLevel, (u + width - 0.5) * uScale,    v * vScale);
-        tessellator.addVertexWithUV(x - off,        y - off, this.zLevel, (u + 0.5) * uScale,        v * vScale);
+        tessellator.addVertexWithUV(x - off, y + height + off, this.zLevel, (u + 0.5) * uScale, (v + height) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y + height + off, this.zLevel, (u + width - 0.5) * uScale, (v + height) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y - off, this.zLevel, (u + width - 0.5) * uScale, v * vScale);
+        tessellator.addVertexWithUV(x - off, y - off, this.zLevel, (u + 0.5) * uScale, v * vScale);
         tessellator.draw();
     }
 
 
-    public void drawTexturedModalRectDouble(final double x, final double y, final double u, final double v, final double width, final double height, final double uWidth, final double vHeight, final double uScale, final double vScale)
-    {
+    public void drawTexturedModalRectDouble(final double x, final double y, final double u, final double v, final double width, final double height, final double uWidth, final double vHeight, final double uScale, final double vScale) {
         final double foon = (0.5f * uScale);
         final double goon = 0.0625f * (16.0f / uWidth);
         final double off = 0.05d;
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(x - off,        y + height + off, this.zLevel, (u + foon) * uScale,             (v + vHeight - foon) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y + height + off, this.zLevel, (u + uWidth - foon) * uScale,    (v + vHeight - foon) * vScale);
-        tessellator.addVertexWithUV(x + width + off,y - off, this.zLevel, (u + uWidth - foon) * uScale,    (v + foon) * vScale);
-        tessellator.addVertexWithUV(x - off,        y - off, this.zLevel, (u + foon) * uScale,             (v + foon) * vScale);
+        tessellator.addVertexWithUV(x - off, y + height + off, this.zLevel, (u + foon) * uScale, (v + vHeight - foon) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y + height + off, this.zLevel, (u + uWidth - foon) * uScale, (v + vHeight - foon) * vScale);
+        tessellator.addVertexWithUV(x + width + off, y - off, this.zLevel, (u + uWidth - foon) * uScale, (v + foon) * vScale);
+        tessellator.addVertexWithUV(x - off, y - off, this.zLevel, (u + foon) * uScale, (v + foon) * vScale);
         tessellator.draw();
     }
 
-    public void drawTexturedModalRect(final double x, final double y, final int u, final int v, final int width, final int height, final int uvWidth, final int uvHeight)
-    {
+    public void drawTexturedModalRect(final double x, final double y, final int u, final int v, final int width, final int height, final int uvWidth, final int uvHeight) {
         final float uScale = 0.00390625F;
         final float vScale = 0.00390625F;
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertexWithUV(x + 0, y + height, this.zLevel, (u) * uScale, (v + uvHeight) * vScale);
         tessellator.addVertexWithUV(x + width, y + height, this.zLevel, (u + uvWidth) * uScale, (v + uvHeight) * vScale);
@@ -322,12 +287,11 @@ public class Gui
         tessellator.addVertexWithUV(x + 0, y + 0, this.zLevel, (u) * uScale, (v) * vScale);
         tessellator.draw();
     }
-    
-    public void drawTexturedModalRect(final int x, final int y, final int u, final int v, final int width, final int height, final int uvWidth, final float scale)
-    {
+
+    public void drawTexturedModalRect(final int x, final int y, final int u, final int v, final int width, final int height, final int uvWidth, final float scale) {
         final float uScale = scale;
         final float vScale = scale;
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertexWithUV(x, y + height, this.zLevel, (u) * uScale, (v + uvWidth) * vScale);
         tessellator.addVertexWithUV(x + width, y + height, this.zLevel, (u + uvWidth) * uScale, (v + uvWidth) * vScale);
@@ -335,13 +299,13 @@ public class Gui
         tessellator.addVertexWithUV(x, y, this.zLevel, (u) * uScale, (v) * vScale);
         tessellator.draw();
     }
-    public void drawTexturedIcon(final int x, final int y, final int width, final int height, final IconCoordinate coordinate)
-    {
+
+    public void drawTexturedIcon(final int x, final int y, final int width, final int height, final IconCoordinate coordinate) {
         coordinate.parentAtlas.bind();
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(x,      y + height, this.zLevel, coordinate.getIconUMin(), coordinate.getIconVMax());
-        tessellator.addVertexWithUV(x + width,  y + height, this.zLevel, coordinate.getIconUMax(), coordinate.getIconVMax());
+        tessellator.addVertexWithUV(x, y + height, this.zLevel, coordinate.getIconUMin(), coordinate.getIconVMax());
+        tessellator.addVertexWithUV(x + width, y + height, this.zLevel, coordinate.getIconUMax(), coordinate.getIconVMax());
         tessellator.addVertexWithUV(x + width, y, this.zLevel, coordinate.getIconUMax(), coordinate.getIconVMin());
         tessellator.addVertexWithUV(x, y, this.zLevel, coordinate.getIconUMin(), coordinate.getIconVMin());
         tessellator.draw();
@@ -351,7 +315,7 @@ public class Gui
         final Texture tex = re.loadTexture(texture);
         tex.bind();
 
-        final Tessellator t = Tessellator.instance;
+        final TessellatorGeneral t = GLRenderer.getTessellator();
         if (tex.hasMeta("gui")) {
             final GuiTextureProperties properties = Objects.requireNonNull(tex.getMeta("gui", GuiTextureProperties.class));
             switch (properties.type) {
@@ -365,13 +329,13 @@ public class Gui
                     break;
                 }
                 case GuiTextureProperties.TYPE_TILE: {
-                    final double uScale = 1d/ properties.width;
-                    final double vScale = 1d/ properties.height;
+                    final double uScale = 1d / properties.width;
+                    final double vScale = 1d / properties.height;
                     t.startDrawingQuads();
-                    t.addVertexWithUV(x        , y + height, this.zLevel, 0,              height * vScale);
+                    t.addVertexWithUV(x, y + height, this.zLevel, 0, height * vScale);
                     t.addVertexWithUV(x + width, y + height, this.zLevel, width * uScale, height * vScale);
-                    t.addVertexWithUV(x + width, y         , this.zLevel, width * uScale, 0);
-                    t.addVertexWithUV(x        , y         , this.zLevel, 0,              0);
+                    t.addVertexWithUV(x + width, y, this.zLevel, width * uScale, 0);
+                    t.addVertexWithUV(x, y, this.zLevel, 0, 0);
                     t.draw();
                     break;
                 }
@@ -515,10 +479,10 @@ public class Gui
             }
         } else {
             t.startDrawingQuads();
-            t.addVertexWithUV(x        , y + height, this.zLevel, 0, 1);
+            t.addVertexWithUV(x, y + height, this.zLevel, 0, 1);
             t.addVertexWithUV(x + width, y + height, this.zLevel, 1, 1);
-            t.addVertexWithUV(x + width, y         , this.zLevel, 1, 0);
-            t.addVertexWithUV(x        , y         , this.zLevel, 0, 0);
+            t.addVertexWithUV(x + width, y, this.zLevel, 1, 0);
+            t.addVertexWithUV(x, y, this.zLevel, 0, 0);
             t.draw();
         }
     }
@@ -526,19 +490,18 @@ public class Gui
     public void drawGuiIcon(final int x, final int y, final int width, final int height, final @NotNull IconCoordinate coordinate) {
         drawGuiIconDouble(x, y, width, height, coordinate);
     }
-    public void drawGuiIconDouble(final double x, final double y, final double width, final double height, final @NotNull IconCoordinate coordinate) {
-        coordinate.parentAtlas.bind();
-        final Tessellator t = Tessellator.instance;
+
+    public void addGuiIconDouble(@NotNull TessellatorGeneral t, final double x, final double y, final double width, final double height, final @NotNull IconCoordinate coordinate) {
+        final double epW = 0.25 * coordinate.parentAtlas.getInverseWidth();
+        final double epH = 0.25 * coordinate.parentAtlas.getInverseHeight();
         if (coordinate.hasMeta("gui")) {
             final GuiTextureProperties properties = Objects.requireNonNull(coordinate.getMeta("gui", GuiTextureProperties.class));
             switch (properties.type) {
                 case GuiTextureProperties.TYPE_STRETCH: {
-                    t.startDrawingQuads();
-                    t.addVertexWithUV(x,            y + height, this.zLevel, coordinate.getIconUMin(), coordinate.getIconVMax());
-                    t.addVertexWithUV(x + width,    y + height, this.zLevel, coordinate.getIconUMax(), coordinate.getIconVMax());
-                    t.addVertexWithUV(x + width,    y, this.zLevel, coordinate.getIconUMax(), coordinate.getIconVMin());
-                    t.addVertexWithUV(x,            y, this.zLevel, coordinate.getIconUMin(), coordinate.getIconVMin());
-                    t.draw();
+                    t.addVertexWithUV(x, y + height, this.zLevel, coordinate.getIconUMin() + epW, coordinate.getIconVMax() - epH);
+                    t.addVertexWithUV(x + width, y + height, this.zLevel, coordinate.getIconUMax() - epW, coordinate.getIconVMax() - epH);
+                    t.addVertexWithUV(x + width, y, this.zLevel, coordinate.getIconUMax() - epW, coordinate.getIconVMin() + epH);
+                    t.addVertexWithUV(x, y, this.zLevel, coordinate.getIconUMin() + epW, coordinate.getIconVMin() + epH);
                     break;
                 }
                 case GuiTextureProperties.TYPE_TILE: {
@@ -553,37 +516,37 @@ public class Gui
 
                     for (int i = 0; i < repeatsX; i++) {
                         for (int j = 0; j < repeatsY; j++) {
-                            drawIconTextureDouble(
+                            addIconTextureDouble(t,
                                 x + properties.width * i, y + properties.height * j,
                                 x + properties.width * (i + 1), y + properties.height * (j + 1),
-                                0, 0,
+                                epW, epH,
                                 properties.width * uScale, properties.height * vScale,
                                 coordinate);
                         }
                     }
 
                     for (int j = 0; j < repeatsY; j++) {
-                        drawIconTextureDouble(
+                        addIconTextureDouble(t,
                             x + properties.width * repeatsX, y + properties.height * j,
                             x + properties.width * repeatsX + remainderX, y + properties.height * (j + 1),
-                            0, 0,
+                            epW, epH,
                             remainderX * uScale, properties.height * vScale,
                             coordinate);
                     }
 
                     for (int i = 0; i < repeatsX; i++) {
-                        drawIconTextureDouble(
+                        addIconTextureDouble(t,
                             x + properties.width * i, y + properties.height * repeatsY,
                             x + properties.width * (i + 1), y + properties.height * repeatsY + remainderY,
-                            0, 0,
+                            epW, epH,
                             properties.width * uScale, remainderY * vScale,
                             coordinate);
                     }
 
-                    drawIconTextureDouble(
+                    addIconTextureDouble(t,
                         x + properties.width * repeatsX, y + properties.height * repeatsY,
                         x + properties.width * repeatsX + remainderX, y + properties.height * repeatsY + remainderY,
-                        0, 0,
+                        epW, epH,
                         remainderX * uScale, remainderY * vScale,
                         coordinate);
 
@@ -611,7 +574,7 @@ public class Gui
 
                     { // Inner
                         if (properties.stretchInner) { // Stretch Inner // TODO implement
-                            drawIconTextureDouble(
+                            addIconTextureDouble(t,
                                 x + innerLeft, y + innerTop,
                                 x + innerLeft + width - properties.border.right - properties.border.left, y + innerTop + height - properties.border.bottom - properties.border.top,
                                 innerLeft * uScale, innerTop * vScale,
@@ -619,7 +582,7 @@ public class Gui
                                 coordinate);
                         } else {
                             for (int j = 0; j < repeatsY; j++) {
-                                drawIconTextureDouble(
+                                addIconTextureDouble(t,
                                     x + innerLeft + repeatsX * innerWidth, y + innerTop + j * innerHeight,
                                     x + innerLeft + repeatsX * innerWidth + remainderX, y + innerTop + j * innerHeight + innerHeight,
                                     innerLeft * uScale, innerTop * vScale,
@@ -628,13 +591,13 @@ public class Gui
                             }
 
                             for (int i = 0; i < repeatsX; i++) {
-                                drawIconTextureDouble(
+                                addIconTextureDouble(t,
                                     x + innerLeft + i * innerWidth, y + innerTop + repeatsY * innerHeight,
                                     x + innerLeft + i * innerWidth + innerWidth, y + innerTop + repeatsY * innerHeight + remainderY,
                                     innerLeft * uScale, innerTop * vScale,
                                     (innerLeft + innerWidth) * uScale, (innerTop + remainderY) * vScale, coordinate);
                             }
-                            drawIconTextureDouble(
+                            addIconTextureDouble(t,
                                 x + innerLeft + repeatsX * innerWidth, y + innerTop + repeatsY * innerHeight,
                                 x + innerLeft + repeatsX * innerWidth + remainderX, y + innerTop + repeatsY * innerHeight + remainderY,
                                 innerLeft * uScale, innerTop * vScale,
@@ -644,7 +607,7 @@ public class Gui
                                 for (int j = 0; j < repeatsY; j++) {
                                     final double xMin = (x + innerLeft) + i * innerWidth;
                                     final double yMin = (y + innerTop) + j * innerHeight;
-                                    drawIconTextureDouble(
+                                    addIconTextureDouble(t,
                                         xMin, yMin,
                                         xMin + innerWidth, yMin + innerHeight,
                                         innerLeft * uScale, innerTop * vScale,
@@ -657,44 +620,44 @@ public class Gui
 
                     { // Left Right
                         for (int i = 0; i < repeatsY; i++) {
-                            drawIconTextureDouble(
+                            addIconTextureDouble(t,
                                 x, y + innerTop + i * innerHeight,
                                 x + innerLeft, y + innerTop + i * innerHeight + innerHeight,
-                                0, innerTop * vScale,
+                                epW, innerTop * vScale,
                                 innerLeft * uScale, (innerTop + innerHeight) * vScale,
                                 coordinate);
 
-                            drawIconTextureDouble(
+                            addIconTextureDouble(t,
                                 x + width - properties.border.right, y + innerTop + i * innerHeight,
                                 x + width, y + innerTop + i * innerHeight + innerHeight,
-                                innerRight * uScale, innerTop * vScale,
+                                innerRight * uScale - epW, innerTop * vScale,
                                 (innerRight + properties.border.right) * uScale, (innerTop + innerHeight) * vScale,
                                 coordinate);
                         }
 
-                        drawIconTextureDouble(
+                        addIconTextureDouble(t,
                             x, y + innerTop + repeatsY * innerHeight,
                             x + innerLeft, y + innerTop + repeatsY * innerHeight + remainderY,
-                            0, innerTop * vScale,
+                            epW, innerTop * vScale,
                             innerLeft * uScale, (innerTop + remainderY) * vScale,
                             coordinate);
 
-                        drawIconTextureDouble(
+                        addIconTextureDouble(t,
                             x + width - properties.border.right, y + innerTop + repeatsY * innerHeight,
                             x + width, y + innerTop + repeatsY * innerHeight + remainderY,
-                            innerRight * uScale, innerTop * vScale,
+                            innerRight * uScale - epW, innerTop * vScale,
                             (innerRight + properties.border.right) * uScale, (innerTop + remainderY) * vScale,
                             coordinate);
                     }
                     { // Top Bottom
                         for (int i = 0; i < repeatsX; i++) {
-                            drawIconTextureDouble(x + innerLeft + i * innerWidth, y,
+                            addIconTextureDouble(t, x + innerLeft + i * innerWidth, y,
                                 x + innerLeft + i * innerWidth + innerWidth, y + properties.border.top,
-                                innerLeft * uScale, 0,
+                                innerLeft * uScale, epH,
                                 (innerLeft + innerWidth) * uScale, properties.border.top * vScale,
                                 coordinate);
 
-                            drawIconTextureDouble(
+                            addIconTextureDouble(t,
                                 x + innerLeft + i * innerWidth, y + height - properties.border.bottom,
                                 x + innerLeft + i * innerWidth + innerWidth, y + height,
                                 innerLeft * uScale, innerBottom * vScale,
@@ -702,14 +665,14 @@ public class Gui
                                 coordinate);
                         }
 
-                        drawIconTextureDouble(
+                        addIconTextureDouble(t,
                             x + innerLeft + repeatsX * innerWidth, y,
                             x + innerLeft + repeatsX * innerWidth + remainderX, y + properties.border.top,
-                            innerLeft * uScale, 0,
+                            innerLeft * uScale, epH,
                             (innerLeft + remainderX) * uScale, properties.border.top * vScale,
                             coordinate);
 
-                        drawIconTextureDouble(
+                        addIconTextureDouble(t,
                             x + innerLeft + repeatsX * innerWidth, y + height - properties.border.bottom,
                             x + innerLeft + repeatsX * innerWidth + remainderX, y + height,
                             innerLeft * uScale, innerBottom * vScale,
@@ -717,23 +680,23 @@ public class Gui
                             coordinate);
                     }
 
-                    drawIconTextureDouble(
+                    addIconTextureDouble(t,
                         x, y,
                         x + properties.border.left, y + properties.border.top,
-                        0, 0,
+                        epW, epH,
                         properties.border.left * uScale, properties.border.top * vScale, coordinate);
-                    drawIconTextureDouble(
+                    addIconTextureDouble(t,
                         x, y + height - properties.border.bottom,
                         x + properties.border.left, y + height,
-                        0, innerBottom * vScale,
+                        epW, innerBottom * vScale,
                         properties.border.left * uScale, (innerBottom + properties.border.bottom) * vScale, coordinate);
 
-                    drawIconTextureDouble(
+                    addIconTextureDouble(t,
                         x + width - properties.border.right, y,
                         x + width, y + properties.border.top,
-                        innerRight * uScale, 0,
+                        innerRight * uScale, epH,
                         (innerRight + properties.border.right) * uScale, properties.border.top * uScale, coordinate);
-                    drawIconTextureDouble(
+                    addIconTextureDouble(t,
                         x + width - properties.border.right, y + height - properties.border.bottom,
                         x + width, y + height,
                         innerRight * uScale, innerBottom * vScale,
@@ -744,47 +707,56 @@ public class Gui
                 }
             }
         } else {
-            drawIconTextureDouble(x, y, x + width, y + height, 0, 0, coordinate.width, coordinate.height, coordinate);
+            addIconTextureDouble(t, x, y, x + width, y + height, epW, epH, coordinate.width - epW, coordinate.height - epH, coordinate);
         }
     }
 
-    public void drawIconTexture(final int x0, final int y0, final int x1, final int y1, final int u0, final int v0, final int u1, final int v1, final IconCoordinate coordinate) {
+    public void drawGuiIconDouble(final double x, final double y, final double width, final double height, final @NotNull IconCoordinate coordinate) {
         coordinate.parentAtlas.bind();
+        final TessellatorGeneral t = GLRenderer.getTessellator();
+        t.startDrawingQuads();
+        addGuiIconDouble(t, x, y, width, height, coordinate);
+        t.draw();
+    }
 
-        final double realU0 = coordinate.getSubIconU(u0 /((double)coordinate.width));
-        final double realU1 = coordinate.getSubIconU(u1 /((double)coordinate.width));
-        final double realV0 = coordinate.getSubIconV(v0 /((double)coordinate.height));
-        final double realV1 = coordinate.getSubIconV(v1 /((double)coordinate.height));
-
-//        System.out.printf("%s, %s, %s, %s\n", realU0, realU1, realV0, realV1);
+    public void addIconTexture(@NotNull TessellatorGeneral t, final int x0, final int y0, final int x1, final int y1, final int u0, final int v0, final int u1, final int v1, final @NotNull IconCoordinate coordinate) {
+        final double realU0 = coordinate.getSubIconU(u0 / ((double) coordinate.width));
+        final double realU1 = coordinate.getSubIconU(u1 / ((double) coordinate.width));
+        final double realV0 = coordinate.getSubIconV(v0 / ((double) coordinate.height));
+        final double realV1 = coordinate.getSubIconV(v1 / ((double) coordinate.height));
 
-        final Tessellator t = Tessellator.instance;
-        t.startDrawingQuads();
         t.addVertexWithUV(x0, y1, this.zLevel, realU0, realV1);
         t.addVertexWithUV(x1, y1, this.zLevel, realU1, realV1);
         t.addVertexWithUV(x1, y0, this.zLevel, realU1, realV0);
         t.addVertexWithUV(x0, y0, this.zLevel, realU0, realV0);
-        t.draw();
     }
 
-    public void drawIconTextureDouble(final double x0, final double y0, final double x1, final double y1, final double u0, final double v0, final double u1, final double v1, final IconCoordinate coordinate) {
+    public void drawIconTexture(final int x0, final int y0, final int x1, final int y1, final int u0, final int v0, final int u1, final int v1, final @NotNull IconCoordinate coordinate) {
         coordinate.parentAtlas.bind();
+        final TessellatorGeneral t = GLRenderer.getTessellator();
+        t.startDrawingQuads();
+        addIconTexture(t, x0, y0, x1, y1, u0, v0, u1, v1, coordinate);
+        t.draw();
+    }
 
-        final double realU0 = coordinate.getSubIconU(u0 /((double)coordinate.width));
-        final double realU1 = coordinate.getSubIconU(u1 /((double)coordinate.width));
-        final double realV0 = coordinate.getSubIconV(v0 /((double)coordinate.height));
-        final double realV1 = coordinate.getSubIconV(v1 /((double)coordinate.height));
-
-//        System.out.printf("%s, %s, %s, %s\n", realU0, realU1, realV0, realV1);
+    public void addIconTextureDouble(@NotNull TessellatorGeneral t, final double x0, final double y0, final double x1, final double y1, final double u0, final double v0, final double u1, final double v1, final @NotNull IconCoordinate coordinate) {
+        final double realU0 = coordinate.getSubIconU(u0 / ((double) coordinate.width));
+        final double realU1 = coordinate.getSubIconU(u1 / ((double) coordinate.width));
+        final double realV0 = coordinate.getSubIconV(v0 / ((double) coordinate.height));
+        final double realV1 = coordinate.getSubIconV(v1 / ((double) coordinate.height));
 
-        final Tessellator t = Tessellator.instance;
-        t.startDrawingQuads();
         t.addVertexWithUV(x0, y1, this.zLevel, realU0, realV1);
         t.addVertexWithUV(x1, y1, this.zLevel, realU1, realV1);
         t.addVertexWithUV(x1, y0, this.zLevel, realU1, realV0);
         t.addVertexWithUV(x0, y0, this.zLevel, realU0, realV0);
+    }
+
+    public void drawIconTextureDouble(final double x0, final double y0, final double x1, final double y1, final double u0, final double v0, final double u1, final double v1, final @NotNull IconCoordinate coordinate) {
+        coordinate.parentAtlas.bind();
+        final TessellatorGeneral t = GLRenderer.getTessellator();
+        t.startDrawingQuads();
+        addIconTextureDouble(t, x0, y0, x1, y1, u0, v0, u1, v1, coordinate);
         t.draw();
     }
 
-    public float zLevel;
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/HeldItemTooltipElement.java b/game/client/src/main/java/net/minecraft/client/gui/HeldItemTooltipElement.java
index 7bd5e1000..92f4bf44c 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/HeldItemTooltipElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/HeldItemTooltipElement.java
@@ -1,17 +1,17 @@
 package net.minecraft.client.gui;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.option.Option;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.client.util.helper.Colors;
 import net.minecraft.core.util.helper.Time;
 
 public class HeldItemTooltipElement extends Gui {
 
-	private Minecraft mc;
+	private final Minecraft mc;
 	
 	private int lastItemID;
 	private int lastSelectedItem;
@@ -36,13 +36,13 @@ public class HeldItemTooltipElement extends Gui {
 			int id = getItemID(item);
 			int i = mc.thePlayer.inventory.getCurrentItemIndex();
 			
-			if(id != lastItemID || i != lastSelectedItem) {
+			if(id != this.lastItemID || i != this.lastSelectedItem) {
 				updateString(item);
-				
-				time = displayTime;
-				
-				lastItemID = id;
-				lastSelectedItem = i;
+
+                this.time = this.displayTime;
+
+                this.lastItemID = id;
+                this.lastSelectedItem = i;
 			}
 		}
 		
@@ -55,13 +55,13 @@ public class HeldItemTooltipElement extends Gui {
 			int id = getItemID(item);
 			int i = mc.thePlayer.inventory.getCurrentItemIndex();
 
-			if(id != lastItemID || i != lastSelectedItem) {
+			if(id != this.lastItemID || i != this.lastSelectedItem) {
 				updateString(item);
 
-				time = displayTime;
+                this.time = this.displayTime;
 
-				lastItemID = id;
-				lastSelectedItem = i;
+                this.lastItemID = id;
+                this.lastSelectedItem = i;
 			}
 		}
 
@@ -70,7 +70,7 @@ public class HeldItemTooltipElement extends Gui {
 	
 	private void updateString(ItemStack item) {
 		if(item == null) {
-			string = null;
+            this.string = null;
 			return;
 		}
 		
@@ -79,7 +79,7 @@ public class HeldItemTooltipElement extends Gui {
 	}
 	
 	public void setOptionNameAndValueString(Option<?> option) {
-		setString(option.getDisplayStringName() + ": " + mc.gameSettings.getDisplayString(option));
+		setString(option.getDisplayStringName() + ": " + this.mc.gameSettings.getDisplayString(option));
 	}
 	
 	public void setString(String string) {
@@ -90,28 +90,28 @@ public class HeldItemTooltipElement extends Gui {
 		this.string = string;
 		this.color = color;
 		
-		this.time = displayTime;
+		this.time = this.displayTime;
 	}
 	
 	public void render(Minecraft mc, int width, int height, int screenPadding) {
 		render(mc, width/2, height - 50 - screenPadding);
 	}
 	public void render(Minecraft mc, int x, int y){
-		if(string == null) return;
-		if(time < 0.0) {
+		if(this.string == null) return;
+		if(this.time < 0.0) {
 			return;
 		}
 
 		double alpha;
 
-		if (time < fadeTime) {
-			alpha = time / fadeTime;
+		if (this.time < this.fadeTime) {
+			alpha = this.time / this.fadeTime;
 		} else {
 			alpha = 1.0;
 		}
 
 		if(!mc.isGamePaused) {
-			time -= Time.delta;
+            this.time -= Time.delta;
 		}
 
 		int a = (int) (alpha * 255);
@@ -119,18 +119,18 @@ public class HeldItemTooltipElement extends Gui {
 			return;
 		}
 
-		int rgb = (color & 0x00FFFFFF) | (a << 24);
+		int rgb = (this.color & 0x00FFFFFF) | (a << 24);
 
 		if(a < 255) {
-			glEnable(GL_BLEND);
-			glDisable(GL_ALPHA_TEST);
-			glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+			GLRenderer.enableState(State.BLEND);
+			GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+//			glDisable(GL_ALPHA_TEST);
 		}
 
-		mc.font.renderCentered(Tessellator.instance, this.string, x, y).setShadow().setColor(rgb).call();
+		mc.font.renderCentered(this.string, x, y).setShadow().setColor(rgb).call();
 
-		glDisable(GL_BLEND);
-		glEnable(GL_ALPHA_TEST);
+		GLRenderer.disableState(State.BLEND);
+//		glEnable(GL_ALPHA_TEST);
 	}
 	
 	private int getItemID(ItemStack stack) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/IntegerSliderElement.java b/game/client/src/main/java/net/minecraft/client/gui/IntegerSliderElement.java
index efeda51d5..db32b7bfc 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/IntegerSliderElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/IntegerSliderElement.java
@@ -1,140 +1,125 @@
 package net.minecraft.client.gui;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.option.OptionToggleable;
 
 public class IntegerSliderElement extends ButtonElement {
 
-	public int sliderValue;
-	public boolean dragging;
-	public boolean renderText = true;
-	private OptionToggleable<?> option;
-
-	public IconCoordinate backgroundTexture;
-
-	public IntegerSliderElement(int id, int xPosition, int yPosition, OptionToggleable<?> option) {
-		this(id, xPosition, yPosition, 150, 20, option);
-	}
-
-	public IntegerSliderElement(int id, int xPosition, int yPosition, int width, int height, OptionToggleable<?> option) {
-		super(id, xPosition, yPosition, width, height, option.getDisplayStringValue());
-		
-		this.dragging = false;
-		this.option = option;
-		this.sliderValue = option.getValueIndex();
-		displayString = option.getDisplayStringValue();
-	}
-
-	@Override
-	protected void setDefaultTextures() {
-		backgroundTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_background");
-		defaultTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider");
-		hoveredTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_highlighted");
-		disabledTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_disabled");
-	}
-
-	private int getSliderWidth()
-	{
-		return 8;
-	}
-
-	@Override
-	public void mouseDragged(Minecraft mc, int mouseX, int mouseY) {
-		if(!visible) {
-			return;
-		}
-		int sliderWidth = getSliderWidth();
-		int maxValue = option.size() - 1;
-		if(dragging) {
-			int segments = maxValue;
-			float percentage = (float) (mouseX - (xPosition + 4) - (width / (2 * segments))) / (float) (width - sliderWidth);
-			if(percentage > 1.0f)
-				percentage = 1.0f;
-			if(percentage < 0.0f)
-				percentage = 0.0f;
-			sliderValue = (int) Math.ceil(segments * percentage);
-			option.setValueWithIndex(sliderValue);
-			displayString = option.getDisplayStringValue();
-		}
-		GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-	}
-
-	@Override
-	public void drawButton(Minecraft mc, int mouseX, int mouseY) {
-		if (!visible) return;
-
-		boolean mouseOver = mouseX >= xPosition && mouseY >= yPosition && mouseX < xPosition + width && mouseY < yPosition + height;
-		int state = getButtonState(mouseOver);
-
-		GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-
-		IconCoordinate tex;
-		switch (state) {
-			case STATE_DISABLED:
-				tex = disabledTexture;
-				break;
-			case STATE_HOVERED:
-				tex = hoveredTexture;
-				break;
-			case STATE_DEFAULT:
-			default:
-				tex = defaultTexture;
-		}
-
-		// Draw background
-		drawGuiIcon(xPosition, yPosition, width, height, backgroundTexture);
-
-		// Draw foreground
-		int sliderWidth = getSliderWidth();
-		int maxValue = option.size() - 1;
-		drawGuiIcon(xPosition + (int) ((sliderValue / (float) maxValue) * (float) (width - sliderWidth)), yPosition, sliderWidth, height, tex);
-
-		mouseDragged(mc, mouseX, mouseY);
-
-		int textColor;
-		switch (state) {
-			case 0:
-				textColor = 0xA0A0A0;
-				break;
-			case 1:
-				textColor = 0xE0E0E0;
-				break;
-			default:
-				textColor = 0xFFFFA0;
-				break;
-		}
-
-		if (this.renderText) {
-			drawStringCenteredShadow(mc.font, displayString, xPosition + width / 2, yPosition + (height - 8) / 2, textColor);
-		}
-	}
-
-	@Override
-	public boolean mouseClicked(Minecraft mc, int mouseX, int mouseY) {
-		if(super.mouseClicked(mc, mouseX, mouseY)) {
-			int segments = option.size() - 1;
-			float percentage = (float) (mouseX - (xPosition + 4) - (width / (2 * segments))) / (float) (width - 8);
-			if(percentage > 1.0f)
-				percentage = 1.0f;
-			if(percentage < 0.0f)
-				percentage = 0.0f;
-			sliderValue = (int) Math.ceil(segments * percentage);
-			option.setValueWithIndex(sliderValue);
-			displayString = option.getDisplayStringValue();
-			dragging = true;
-			return true;
-		} else {
-			return false;
-		}
-	}
-
-	@Override
-	public void mouseReleased(int mouseX, int mouseY) {
-		dragging = false;
-		displayString = option.getDisplayString();
-	}
+    public int sliderValue;
+    public boolean dragging;
+    public boolean renderText = true;
+    private final OptionToggleable<?> option;
+
+    public IconCoordinate backgroundTexture;
+
+    public IntegerSliderElement(int id, int xPosition, int yPosition, OptionToggleable<?> option) {
+        this(id, xPosition, yPosition, 150, 20, option);
+    }
+
+    public IntegerSliderElement(int id, int xPosition, int yPosition, int width, int height, OptionToggleable<?> option) {
+        super(id, xPosition, yPosition, width, height, option.getDisplayStringValue());
+
+        this.dragging = false;
+        this.option = option;
+        this.sliderValue = option.getValueIndex();
+        this.displayString = option.getDisplayStringValue();
+    }
+
+    @Override
+    protected void setDefaultTextures() {
+        this.backgroundTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_background");
+        this.defaultTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider");
+        this.hoveredTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_highlighted");
+        this.disabledTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_disabled");
+    }
+
+    private int getSliderWidth() {
+        return 8;
+    }
+
+    @Override
+    public void mouseDragged(Minecraft mc, int mouseX, int mouseY) {
+        if (!this.visible) {
+            return;
+        }
+        int sliderWidth = getSliderWidth();
+        int maxValue = this.option.size() - 1;
+        if (this.dragging) {
+            int segments = maxValue;
+            float percentage = (float) (mouseX - (this.xPosition + 4) - (this.width / (2 * segments))) / (float) (this.width - sliderWidth);
+            if (percentage > 1.0f)
+                percentage = 1.0f;
+            if (percentage < 0.0f)
+                percentage = 0.0f;
+            this.sliderValue = (int) Math.ceil(segments * percentage);
+            this.option.setValueWithIndex(this.sliderValue);
+            this.displayString = this.option.getDisplayStringValue();
+        }
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+    }
+
+    @Override
+    public void drawButton(Minecraft mc, int mouseX, int mouseY) {
+        if (!this.visible) return;
+
+        boolean mouseOver = mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height;
+        int state = getButtonState(mouseOver);
+
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+
+        IconCoordinate tex = switch (state) {
+            case STATE_DISABLED -> this.disabledTexture;
+            case STATE_HOVERED -> this.hoveredTexture;
+            default -> this.defaultTexture;
+        };
+
+        // Draw background
+        drawGuiIcon(this.xPosition, this.yPosition, this.width, this.height, this.backgroundTexture);
+
+        // Draw foreground
+        int sliderWidth = getSliderWidth();
+        int maxValue = this.option.size() - 1;
+        drawGuiIcon(this.xPosition + (int) ((this.sliderValue / (float) maxValue) * (float) (this.width - sliderWidth)), this.yPosition, sliderWidth, this.height, tex);
+
+        mouseDragged(mc, mouseX, mouseY);
+
+        int textColor = switch (state) {
+            case 0 -> 0xA0A0A0;
+            case 1 -> 0xE0E0E0;
+            default -> 0xFFFFA0;
+        };
+
+        if (this.renderText) {
+            drawStringCenteredShadow(mc.font, this.displayString, this.xPosition + this.width / 2, this.yPosition + (this.height - 8) / 2, textColor);
+        }
+    }
+
+    @Override
+    public boolean mouseClicked(Minecraft mc, int mouseX, int mouseY) {
+        if (super.mouseClicked(mc, mouseX, mouseY)) {
+            int segments = this.option.size() - 1;
+            float percentage = (float) (mouseX - (this.xPosition + 4) - (this.width / (2 * segments))) / (float) (this.width - 8);
+            if (percentage > 1.0f)
+                percentage = 1.0f;
+            if (percentage < 0.0f)
+                percentage = 0.0f;
+            this.sliderValue = (int) Math.ceil(segments * percentage);
+            this.option.setValueWithIndex(this.sliderValue);
+            this.displayString = this.option.getDisplayStringValue();
+            this.dragging = true;
+            return true;
+        } else {
+            return false;
+        }
+    }
+
+    @Override
+    public void mouseReleased(int mouseX, int mouseY) {
+        this.dragging = false;
+        this.displayString = this.option.getDisplayString();
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ItemElement.java b/game/client/src/main/java/net/minecraft/client/gui/ItemElement.java
index 219689e0c..5123037c4 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ItemElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ItemElement.java
@@ -2,19 +2,19 @@ package net.minecraft.client.gui;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.Lighting;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.item.model.ItemModel;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.WeightedRandomBag;
 import net.minecraft.core.WeightedRandomLootObject;
 import net.minecraft.core.data.registry.recipe.entry.RecipeEntryTrommel;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.player.inventory.slot.Slot;
 import net.minecraft.client.gui.guidebook.SlotGuidebook;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 
 public class ItemElement extends Gui {
     Minecraft mc;
@@ -29,8 +29,8 @@ public class ItemElement extends Gui {
 
         // Do setup
         Lighting.enableInventoryLight();
-        GL11.glColor4f(1, 1, 1, 1);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
 
         // Draw slot background
         if (slot != null) {
@@ -38,34 +38,34 @@ public class ItemElement extends Gui {
             if (slot.getItemIcon() != null) {
                 final IconCoordinate iconIndex = TextureRegistry.getTexture(slot.getItemIcon());
                 if (itemStack == null) {
-                    GL11.glDisable(GL11.GL_LIGHTING);
+                    GLRenderer.globalSetLightEnabled(false);
                     this.drawTexturedIcon(x, y, 16, 16, iconIndex);
-                    GL11.glEnable(GL11.GL_LIGHTING);
+                    GLRenderer.globalSetLightEnabled(true);
                     hasDrawnSlotBackground = true;
                 }
             }
 
             if (slot.isLocked()) {
-                GL11.glColor4f(1, 1, 1, 1);
-                GL11.glDisable(GL11.GL_LIGHTING);
+                GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+                GLRenderer.globalSetLightEnabled(false);
                 final IconCoordinate iconCoordinate = TextureRegistry.getTexture("minecraft:gui/slot_locked");
                 this.drawGuiIcon(x - 1, y - 1, 18, 18, iconCoordinate);
-                GL11.glEnable(GL11.GL_LIGHTING);
+                GLRenderer.globalSetLightEnabled(true);
             }
         }
 
         // Draw item
         if (!hasDrawnSlotBackground) {
-            GL11.glEnable(GL11.GL_DEPTH_TEST);
+            GLRenderer.enableState(State.DEPTH_TEST);
             if (itemStack != null) {
                 final ItemModel itemModel = ItemModelDispatcher.getInstance().getDispatch(itemStack.getItem());
-                itemModel.renderGui(Tessellator.instance, null, itemStack, x, y, discovered ? 1.0f : 0.0f, 1.0f, 1f);
-                if (slot instanceof SlotGuidebook) {
-                    if (((SlotGuidebook) slot).recipe instanceof RecipeEntryTrommel && ((SlotGuidebook) slot).item != null && ((SlotGuidebook) slot).isOutput) {
-                        final WeightedRandomBag<WeightedRandomLootObject> loot = ((RecipeEntryTrommel) ((SlotGuidebook) slot).recipe).getOutput();
+                itemModel.renderGui(GLRenderer.getTessellator(), null, itemStack, x, y, discovered ? LightmapHelper.getLightmapCoord(15, 15) : LightmapHelper.getLightmapCoord(0, 0), 1f);
+                if (slot instanceof SlotGuidebook slotGuidebook) {
+                    if (slotGuidebook.recipe instanceof RecipeEntryTrommel recipeEntryTrommel && slotGuidebook.item != null && slotGuidebook.isOutput) {
+                        final WeightedRandomBag<WeightedRandomLootObject> loot = recipeEntryTrommel.getOutput();
                         int index = slot.index;
-                        if (((SlotGuidebook) slot).recipeAmount > 8) {
-                            index = slot.index + (9 * ((SlotGuidebook) slot).recipeIndex);
+                        if (slotGuidebook.recipeAmount > 8) {
+                            index = slot.index + (9 * slotGuidebook.recipeIndex);
                         }
                         final WeightedRandomLootObject lootObject = loot.getEntries().get(index);
                         final String s;
@@ -74,31 +74,30 @@ public class ItemElement extends Gui {
                         } else {
                             s = String.valueOf(lootObject.getFixedYield());
                         }
-                        itemModel.renderItemOverlayIntoGUI(Tessellator.instance, this.mc.font, this.mc.textureManager, itemStack, x, y, discovered ? s : "?", 1.0f);
+                        itemModel.renderItemOverlayIntoGUI(GLRenderer.getTessellator(), this.mc.font, this.mc.textureManager, itemStack, x, y, discovered ? s : "?", 1.0f);
                     } else {
-                        itemModel.renderItemOverlayIntoGUI(Tessellator.instance, this.mc.font, this.mc.textureManager, itemStack, x, y, discovered ? null : "?", 1.0f);
+                        itemModel.renderItemOverlayIntoGUI(GLRenderer.getTessellator(), this.mc.font, this.mc.textureManager, itemStack, x, y, discovered ? null : "?", 1.0f);
                     }
                 } else {
-                    itemModel.renderItemOverlayIntoGUI(Tessellator.instance, this.mc.font, this.mc.textureManager, itemStack, x, y, discovered ? null : "?", 1.0f);
+                    itemModel.renderItemOverlayIntoGUI(GLRenderer.getTessellator(), this.mc.font, this.mc.textureManager, itemStack, x, y, discovered ? null : "?", 1.0f);
                 }
             }
-            GL11.glDisable(GL11.GL_DEPTH_TEST);
+            GLRenderer.disableState(State.DEPTH_TEST);
         }
 
         // Draw selection overlay
         if (isSelected) {
-            GL11.glDisable(GL11.GL_LIGHTING);
-            GL11.glDisable(GL11.GL_DEPTH_TEST);
+            GLRenderer.globalSetLightEnabled(false);
+            GLRenderer.disableState(State.DEPTH_TEST);
             this.drawRect(x, y, x + 16, y + 16, 0x80FFFFFF);
-            GL11.glEnable(GL11.GL_LIGHTING);
-            GL11.glEnable(GL11.GL_DEPTH_TEST);
+            GLRenderer.globalSetLightEnabled(true);
+            GLRenderer.enableState(State.DEPTH_TEST);
         }
 
         // Clean up
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
         Lighting.disable();
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
+        GLRenderer.disableState(State.DEPTH_TEST);
     }
 
     public void render(final ItemStack itemStack, final int x, final int y, final boolean isSelected) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ListLayout.java b/game/client/src/main/java/net/minecraft/client/gui/ListLayout.java
index 78e4bb70c..ff763f08d 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ListLayout.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ListLayout.java
@@ -1,131 +1,104 @@
 package net.minecraft.client.gui;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.util.ArrayList;
 import java.util.List;
 
-public class ListLayout{
-	
-	public final Screen screen;
-	
-	public final List<GuiElement> elements = new ArrayList<>();
-	
-	public double alignX = 0.0;
-	public double alignY = 0.0;
-	
-	public double alignSelfX = 0.0;
-	public double alignSelfY = 0.0;
-	
-	public int offsetX;
-	public int offsetY;
-	
-	public boolean vertical = true;
-	
-	public int margin = 0;
-	
-	public int elementWidth = 200;
-	public int elementHeight = 20;
-	
-	private int listX;
-	private int listY;
-	
-	private int listWidth;
-	private int listHeight;
-	
-	public ListLayout(Screen screen) {
-		this.screen = screen;
-	}
-	
-	public ListLayout addElement(GuiElement element) {
-		this.elements.add(element);
-		return this;
-	}
-	
-	public void updateElementPositions() {
-		int elementCount = elements.size();
-		
-		if(vertical) {
-			listWidth = elementWidth;
-			listHeight = elementHeight * elementCount + (elementCount - 1) * margin;
-		}else {
-			listWidth = elementWidth * elementCount + (elementCount - 1) * margin;
-			listHeight = elementHeight;
-		}
-		
-		listX = mix(0, screen.width, alignX) + offsetX;
-		listY = mix(0, screen.height, alignY) + offsetY;
-		
-		listX += mix(0, -listWidth, alignSelfX);
-		listY += mix(0, -listHeight, alignSelfY);
-		
-		for(int i=0; i < elements.size(); i++) {
-			GuiElement element = elements.get(i);
-			
-			element.setWidth(elementWidth);
-			element.setHeight(elementHeight);
-			
-			if(vertical) {
-				element.setX(listX);
-				element.setY(listY + i * elementHeight + i * margin);
-			}else {
-				element.setX(listX + i * elementWidth + i * margin);
-				element.setY(listY);
-			}
-		}
-	}
-	
-	public static int mix(int a, int b, double c) {
-		return (int) (a * (1.0 - c) + b * c);
-	}
-	
-	public void drawDebug() {
-		glDisable(GL_TEXTURE_2D);
-		glColor3d(0.1, 0.1, 0.1);
-		drawRectangle(listX-1, listY-1, listWidth+2, listHeight+2);
-		glColor3d(0.2, 0.2, 0.2);
-		drawRectangle(listX, listY, listWidth, listHeight);
-		glColor3d(0.4, 0.4, 0.4);
-		for(GuiElement element : elements) {
-			drawRectangle(element.getX(), element.getY(), element.getWidth(), element.getHeight());
-		}
-	}
-	
-	private static void drawRectangle(int x, int y, int w, int h) {
-		glBegin(GL_QUADS);
-		glVertex2d(x, y);
-		glVertex2d(x, y+h);
-		glVertex2d(x+w, y+h);
-		glVertex2d(x+w, y);
-		glEnd();
-	}
-	
-	public ListLayout setAlign(double x, double y) {
-		this.alignX = x;
-		this.alignY = y;
-		return this;
-	}
-	
-	public ListLayout setVertical(boolean vertical) {
-		this.vertical = vertical;
-		return this;
-	}
-	
-	public ListLayout setElementSize(int width, int height) {
-		this.elementWidth = width;
-		this.elementHeight = height;
-		return this;
-	}
-	
-	public ListLayout setOffset(int x, int y) {
-		this.offsetX = x;
-		this.offsetY = y;
-		return this;
-	}
-	
-	public ListLayout setMargin(int margin) {
-		this.margin = margin;
-		return this;
-	}
-	
+public class ListLayout {
+
+    public final Screen screen;
+
+    public final List<GuiElement> elements = new ArrayList<>();
+
+    public double alignX = 0.0;
+    public double alignY = 0.0;
+
+    public double alignSelfX = 0.0;
+    public double alignSelfY = 0.0;
+
+    public int offsetX;
+    public int offsetY;
+
+    public boolean vertical = true;
+
+    public int margin = 0;
+
+    public int elementWidth = 200;
+    public int elementHeight = 20;
+
+    public ListLayout(Screen screen) {
+        this.screen = screen;
+    }
+
+    public ListLayout addElement(GuiElement element) {
+        this.elements.add(element);
+        return this;
+    }
+
+    public void updateElementPositions() {
+        int elementCount = this.elements.size();
+
+        int listHeight;
+        int listWidth;
+        if (this.vertical) {
+            listWidth = this.elementWidth;
+            listHeight = this.elementHeight * elementCount + (elementCount - 1) * this.margin;
+        } else {
+            listWidth = this.elementWidth * elementCount + (elementCount - 1) * this.margin;
+            listHeight = this.elementHeight;
+        }
+
+        int listX = mix(0, this.screen.width, this.alignX) + this.offsetX;
+        int listY = mix(0, this.screen.height, this.alignY) + this.offsetY;
+
+        listX += mix(0, -listWidth, this.alignSelfX);
+        listY += mix(0, -listHeight, this.alignSelfY);
+
+        for (int i = 0; i < this.elements.size(); i++) {
+            GuiElement element = this.elements.get(i);
+
+            element.setWidth(this.elementWidth);
+            element.setHeight(this.elementHeight);
+
+            if (this.vertical) {
+                element.setX(listX);
+                element.setY(listY + i * this.elementHeight + i * this.margin);
+            } else {
+                element.setX(listX + i * this.elementWidth + i * this.margin);
+                element.setY(listY);
+            }
+        }
+    }
+
+    public static int mix(int a, int b, double c) {
+        return (int) (a * (1.0 - c) + b * c);
+    }
+
+    public ListLayout setAlign(double x, double y) {
+        this.alignX = x;
+        this.alignY = y;
+        return this;
+    }
+
+    public ListLayout setVertical(boolean vertical) {
+        this.vertical = vertical;
+        return this;
+    }
+
+    public ListLayout setElementSize(int width, int height) {
+        this.elementWidth = width;
+        this.elementHeight = height;
+        return this;
+    }
+
+    public ListLayout setOffset(int x, int y) {
+        this.offsetX = x;
+        this.offsetY = y;
+        return this;
+    }
+
+    public ListLayout setMargin(int margin) {
+        this.margin = margin;
+        return this;
+    }
+
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/MainMenuBackground.java b/game/client/src/main/java/net/minecraft/client/gui/MainMenuBackground.java
index 12d80c1fc..5b0894194 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/MainMenuBackground.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/MainMenuBackground.java
@@ -1,7 +1,5 @@
 package net.minecraft.client.gui;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.awt.image.BufferedImage;
 import java.io.InputStream;
 import java.util.ArrayList;
@@ -17,11 +15,15 @@ import com.mojang.logging.LogUtils;
 import net.minecraft.client.GLAllocation;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.OpenGLHelper;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texturepack.TexturePack;
 import net.minecraft.client.render.texturepack.TexturePackException;
 import net.minecraft.client.util.helper.TexturePackJsonHelper;
 import net.minecraft.core.util.helper.Buffer;
+import org.lwjgl.opengl.GL41;
 import org.slf4j.Logger;
 
 public class MainMenuBackground {
@@ -46,22 +48,22 @@ public class MainMenuBackground {
 	private long lastTick = 0;
 	
 	public void draw() {
-		if(backgroundList.isEmpty()) {
+		if(this.backgroundList.isEmpty()) {
 			return;
 		}
 		
-		glClear(GL_COLOR_BUFFER_BIT);
-		glEnable(GL_BLEND);
-		glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+		GL41.glClear(GL41.GL_COLOR_BUFFER_BIT);
+		GLRenderer.enableState(State.BLEND);
+		GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
 		
-		if(backgroundList.size() == 1) {
-			if(currentBackground == null) {
-				currentBackground = loadRandomBackground();
+		if(this.backgroundList.size() == 1) {
+			if(this.currentBackground == null) {
+                this.currentBackground = loadRandomBackground();
 			}
 			
 			OpenGLHelper.checkError("pre draw background");
 			
-			drawImage(currentBackground, 1.0f);
+			drawImage(this.currentBackground, 1.0f);
 			
 			OpenGLHelper.checkError("draw background");
 			
@@ -70,51 +72,57 @@ public class MainMenuBackground {
 		
 		OpenGLHelper.checkError("pre draw background");
 
-		if(currentBackground == null) {
-			currentBackground = loadRandomBackground();
+		if(this.currentBackground == null) {
+            this.currentBackground = loadRandomBackground();
 		}
-		if(nextBackground == null) {
-			nextBackground = loadRandomBackground();
+		if(this.nextBackground == null) {
+            this.nextBackground = loadRandomBackground();
 		}
 		
 		long now = System.currentTimeMillis();
-		float delta = Math.min(((now - lastTick) / 1000.0f), 0.33f);
-		lastTick = now;
-		
-		currentDisplayTime += delta;
+		float delta = Math.min(((now - this.lastTick) / 1000.0f), 0.33f);
+        this.lastTick = now;
+
+        this.currentDisplayTime += delta;
 		
-		if(currentDisplayTime >= displayTime + fadeTime) {
-			currentDisplayTime = 0.0f;
+		if(this.currentDisplayTime >= this.displayTime + this.fadeTime) {
+            this.currentDisplayTime = 0.0f;
 			
-			delete(currentBackground);
-			currentBackground = nextBackground;
-			nextBackground = null;
+			delete(this.currentBackground);
+            this.currentBackground = this.nextBackground;
+            this.nextBackground = null;
 		}
 		
-		drawImage(currentBackground, 1.0f);
+		drawImage(this.currentBackground, 1.0f);
 		
-		float nextBackgroundAlpha = (currentDisplayTime - displayTime) / fadeTime;
+		float nextBackgroundAlpha = (this.currentDisplayTime - this.displayTime) / this.fadeTime;
 		if(nextBackgroundAlpha > 0.0f) {
-			drawImage(nextBackground, nextBackgroundAlpha);	
+			drawImage(this.nextBackground, nextBackgroundAlpha);
 		}
 		
 		OpenGLHelper.checkError("draw background");
 	}
 	
 	private Background loadRandomBackground() {
-		BackgroundListEntry randomBackground = backgroundList.get(random.nextInt(backgroundList.size()));
+		BackgroundListEntry randomBackground = this.backgroundList.get(this.random.nextInt(this.backgroundList.size()));
 
 		BufferedImage image = randomBackground.loadBackgroundImage();
 		
 		Buffer.put(image);
 		
 		int texture = GLAllocation.generateTexture();
-		glBindTexture(GL_TEXTURE_2D, texture);
-		glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, image.getWidth(), image.getHeight(), 0, GL_RGBA, GL_UNSIGNED_BYTE, Buffer.buffer);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
+		OpenGLHelper.checkError("setup background5");
+		GL41.glBindTexture(GL41.GL_TEXTURE_2D, texture);
+		OpenGLHelper.checkError("setup background4");
+		GL41.glTexImage2D(GL41.GL_TEXTURE_2D, 0, GL41.GL_RGBA, image.getWidth(), image.getHeight(), 0, GL41.GL_RGBA, GL41.GL_UNSIGNED_BYTE, Buffer.buffer);
+		OpenGLHelper.checkError("setup background3");
+		GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MIN_FILTER, GL41.GL_LINEAR);
+		OpenGLHelper.checkError("setup background3");
+		GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MAG_FILTER, GL41.GL_LINEAR);
+		OpenGLHelper.checkError("setup background2");
+		GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_S, GL41.GL_CLAMP_TO_EDGE);
+		OpenGLHelper.checkError("setup background1");
+		GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_T, GL41.GL_CLAMP_TO_EDGE);
 
 		OpenGLHelper.checkError("setup background");
 		
@@ -123,14 +131,13 @@ public class MainMenuBackground {
 	}
 	
 	private void drawImage(Background background, float alpha) {
-		glEnable(GL_TEXTURE_2D);
-		glBindTexture(GL_TEXTURE_2D, background.texture);
-		glColor4d(0.6, 0.6, 0.6, alpha);
+		GL41.glBindTexture(GL41.GL_TEXTURE_2D, background.texture);
+		GLRenderer.setColor4f(0.6f, 0.6f, 0.6f, alpha);
 
 		int border = 1;
 
-		int displayWidth = mc.resolution.getScaledWidthScreenCoords();
-		int displayHeight = mc.resolution.getScaledHeightScreenCoords();
+		int displayWidth = this.mc.resolution.getScaledWidthScreenCoords();
+		int displayHeight = this.mc.resolution.getScaledHeightScreenCoords();
 		
 		int imageWidth = background.width - 2 * border;
 		int imageHeight = background.height - 2 * border;
@@ -160,9 +167,9 @@ public class MainMenuBackground {
 		float uborder = border / (float) background.width;
 		float vborder = border / (float) background.height;
 		
-		Tessellator tessellator = Tessellator.instance;
+		TessellatorGeneral tessellator = GLRenderer.getTessellator();
 		tessellator.startDrawingQuads();
-		tessellator.setColorRGBA_F(0.75f, 0.75f, 0.75f, alpha);
+		tessellator.setColor4f(0.75f, 0.75f, 0.75f, alpha);
 		tessellator.drawRectangleWithUV(x, y, w, h, uborder, vborder, 1.0 - uborder * 2.0f, 1.0 - vborder * 2.0f);
 		tessellator.draw();
 	}
@@ -171,13 +178,13 @@ public class MainMenuBackground {
 	 * Dont keep textures in memory when loading a world
 	 */
 	public void deleteTextures() {
-		if(currentBackground != null) {
-			delete(currentBackground);
-			currentBackground = null;
+		if(this.currentBackground != null) {
+			delete(this.currentBackground);
+            this.currentBackground = null;
 		}
-		if(nextBackground != null) {
-			delete(nextBackground);
-			nextBackground = null;
+		if(this.nextBackground != null) {
+			delete(this.nextBackground);
+            this.nextBackground = null;
 		}
 	}
 	
@@ -186,16 +193,16 @@ public class MainMenuBackground {
 	}
 	
 	public boolean isEnabled() {
-		return !backgroundList.isEmpty();
+		return !this.backgroundList.isEmpty();
 	}
 	
 	public void refresh(List<Throwable> errors) {
 		deleteTextures();
+
+        this.backgroundList.clear();
 		
-		backgroundList.clear();
-		
-		TexturePack defaultTexturePack = mc.texturePackList.getDefaultTexturePack();
-		TexturePack currentTexturePack = mc.texturePackList.getHighestPriorityPack();
+		TexturePack defaultTexturePack = this.mc.texturePackList.getDefaultTexturePack();
+		TexturePack currentTexturePack = this.mc.texturePackList.getHighestPriorityPack();
 		
 		loadBackgrounds(defaultTexturePack, errors);
 		
@@ -209,7 +216,7 @@ public class MainMenuBackground {
 			JsonObject rootObject = TexturePackJsonHelper.readJsonObject(texturePack, "/bg/backgrounds.json");
 
 			if(rootObject.has("replace") && rootObject.getBoolean("replace")) {
-				backgroundList.clear();
+                this.backgroundList.clear();
 			}
 			
 			JsonArray backgrounds = TexturePackJsonHelper.getArray(rootObject, "backgrounds");
@@ -221,28 +228,28 @@ public class MainMenuBackground {
                         LOGGER.warn("Skipping background '{}'", name);
 						continue;
 					}
-					
-					backgroundList.add(new BackgroundListEntry(texturePack, name));
+
+                    this.backgroundList.add(new BackgroundListEntry(texturePack, name));
 				}
 			}catch (Exception e) {
 				throw new TexturePackException("Error in background.json", e);
 			}
 		}catch (Exception e) {
 			errors.add(e);
-			backgroundList.clear();
+            this.backgroundList.clear();
 		}
 	}
 	
 	public void print() {
 		LOGGER.info("Backgrounds: ");
-		for(BackgroundListEntry bg : backgroundList) {
+		for(BackgroundListEntry bg : this.backgroundList) {
             LOGGER.info("    {}", bg);
 		}
 	}
 	
 	public void nextImage() {
-		if(currentDisplayTime < displayTime) {
-			currentDisplayTime = displayTime;
+		if(this.currentDisplayTime < this.displayTime) {
+            this.currentDisplayTime = this.displayTime;
 		}
 	}
 	
@@ -270,7 +277,7 @@ public class MainMenuBackground {
 		}
 		
 		public BufferedImage loadBackgroundImage() {
-            try (InputStream stream = mc.texturePackList.getResourceAsStream("/bg/" + name + ".png")) {
+            try (InputStream stream = MainMenuBackground.this.mc.texturePackList.getResourceAsStream("/bg/" + this.name + ".png")) {
                 return ImageIO.read(stream);
             } catch (Exception e) {
                 throw new RuntimeException(e);
@@ -278,7 +285,7 @@ public class MainMenuBackground {
 		}
 		
 		public String toString() {
-			return texturePack.manifest.getName() + "/" + name;
+			return this.texturePack.manifest.getName() + "/" + this.name;
 		}
 	}
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/Screen.java b/game/client/src/main/java/net/minecraft/client/gui/Screen.java
index 02e3e754b..32d85eb37 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/Screen.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/Screen.java
@@ -1,14 +1,14 @@
 package net.minecraft.client.gui;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.util.ArrayList;
 import java.util.List;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.window.CursorShape;
 import net.minecraft.client.util.debug.DebugRender;
 import net.minecraft.client.input.InputType;
@@ -18,7 +18,6 @@ import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 public abstract class Screen extends Gui {
     public final @NotNull Minecraft mc = Minecraft.getMinecraft();
@@ -171,14 +170,14 @@ public abstract class Screen extends Gui {
     }
 
     public void renderTexturedBackground() {
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_FOG);
-        final Tessellator tessellator = Tessellator.instance;
+        GLRenderer.globalSetLightEnabled(false);
+//        GL11.glDisable(GL11.GL_FOG);
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
         final float scale = 32F;
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0x404040);
+        tessellator.setColorOpaque1i(0x404040);
         tessellator.addVertexWithUV(0.0D, this.height, 0.0D, 0.0D, (float) this.height / scale);
         tessellator.addVertexWithUV(this.width, this.height, 0.0D, (float) this.width / scale, (float) this.height / scale);
         tessellator.addVertexWithUV(this.width, 0.0D, 0.0D, (float) this.width / scale, 0);
@@ -188,11 +187,11 @@ public abstract class Screen extends Gui {
 
     public void drawControllerCursor() {
         if (this.mc.controllerInput == null || this.mc.controllerInput.hideCursor) return;
-        glDisable(GL_DEPTH_TEST);
-        glEnable(GL_BLEND);
-        glColor3d(1.0, 1.0, 1.0);
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setColor3f(1f, 1f, 1f);
         this.drawGuiTexture(this.mc.textureManager, (int) (this.mc.controllerInput.cursorX - 8), (int) (this.mc.controllerInput.cursorY - 8), 16, 16, "/assets/minecraft/textures/gui/controller/cursor.png");
-        glDisable(GL_BLEND);
+        GLRenderer.disableState(State.BLEND);
     }
 
     public void controllerInput(final @NotNull ControllerInput controller) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenConsole.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenConsole.java
index 50f7557bd..f9f4fc7cb 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenConsole.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenConsole.java
@@ -7,12 +7,8 @@ import net.minecraft.client.console.LogMessageReceiver;
 import net.minecraft.client.console.syntax.RendererFactory;
 import net.minecraft.client.gui.text.ITextField;
 import net.minecraft.client.gui.text.TextFieldEditor;
-import net.minecraft.client.render.font.FontMonospace;
 import net.minecraft.client.console.shell.RuntimeExecutor;
-import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.font.FontRendererDefault;
 import net.minecraft.client.render.font.Fonts;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.client.render.window.CursorShape;
 import net.minecraft.core.net.command.TextFormatting;
 import net.minecraft.core.util.helper.MathHelper;
@@ -38,8 +34,6 @@ public class ScreenConsole extends Screen {
 
         private final @NotNull Map<LogMessage.@NotNull Level, @NotNull TextFormatting> preludes = new HashMap<>();
 
-        private final @NotNull FontRenderer fontRenderer = new FontRendererDefault(Fonts.MONOSPACE);
-
         private int width = 0;
         private int scroll = 0;
 
@@ -74,7 +68,7 @@ public class ScreenConsole extends Screen {
             final int lines = Math.min(heightLines, WORKED_LINES.size() - this.scroll);
             for (int i = lines - 1; i >= 0; i--) {
                 final @NotNull String line = WORKED_LINES.get((WORKED_LINES.size() - 1) - (i + this.scroll));
-                this.fontRenderer.render(Tessellator.instance, line, x, y + getHeight(numLines) - LINE_HEIGHT - LINE_HEIGHT * i).setColor(0xFF_CF_CF_CF).call();
+                Minecraft.getMinecraft().font.render(line, x, y + getHeight(numLines) - LINE_HEIGHT - LINE_HEIGHT * i).setFont(Fonts.MONOSPACE).setColor(0xFF_CF_CF_CF).call();
             }
             renderScrollIndicator(x, y, numLines);
         }
@@ -136,7 +130,7 @@ public class ScreenConsole extends Screen {
 
         private void formatString(final @NotNull LogMessage message, final @NotNull List<@NotNull String> out) {
             out.clear();
-            final @NotNull String @NotNull[] workedString = message.getMessage()
+            final @NotNull String @NotNull [] workedString = message.getMessage()
                 .replace("\r\n", "\n")
                 .replace("\t", "    ")
                 .split("\n");
@@ -156,9 +150,9 @@ public class ScreenConsole extends Screen {
                         if (newFormat != null) {
                             nextFormat = newFormat;
                         }
-                        lineWidth -= this.fontRenderer.getFont().charWidth(c) + this.fontRenderer.getFont().charWidth(trimmedLine.charAt(i + 1));
+                        lineWidth -= Fonts.MONOSPACE.charWidth(c) + Fonts.MONOSPACE.charWidth(trimmedLine.charAt(i + 1));
                     }
-                    final int cWidth = this.fontRenderer.getFont().charWidth(c);
+                    final int cWidth = Fonts.MONOSPACE.charWidth(c);
                     if (lineWidth + cWidth >= this.width) {
                         out.add(currentFormat.toString() + sb);
                         sb = new StringBuilder();
@@ -177,8 +171,6 @@ public class ScreenConsole extends Screen {
         private static final @NotNull List<@NotNull String> HISTORY = new ArrayList<>();
         private static final @Nullable RuntimeExecutor EXECUTOR = new RuntimeExecutor();
 
-        private final @NotNull FontRenderer fontRenderer = new FontRendererDefault(Fonts.MONOSPACE);
-
         private @NotNull String text = "";
         private @NotNull String highlightedText = "";
         private @NotNull String originalText = "";
@@ -198,38 +190,38 @@ public class ScreenConsole extends Screen {
 
         public void render(final int x, final int y) {
             boolean addedStart = false;
-            final @NotNull String @NotNull[] splitHighlighted = this.highlightedText.split("\n", -1);
+            final @NotNull String @NotNull [] splitHighlighted = this.highlightedText.split("\n", -1);
             for (int i = 0; i < splitHighlighted.length; i++) {
-                drawStringNoShadow(this.fontRenderer, (addedStart ? "  " : "> ") + splitHighlighted[i].replace("\n", ""), x, y + i * LINE_HEIGHT, 0xFF_E0_E0_E0);
+                Minecraft.getMinecraft().font.render((addedStart ? "  " : "> ") + splitHighlighted[i].replace("\n", ""), x, y).setFont(Fonts.MONOSPACE).setZ(this.zLevel).setColor(0xFF_E0_E0_E0).call();
                 addedStart = true;
             }
 
             final @NotNull String @NotNull [] split = this.text.split("\n", -1);
-            final int offsetWidth = MathHelper.ceil(this.fontRenderer.stringWidthDouble("  "));
+            final int offsetWidth = MathHelper.ceil(Minecraft.getMinecraft().font.stringWidthDouble("  "));
             final int[] cursorPos = getCursor();
             final int cursorX;
             if (cursorPos[0] == split[cursorPos[1]].length()) {
-                cursorX = MathHelper.ceil(this.fontRenderer.stringWidthDouble(split[cursorPos[1]]));
+                cursorX = MathHelper.ceil(Minecraft.getMinecraft().font.stringWidthDouble(split[cursorPos[1]]));
             } else {
-                cursorX = MathHelper.ceil(this.fontRenderer.stringWidthDouble(split[cursorPos[1]].substring(0, cursorPos[0])));
+                cursorX = MathHelper.ceil(Minecraft.getMinecraft().font.stringWidthDouble(split[cursorPos[1]].substring(0, cursorPos[0])));
             }
-            if ((cursorCounter / 6) % 2 == 0) {
-                drawStringNoShadow(this.fontRenderer, "█", x + offsetWidth + cursorX, y + cursorPos[1] * LINE_HEIGHT, 0xFF_FF_FF_FF);
+            if ((this.cursorCounter / 6) % 2 == 0) {
+                Minecraft.getMinecraft().font.render("█", x + offsetWidth + cursorX, y + cursorPos[1] * LINE_HEIGHT).setFont(Fonts.MONOSPACE).setZ(this.zLevel).setColor(0xFF_FF_FF_FF).call();
                 if (this.editor.getCursor() < this.text.length() && this.text.charAt(this.editor.getCursor()) != '\n') {
-                    drawStringNoShadow(this.fontRenderer, "" + this.text.charAt(this.editor.getCursor()), x + offsetWidth + cursorX, y + cursorPos[1] * LINE_HEIGHT, 0xFF_00_00_00);
+                    Minecraft.getMinecraft().font.render("" + this.text.charAt(this.editor.getCursor()), x + offsetWidth + cursorX, y + cursorPos[1] * LINE_HEIGHT).setFont(Fonts.MONOSPACE).setZ(this.zLevel).setColor(0xFF_00_00_00).call();
                 }
             } else {
-                drawStringNoShadow(this.fontRenderer, "_", x + offsetWidth + cursorX, y + cursorPos[1] * LINE_HEIGHT, 0xFF_FF_FF_FF);
+                Minecraft.getMinecraft().font.render("_", x + offsetWidth + cursorX, y + cursorPos[1] * LINE_HEIGHT).setFont(Fonts.MONOSPACE).setZ(this.zLevel).setColor(0xFF_FF_FF_FF).call();
             }
         }
 
         public void click(final int mx, final int my) {
-            final int oneChar = MathHelper.ceil(this.fontRenderer.stringWidthDouble(" "));
+            final int oneChar = MathHelper.ceil(Minecraft.getMinecraft().font.stringWidthDouble(" "));
 
             final int cx = (mx - (oneChar * 2)) / oneChar;
             final int cy = my / LINE_HEIGHT;
 
-            final @NotNull String @NotNull[] split = this.text.split("\n");
+            final @NotNull String @NotNull [] split = this.text.split("\n");
             int cursor = 0;
             for (int y = 0; y < cy; y++) {
                 cursor += split[y].length() + 1;
@@ -253,7 +245,7 @@ public class ScreenConsole extends Screen {
                     this.editor.handleInput(key, '\n');
                 } else {
                     final @NotNull String line = this.text.trim();
-                    final @NotNull String @NotNull[] split = this.highlightedText.trim().split("\n");
+                    final @NotNull String @NotNull [] split = this.highlightedText.trim().split("\n");
                     final @NotNull StringBuilder sb = new StringBuilder();
                     for (final @NotNull String s : split) {
                         sb
@@ -280,7 +272,7 @@ public class ScreenConsole extends Screen {
                 realPos -= cursorPos[0];
                 this.editor.setCursor(realPos);
             } else if (key == Keyboard.KEY_END && isMultiLine) {
-                final @NotNull String @NotNull[] split = this.text.split("\n", -1);
+                final @NotNull String @NotNull [] split = this.text.split("\n", -1);
                 final int[] cursorPos = getCursor();
                 int realPos = this.editor.getCursor();
                 realPos -= cursorPos[0];
@@ -288,7 +280,7 @@ public class ScreenConsole extends Screen {
                 this.editor.setCursor(realPos);
             } else if (key == Keyboard.KEY_UP) {
                 if (isMultiLine && !(Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT))) {
-                    final @NotNull String @NotNull[] split = this.text.split("\n", -1);
+                    final @NotNull String @NotNull [] split = this.text.split("\n", -1);
                     int[] cursorPos = getCursor();
                     if (cursorPos[1] == 0) return;
                     int realPos = this.editor.getCursor();
@@ -310,7 +302,7 @@ public class ScreenConsole extends Screen {
                 }
             } else if (key == Keyboard.KEY_DOWN) {
                 if (isMultiLine && !(Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT))) {
-                    final @NotNull String @NotNull[] split = this.text.split("\n", -1);
+                    final @NotNull String @NotNull [] split = this.text.split("\n", -1);
                     int[] cursorPos = getCursor();
                     if (cursorPos[1] == split.length - 1) return;
                     int realPos = this.editor.getCursor();
@@ -361,8 +353,8 @@ public class ScreenConsole extends Screen {
             return 1024;
         }
 
-        private int @NotNull[] getCursor() {
-            final @NotNull String @NotNull[] split = this.text.split("\n", -1);
+        private int @NotNull [] getCursor() {
+            final @NotNull String @NotNull [] split = this.text.split("\n", -1);
 
             int cursor = this.editor.getCursor();
             int cursorLine = 0;
@@ -373,7 +365,7 @@ public class ScreenConsole extends Screen {
                 }
                 cursor -= split[i].length() + 1;
             }
-            return new int[] { cursor, cursorLine };
+            return new int[]{cursor, cursorLine};
         }
     }
 
@@ -409,10 +401,9 @@ public class ScreenConsole extends Screen {
     @Override
     public void init() {
         if (this.parentScreen != null) {
-            if (this.parentScreen.width != width || this.parentScreen.height != height)
-            {
-                this.parentScreen.width = width;
-                this.parentScreen.height = height;
+            if (this.parentScreen.width != this.width || this.parentScreen.height != this.height) {
+                this.parentScreen.width = this.width;
+                this.parentScreen.height = this.height;
                 this.parentScreen.buttons.clear();
                 this.parentScreen.init();
             }
@@ -454,7 +445,7 @@ public class ScreenConsole extends Screen {
         GL11.glDisable(GL11.GL_TEXTURE_2D);
         drawRect(0, 0, this.width, getMaxY(), 0xDF_00_00_00);
 
-        this.logRenderer.render(PADDING, PADDING, heightLines - inputRenderer.getHeightLines());
+        this.logRenderer.render(PADDING, PADDING, heightLines - this.inputRenderer.getHeightLines());
 
         final int inputRendererHeight = this.inputRenderer.getHeightLines() * LINE_HEIGHT;
         this.inputRenderer.render(PADDING, getMaxY() - PADDING - inputRendererHeight);
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenControllerSetup.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenControllerSetup.java
index 80f4c1155..db1d1d5eb 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenControllerSetup.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenControllerSetup.java
@@ -5,13 +5,13 @@ import net.minecraft.client.input.InputType;
 import net.minecraft.client.input.controller.Button;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.input.controller.ControllerType;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.lang.I18n;
 import org.jetbrains.annotations.NotNull;
 
 import java.util.Arrays;
 
-import static org.lwjgl.opengl.GL11.*;
-
 public class ScreenControllerSetup extends Screen {
     private ControllerInput lastController = null;
     private ButtonElement controllerButton;
@@ -22,15 +22,15 @@ public class ScreenControllerSetup extends Screen {
 
     @Override
     public void init() {
-        controllerButton = new ButtonElement(0, 0, 0, "");
-        controllerButton.xPosition = width / 2 - 100;
-        controllerButton.yPosition = 16;
-        controllerButton.width = 200;
-        controllerButton.height = 20;
+        this.controllerButton = new ButtonElement(0, 0, 0, "");
+        this.controllerButton.xPosition = this.width / 2 - 100;
+        this.controllerButton.yPosition = 16;
+        this.controllerButton.width = 200;
+        this.controllerButton.height = 20;
 
-        buttons.add(controllerButton);
+        this.buttons.add(this.controllerButton);
 
-        buttons.add(new ButtonElement(-1, width / 2 - 100, height - 40, I18n.getInstance().translateKey("gui.controller_setup.button.back")).setListener((e) -> mc.displayScreen(parentScreen)));
+        this.buttons.add(new ButtonElement(-1, this.width / 2 - 100, this.height - 40, I18n.getInstance().translateKey("gui.controller_setup.button.back")).setListener((e) -> this.mc.displayScreen(this.parentScreen)));
 
         updateDisplay();
     }
@@ -38,9 +38,9 @@ public class ScreenControllerSetup extends Screen {
     @Override
     public void tick() {
         super.tick();
-        if (mc.controllerInput != lastController) {
+        if (this.mc.controllerInput != this.lastController) {
             updateDisplay();
-            lastController = mc.controllerInput;
+            this.lastController = this.mc.controllerInput;
         }
     }
 
@@ -49,13 +49,13 @@ public class ScreenControllerSetup extends Screen {
         renderBackground();
         super.render(mx, my, partialTick);
 
-        ControllerInput controller = mc.controllerInput;
+        ControllerInput controller = this.mc.controllerInput;
 
         if (controller != null) {
             boolean swapJoystickAndDPad = controller.getType().getLayout() == ControllerType.Layout.XBOX || controller.getType().getLayout() == ControllerType.Layout.NINTENDO;
 
-            final int x = width / 2 - 232 / 2;
-            final int y = height / 2 - 164 / 2;
+            final int x = this.width / 2 - 232 / 2;
+            final int y = this.height / 2 - 164 / 2;
 
             final int[][] slots = {
                 { 23, 36 },
@@ -81,11 +81,11 @@ public class ScreenControllerSetup extends Screen {
             final int joyRightSlot = 2;
             final int faceButtonsSlot = 3;
 
-            glDisable(GL_DEPTH_TEST);
-
-            drawStringCenteredNoShadow(fontRenderer, "(" + controller.getType().getPrintableName() + ")", width / 2, 40, 0xFFFFFF);
+            GLRenderer.pushFrame();
+            GLRenderer.disableState(State.DEPTH_TEST);
+            drawStringCenteredNoShadow(this.fontRenderer, "(" + controller.getType().getPrintableName() + ")", this.width / 2, 40, 0xFFFFFF);
 
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/layout.png").bind();
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/layout.png").bind();
 
             drawTexturedModalRect(x, y, 0, 0, 232, 164);
 
@@ -110,17 +110,17 @@ public class ScreenControllerSetup extends Screen {
 
             //Digital Pad
             drawDPad(controller, x + slots[dPadSlot][0], y + slots[dPadSlot][1], controller.digitalPad.up.isPressed(), controller.digitalPad.right.isPressed(), controller.digitalPad.down.isPressed(), controller.digitalPad.left.isPressed());
-
+            GLRenderer.popFrame();
         }
     }
 
     private void drawButtons(ControllerInput controller, int x, int y) {
         int w = 14;
 
-        drawButton(controller, controller.buttonA, x + w * 1, y + w * 2, controller.buttonA.isPressed());
-        drawButton(controller, controller.buttonB, x + w * 2, y + w * 1, controller.buttonB.isPressed());
-        drawButton(controller, controller.buttonX, x + w * 0, y + w * 1, controller.buttonX.isPressed());
-        drawButton(controller, controller.buttonY, x + w * 1, y + w * 0, controller.buttonY.isPressed());
+        drawButton(controller, controller.buttonA, x + w, y + w * 2, controller.buttonA.isPressed());
+        drawButton(controller, controller.buttonB, x + w * 2, y + w, controller.buttonB.isPressed());
+        drawButton(controller, controller.buttonX, x + 0, y + w, controller.buttonX.isPressed());
+        drawButton(controller, controller.buttonY, x + w, y + 0, controller.buttonY.isPressed());
     }
 
     @Override
@@ -132,10 +132,10 @@ public class ScreenControllerSetup extends Screen {
 
         if (button.id == 0) {
             int index;
-            if (mc.controllerInput == null) {
+            if (this.mc.controllerInput == null) {
                 index = -1;
             } else {
-                index = Arrays.asList(InputHandler.controllers).indexOf(mc.controllerInput);
+                index = Arrays.asList(InputHandler.controllers).indexOf(this.mc.controllerInput);
             }
             do {
                 index++;
@@ -145,11 +145,11 @@ public class ScreenControllerSetup extends Screen {
                 }
             } while (InputHandler.controllers[index] == null);
             if (index == -1) {
-                mc.controllerInput = null;
-                mc.setInputType(InputType.KEYBOARD);
+                this.mc.controllerInput = null;
+                this.mc.setInputType(InputType.KEYBOARD);
             } else {
-                mc.controllerInput = InputHandler.controllers[index];
-                mc.setInputType(InputType.CONTROLLER);
+                this.mc.controllerInput = InputHandler.controllers[index];
+                this.mc.setInputType(InputType.CONTROLLER);
             }
             updateDisplay();
             save();
@@ -158,29 +158,29 @@ public class ScreenControllerSetup extends Screen {
 
     @Override
     public void removed() {
-        if (mc.inputType == InputType.CONTROLLER) {
-            mc.mouseInput.grabCursor();
+        if (this.mc.inputType == InputType.CONTROLLER) {
+            this.mc.mouseInput.grabCursor();
         }
     }
 
     private void updateDisplay() {
-        if (mc.controllerInput != null) {
-            controllerButton.displayString = mc.controllerInput.getController().getName();
-            if (controllerButton.displayString.startsWith("SDL GameController ")) {
-                controllerButton.displayString = controllerButton.displayString.substring(19);
+        if (this.mc.controllerInput != null) {
+            this.controllerButton.displayString = this.mc.controllerInput.getController().getName();
+            if (this.controllerButton.displayString.startsWith("SDL GameController ")) {
+                this.controllerButton.displayString = this.controllerButton.displayString.substring(19);
             }
         } else {
-            controllerButton.displayString = I18n.getInstance().translateKey("gui.controller_setup.label.no_controller_selected");
+            this.controllerButton.displayString = I18n.getInstance().translateKey("gui.controller_setup.label.no_controller_selected");
         }
     }
 
     private void save() {
-        if (mc.controllerInput != null) {
-            mc.gameSettings.selectedController.value = mc.controllerInput.getGUID();
+        if (this.mc.controllerInput != null) {
+            this.mc.gameSettings.selectedController.value = this.mc.controllerInput.getGUID();
         } else {
-            mc.gameSettings.selectedController.value = "";
+            this.mc.gameSettings.selectedController.value = "";
         }
-        mc.gameSettings.saveOptions();
+        this.mc.gameSettings.saveOptions();
     }
 
     private void drawButton(ControllerInput controller, Button button, int x, int y, boolean pressed) {
@@ -193,7 +193,7 @@ public class ScreenControllerSetup extends Screen {
             vOffset = sizeV;
         }
 
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/" + controller.getType().getAssetName() + ".png").bind();
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/" + controller.getType().getAssetName() + ".png").bind();
 
         drawTexturedModalRect(x, y, u, v + vOffset, sizeU, sizeV);
     }
@@ -204,7 +204,7 @@ public class ScreenControllerSetup extends Screen {
         int sizeU = 46;
         int sizeV = 46;
 
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/" + controllerInput.getType().getAssetName() + ".png").bind();
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/" + controllerInput.getType().getAssetName() + ".png").bind();
 
         drawTexturedModalRect(x, y, u, v, sizeU, sizeV);
 
@@ -228,7 +228,7 @@ public class ScreenControllerSetup extends Screen {
         int sizeU = 46;
         int sizeV = 46;
 
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/" + controllerInput.getType().getAssetName() + ".png").bind();
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/controller/" + controllerInput.getType().getAssetName() + ".png").bind();
 
         drawTexturedModalRect(x, y, u, v, sizeU, sizeV);
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenCreateWorld.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenCreateWorld.java
index 4a1196839..317689809 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenCreateWorld.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenCreateWorld.java
@@ -36,29 +36,29 @@ public class ScreenCreateWorld extends Screen {
 
     @Override
     public void tick() {
-        textboxWorldName.updateCursorCounter();
-        textboxSeed.updateCursorCounter();
+        this.textboxWorldName.updateCursorCounter();
+        this.textboxSeed.updateCursorCounter();
     }
 
     @Override
     public void init() {
         I18n i18n = I18n.getInstance();
         Keyboard.enableRepeatEvents(true);
-        buttons.clear();
-        buttons.add(createWorldButton = new ButtonElement(0, width / 2 - 100, height / 4 + 104 + 12,
+        this.buttons.clear();
+        this.buttons.add(this.createWorldButton = new ButtonElement(0, this.width / 2 - 100, this.height / 4 + 104 + 12,
                 i18n.translateKey("gui.create_world.button.create_new_world")));
-        buttons.add(new ButtonElement(1, width / 2 - 100, height / 4 + 128 + 12,
+        this.buttons.add(new ButtonElement(1, this.width / 2 - 100, this.height / 4 + 128 + 12,
                 i18n.translateKey("gui.create_world.button.cancel")));
-        textboxWorldName = new TextFieldElement(this, fontRenderer, width / 2 - 100, 60, 200 - 24, 20,
+        this.textboxWorldName = new TextFieldElement(this, this.fontRenderer, this.width / 2 - 100, 60, 200 - 24, 20,
                 "", i18n.translateKey("gui.create_world.label.new_world"));
-        textboxWorldName.setMaxStringLength(32);
-        textboxSeed = new TextFieldElement(this, fontRenderer, width / 2 - 100, 100, 200 - 24, 20, "", Long.toString(this.worldConfiguration.getNumericSeed()));
-        buttons.add(gamemodeButton = new ButtonElement(2, width / 2 - 100, 100 + 20 + 4, 98, 20, ""));
-        buttons.add(cheatsButton = new ButtonElement(3, width / 2 - 100 + 102, 100 + 20 + 4, 98, 20, ""));
-        buttons.add(worldSettingsButton = new ButtonElement(4, width / 2 - 100, 100 + 20 + 20 + 4 + 4, i18n.translateKey("gui.create_world.button.world_settings")));
-        buttons.add(buttonRandomWorldName = new ButtonElement(5, width / 2 + 100 - 20, 60, 20, 20, "")
+        this.textboxWorldName.setMaxStringLength(32);
+        this.textboxSeed = new TextFieldElement(this, this.fontRenderer, this.width / 2 - 100, 100, 200 - 24, 20, "", Long.toString(this.worldConfiguration.getNumericSeed()));
+        this.buttons.add(this.gamemodeButton = new ButtonElement(2, this.width / 2 - 100, 100 + 20 + 4, 98, 20, ""));
+        this.buttons.add(this.cheatsButton = new ButtonElement(3, this.width / 2 - 100 + 102, 100 + 20 + 4, 98, 20, ""));
+        this.buttons.add(this.worldSettingsButton = new ButtonElement(4, this.width / 2 - 100, 100 + 20 + 20 + 4 + 4, i18n.translateKey("gui.create_world.button.world_settings")));
+        this.buttons.add(this.buttonRandomWorldName = new ButtonElement(5, this.width / 2 + 100 - 20, 60, 20, 20, "")
                 .setTextures("minecraft:gui/misc/button_random", "minecraft:gui/misc/button_random_highlighted", "minecraft:gui/misc/button_random"));
-        buttons.add(buttonRandomSeed = new ButtonElement(6, width / 2 + 100 - 20, 100, 20, 20, "")
+        this.buttons.add(this.buttonRandomSeed = new ButtonElement(6, this.width / 2 + 100 - 20, 100, 20, 20, "")
                 .setTextures("minecraft:gui/misc/button_random", "minecraft:gui/misc/button_random_highlighted", "minecraft:gui/misc/button_random"));
         syncButtons();
     }
@@ -74,34 +74,34 @@ public class ScreenCreateWorld extends Screen {
             return;
         }
         if (button.id == 1) {
-            mc.displayScreen(parentScreen);
+            this.mc.displayScreen(this.parentScreen);
         } else if (button.id == 0) {
-            mc.displayScreen(null);
-            if (createClicked) {
+            this.mc.displayScreen(null);
+            if (this.createClicked) {
                 return;
             }
-            createClicked = true;
+            this.createClicked = true;
 
             this.mc.createAndStartWorld(this.worldConfiguration);
 
-            mc.displayScreen(null);
-        } else if (button == gamemodeButton) {
+            this.mc.displayScreen(null);
+        } else if (button == this.gamemodeButton) {
             List<Gamemode> gamemodeList = Gamemode.getPublicGamemodes();
             this.worldConfiguration.setGamemode(gamemodeList.get((gamemodeList.indexOf(this.worldConfiguration.getGamemode()) + 1) % gamemodeList.size()));
             this.worldConfiguration.setCheatsEnabled(this.worldConfiguration.getGamemode() == Gamemode.creative);
             syncButtons();
-        } else if (button == cheatsButton) {
+        } else if (button == this.cheatsButton) {
             this.worldConfiguration.setCheatsEnabled(!this.worldConfiguration.getCheatsEnabled());
             syncButtons();
-        } else if (button == worldSettingsButton) {
-            mc.displayScreen(new ScreenWorldSettings(this, this.worldConfiguration));
-        } else if (button == buttonRandomWorldName) {
-            textboxWorldName.setText(I18n.getInstance().getCurrentLanguage().getRandomWorldName());
+        } else if (button == this.worldSettingsButton) {
+            this.mc.displayScreen(new ScreenWorldSettings(this, this.worldConfiguration));
+        } else if (button == this.buttonRandomWorldName) {
+            this.textboxWorldName.setText(I18n.getInstance().getCurrentLanguage().getRandomWorldName());
             syncConfig();
-        } else if (button == buttonRandomSeed) {
+        } else if (button == this.buttonRandomSeed) {
             this.worldConfiguration.regenNumericSeed();
-            textboxSeed.setPlaceholder(Long.toString(this.worldConfiguration.getNumericSeed()));
-            textboxSeed.setText("");
+            this.textboxSeed.setPlaceholder(Long.toString(this.worldConfiguration.getNumericSeed()));
+            this.textboxSeed.setText("");
             syncConfig();
         }
     }
@@ -110,8 +110,8 @@ public class ScreenCreateWorld extends Screen {
         I18n i18n = I18n.getInstance();
         this.textboxWorldName.setText(this.worldConfiguration.getWorldName());
         this.textboxSeed.setText(this.worldConfiguration.getStringSeed());
-        gamemodeButton.displayString = i18n.translateKeyAndFormat("gui.create_world.button.gamemode", i18n.translateKey(this.worldConfiguration.getGamemode().getLanguageKey() + ".name"));
-        cheatsButton.displayString = i18n.translateKeyAndFormat("gui.create_world.button.cheats", i18n.translateKey(this.worldConfiguration.getCheatsEnabled() ? "gui.create_world.button.cheats.on" : "gui.create_world.button.cheats.off"));
+        this.gamemodeButton.displayString = i18n.translateKeyAndFormat("gui.create_world.button.gamemode", i18n.translateKey(this.worldConfiguration.getGamemode().getLanguageKey() + ".name"));
+        this.cheatsButton.displayString = i18n.translateKeyAndFormat("gui.create_world.button.cheats", i18n.translateKey(this.worldConfiguration.getCheatsEnabled() ? "gui.create_world.button.cheats.on" : "gui.create_world.button.cheats.off"));
     }
 
     private void syncConfig() {
@@ -122,57 +122,57 @@ public class ScreenCreateWorld extends Screen {
     @Override
     public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
         if (eventKey != Keyboard.KEY_BACK) super.keyPressed(eventCharacter, eventKey, mx, my);
-        if (textboxWorldName.isFocused) {
-            textboxWorldName.textboxKeyTyped(eventCharacter, eventKey);
+        if (this.textboxWorldName.isFocused) {
+            this.textboxWorldName.textboxKeyTyped(eventCharacter, eventKey);
             syncConfig();
-        } else if (textboxSeed.isFocused) {
-            textboxSeed.textboxKeyTyped(eventCharacter, eventKey);
+        } else if (this.textboxSeed.isFocused) {
+            this.textboxSeed.textboxKeyTyped(eventCharacter, eventKey);
             syncConfig();
         }
         if (eventCharacter == '\r') {
-            buttonClicked(buttons.get(0));
+            buttonClicked(this.buttons.get(0));
         }
     }
 
     @Override
     public void mouseClicked(int mx, int my, int buttonNum) {
         super.mouseClicked(mx, my, buttonNum);
-        textboxWorldName.mouseClicked(mx, my, buttonNum);
-        textboxSeed.mouseClicked(mx, my, buttonNum);
+        this.textboxWorldName.mouseClicked(mx, my, buttonNum);
+        this.textboxSeed.mouseClicked(mx, my, buttonNum);
     }
 
     @Override
     public void render(int mx, int my, float partialTick) {
         I18n i18n = I18n.getInstance();
         renderBackground();
-        drawStringCenteredShadow(fontRenderer, i18n.translateKey("gui.create_world.label.title"), width / 2, 20, 0xffffff);
-        drawStringShadow(fontRenderer, i18n.translateKey("gui.create_world.label.world_name"), width / 2 - 100, 47, 0xa0a0a0);
-        drawStringShadow(fontRenderer, i18n.translateKey("gui.create_world.label.seed"), width / 2 - 100, 88, 0xa0a0a0);
-        textboxWorldName.drawTextBox();
-        textboxWorldName.updateCursor(mc, mx, my);
-        textboxSeed.drawTextBox();
-        textboxSeed.updateCursor(mc, mx, my);
+        drawStringCenteredShadow(this.fontRenderer, i18n.translateKey("gui.create_world.label.title"), this.width / 2, 20, 0xffffff);
+        drawStringShadow(this.fontRenderer, i18n.translateKey("gui.create_world.label.world_name"), this.width / 2 - 100, 47, 0xa0a0a0);
+        drawStringShadow(this.fontRenderer, i18n.translateKey("gui.create_world.label.seed"), this.width / 2 - 100, 88, 0xa0a0a0);
+        this.textboxWorldName.drawTextBox();
+        this.textboxWorldName.updateCursor(this.mc, mx, my);
+        this.textboxSeed.drawTextBox();
+        this.textboxSeed.updateCursor(this.mc, mx, my);
         super.render(mx, my, partialTick);
     }
 
     @Override
     public void selectNextField() {
-        if (textboxWorldName.isFocused) {
-            textboxWorldName.setFocused(false);
-            textboxSeed.setFocused(true);
+        if (this.textboxWorldName.isFocused) {
+            this.textboxWorldName.setFocused(false);
+            this.textboxSeed.setFocused(true);
         } else {
-            textboxWorldName.setFocused(true);
-            textboxSeed.setFocused(false);
+            this.textboxWorldName.setFocused(true);
+            this.textboxSeed.setFocused(false);
         }
     }
 
     public void runPreset(String name, String seed, int spawnX, int spawnY, int spawnZ) {
-        overrideSpawnX = spawnX;
-        overrideSpawnY = spawnY;
-        overrideSpawnZ = spawnZ;
+        this.overrideSpawnX = spawnX;
+        this.overrideSpawnY = spawnY;
+        this.overrideSpawnZ = spawnZ;
         this.worldConfiguration.setWorldName(name);
         this.worldConfiguration.setStringSeed(seed);
         this.worldConfiguration.setGamemode(Gamemode.creative);
-        buttonClicked(createWorldButton);
+        buttonClicked(this.createWorldButton);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenCredits.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenCredits.java
index 650fe998f..93a125867 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenCredits.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenCredits.java
@@ -3,13 +3,14 @@ package net.minecraft.client.gui;
 import com.mojang.logging.LogUtils;
 import net.minecraft.client.gui.modelviewer.elements.ListenerButtonElement;
 import net.minecraft.client.render.Scissor;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.net.command.TextFormatting;
 import net.minecraft.core.util.helper.MathHelper;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 import org.slf4j.Logger;
 
 import java.awt.*;
@@ -20,8 +21,6 @@ import java.nio.charset.StandardCharsets;
 import java.util.ArrayList;
 import java.util.List;
 
-import static org.lwjgl.opengl.GL11.*;
-
 public class ScreenCredits extends Screen {
     private static final Logger LOGGER = LogUtils.getLogger();
     private static final int TOP_SPACING = 24;
@@ -80,12 +79,12 @@ public class ScreenCredits extends Screen {
 
     @Override
     public void init() {
-        top = TOP_SPACING;
-        bottom = height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
-        scrollRegionHeight = bottom - top;
-        add(new ListenerButtonElement(0, width / 2 - 100, height - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.credits.button.done")).setActionListener(() -> {
+        this.top = TOP_SPACING;
+        this.bottom = this.height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
+        this.scrollRegionHeight = this.bottom - this.top;
+        add(new ListenerButtonElement(0, this.width / 2 - 100, this.height - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.credits.button.done")).setActionListener(() -> {
             removed();
-            mc.displayScreen(null);
+            this.mc.displayScreen(this.parentScreen);
         }));
 
         onScroll();
@@ -93,15 +92,15 @@ public class ScreenCredits extends Screen {
 
     @Override
     public void tick() {
-        if (!playing) {
-            mc.sndManager.playMusic(SONGS[(int) (Math.random() * SONGS.length)], 0, 0, 0, 1.0f, 1.0f);
-            playing = true;
+        if (!this.playing) {
+            this.mc.sndManager.playMusic(SONGS[(int) (Math.random() * SONGS.length)], 0, 0, 0, 1.0f, 1.0f);
+            this.playing = true;
         }
     }
 
     @Override
     public void removed() {
-        mc.sndManager.stopMusic();
+        this.mc.sndManager.stopMusic();
     }
 
     @Override
@@ -114,86 +113,84 @@ public class ScreenCredits extends Screen {
         }
 
         renderBackground();
-        overlayBackground(0, width, 0, top);
-        overlayBackground(0, width, bottom, height);
+        overlayBackground(0, this.width, 0, this.top);
+        overlayBackground(0, this.width, this.bottom, this.height);
 
         drawScrollBar(mx, my);
 
         super.render(mx, my, partialTick);
 
-        drawStringCenteredNoShadow(fontRenderer, I18n.getInstance().translateKey("gui.credits.label.title"), width / 2, 5, 0xFFFFFF);
+        drawStringCenteredNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.credits.label.title"), this.width / 2, 5, 0xFFFFFF);
 
-        Scissor.enable(0, top, width, bottom - top);
+        Scissor.enable(0, this.top, this.width, this.bottom - this.top);
         drawContent();
         Scissor.disable();
 
-        hue = (hue + 1) % 360f;
+        this.hue = (this.hue + 1) % 360f;
     }
 
     private void drawContent() {
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/title/mclogo.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        drawTexturedModalRect(width / 2 - 274 / 2, 30 - (int)scrollAmount, 0, 0, 274, 50, 1d/274, 1d/50);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/title/mclogo.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        drawTexturedModalRect(this.width / 2 - 274 / 2, 30 - (int) this.scrollAmount, 0, 0, 274, 50, 1d / 274, 1d / 50);
 
-        for (int i = 0; i < lines.size(); i++) {
-            String line = lines.get(i);
+        for (int i = 0; i < this.lines.size(); i++) {
+            String line = this.lines.get(i);
             if (line.startsWith("*")) {
                 line = TextFormatting.BOLD + line.substring(1);
-                int lineWidth = MathHelper.ceil(fontRenderer.stringWidthDouble(line)) + line.length();
-                drawStringNoShadow(this.fontRenderer, line, width / 2 - lineWidth / 2, 100 + i * 12 - (int)scrollAmount, 0xFFFFFF);
+                int lineWidth = MathHelper.ceil(this.fontRenderer.stringWidthDouble(line)) + line.length();
+                drawStringNoShadow(this.fontRenderer, line, this.width / 2 - lineWidth / 2, 100 + i * 12 - (int) this.scrollAmount, 0xFFFFFF);
             } else if (line.startsWith("!")) {
-                int rgb = Color.HSBtoRGB(hue / 360f, 1.0f, 1.0f);
+                int rgb = Color.HSBtoRGB(this.hue / 360f, 1.0f, 1.0f);
                 line = TextFormatting.BOLD + line.substring(1);
-                int lineWidth = MathHelper.ceil(fontRenderer.stringWidthDouble(line)) + line.length();
-                drawStringNoShadow(this.fontRenderer, line, width / 2 - lineWidth / 2, 100 + i * 12 - (int)scrollAmount, rgb);
+                int lineWidth = MathHelper.ceil(this.fontRenderer.stringWidthDouble(line)) + line.length();
+                drawStringNoShadow(this.fontRenderer, line, this.width / 2 - lineWidth / 2, 100 + i * 12 - (int) this.scrollAmount, rgb);
             } else {
-                drawStringNoShadow(this.fontRenderer, line, MathHelper.ceil((width - fontRenderer.stringWidthDouble(line)) / 2), 100 + i * 12 - (int) scrollAmount, 0x7F7F7F);
+                drawStringNoShadow(this.fontRenderer, line, MathHelper.ceil((this.width - this.fontRenderer.stringWidthDouble(line)) / 2), 100 + i * 12 - (int) this.scrollAmount, 0x7F7F7F);
             }
         }
     }
 
     protected void drawScrollBar(int mouseX, int mouseY) {
         float totalPageHeight = getTotalPageHeight();
-        float scrollBarHeightPercent = scrollRegionHeight / totalPageHeight;
+        float scrollBarHeightPercent = this.scrollRegionHeight / totalPageHeight;
 
         if (scrollBarHeightPercent > 1.0f) return;
 
-        glDisable(GL_TEXTURE_2D);
-
-        int scrollBarX = width - 6;
+        int scrollBarX = this.width - 6;
 
-        int scrollBarHeightPx = (int) (scrollBarHeightPercent * scrollRegionHeight);
+        int scrollBarHeightPx = (int) (scrollBarHeightPercent * this.scrollRegionHeight);
         if (scrollBarHeightPx < 32) {
             scrollBarHeightPx = 32;
         }
 
-        float scrollPercent = scrollAmount / (totalPageHeight - scrollRegionHeight);
+        float scrollPercent = this.scrollAmount / (totalPageHeight - this.scrollRegionHeight);
 
-        int scrollBarY = (int) (top + (scrollRegionHeight - scrollBarHeightPx) * scrollPercent);
-
-        Tessellator t = Tessellator.instance;
+        int scrollBarY = (int) (this.top + (this.scrollRegionHeight - scrollBarHeightPx) * scrollPercent);
 
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        TessellatorGeneral t = GLRenderer.getTessellator();
         t.startDrawingQuads();
-        t.setColorOpaque(0, 0, 0);
-        t.drawRectangle(scrollBarX, top, 6, scrollRegionHeight);
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColorOpaque3i(0, 0, 0);
+        t.drawRectangle(scrollBarX, this.top, 6, this.scrollRegionHeight);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(scrollBarX, scrollBarY, 6, scrollBarHeightPx);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(scrollBarX + 1, scrollBarY, 5, scrollBarHeightPx - 1);
         t.draw();
+        GLRenderer.popFrame();
 
-        glEnable(GL_TEXTURE_2D);
-
-        if (clickX != null && clickY != null) {
-            if (clickX >= scrollBarX && clickY >= top && clickX <= scrollBarX + 6 && clickY < bottom) {
-                if (oldScrollAmount == null) {
-                    oldScrollAmount = scrollAmount;
+        if (this.clickX != null && this.clickY != null) {
+            if (this.clickX >= scrollBarX && this.clickY >= this.top && this.clickX <= scrollBarX + 6 && this.clickY < this.bottom) {
+                if (this.oldScrollAmount == null) {
+                    this.oldScrollAmount = this.scrollAmount;
                 }
-                scrollAmount = oldScrollAmount + (clickY - mouseY) * (1.0f / scrollBarHeightPercent) * -1.0f;
+                this.scrollAmount = this.oldScrollAmount + (this.clickY - mouseY) * (1.0f / scrollBarHeightPercent) * -1.0f;
                 onScroll();
             }
         } else {
-            oldScrollAmount = null;
+            this.oldScrollAmount = null;
         }
     }
 
@@ -201,40 +198,40 @@ public class ScreenCredits extends Screen {
     public void mouseClicked(int mx, int my, int buttonNum) {
         super.mouseClicked(mx, my, buttonNum);
 
-        clickX = mx;
-        clickY = my;
+        this.clickX = mx;
+        this.clickY = my;
     }
 
     @Override
     public void renderBackground() {
         super.renderBackground();
 
-        Tessellator tessellator = Tessellator.instance;
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         float scale = 32F;
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0x202020);
+        tessellator.setColorOpaque1i(0x202020);
 
-        tessellator.addVertexWithUV(0, bottom, 0.0D, 0, (float) (bottom + (int) scrollAmount) / scale);
-        tessellator.addVertexWithUV(width, bottom, 0.0D, (float) width / scale, (float) (bottom + (int) scrollAmount) / scale);
-        tessellator.addVertexWithUV(width, top, 0.0D, (float) width / scale, (float) (top + (int) scrollAmount) / scale);
-        tessellator.addVertexWithUV(0, top, 0.0D, 0, (float) (top + (int) scrollAmount) / scale);
+        tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0, (float) (this.bottom + (int) this.scrollAmount) / scale);
+        tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, (float) this.width / scale, (float) (this.bottom + (int) this.scrollAmount) / scale);
+        tessellator.addVertexWithUV(this.width, this.top, 0.0D, (float) this.width / scale, (float) (this.top + (int) this.scrollAmount) / scale);
+        tessellator.addVertexWithUV(0, this.top, 0.0D, 0, (float) (this.top + (int) this.scrollAmount) / scale);
 
         tessellator.draw();
     }
 
     private void overlayBackground(int minX, int maxX, int minY, int maxY) {
-        if (mc.currentWorld == null) {
-            Tessellator tessellator = Tessellator.instance;
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        if (this.mc.currentWorld == null) {
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
             float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x404040);
+            tessellator.setColorOpaque1i(0x404040);
             tessellator.addVertexWithUV(minX, maxY, 0.0D, (float) minX / scale, (float) maxY / scale);
             tessellator.addVertexWithUV(maxX, maxY, 0.0D, (float) maxX / scale, (float) maxY / scale);
-            tessellator.setColorOpaque_I(0x404040);
+            tessellator.setColorOpaque1i(0x404040);
             tessellator.addVertexWithUV(maxX, minY, 0.0D, (float) maxX / scale, (float) minY / scale);
             tessellator.addVertexWithUV(minX, minY, 0.0D, (float) minX / scale, (float) minY / scale);
             tessellator.draw();
@@ -245,19 +242,19 @@ public class ScreenCredits extends Screen {
     private void scroll(float amount) {
         if (amount == 0.0f) return;
 
-        scrollAmount += amount;
+        this.scrollAmount += amount;
         onScroll();
     }
 
     private void onScroll() {
         int totalPageHeight = getTotalPageHeight();
-        if (scrollAmount < 0 || scrollRegionHeight > totalPageHeight) scrollAmount = 0;
-        else if (scrollAmount > totalPageHeight - scrollRegionHeight)
-            scrollAmount = totalPageHeight - scrollRegionHeight;
+        if (this.scrollAmount < 0 || this.scrollRegionHeight > totalPageHeight) this.scrollAmount = 0;
+        else if (this.scrollAmount > totalPageHeight - this.scrollRegionHeight)
+            this.scrollAmount = totalPageHeight - this.scrollRegionHeight;
     }
 
     private int getTotalPageHeight() {
-        return 100 + lines.size() * 12;
+        return 100 + this.lines.size() * 12;
     }
 
     @Override
@@ -265,8 +262,8 @@ public class ScreenCredits extends Screen {
         super.mouseReleased(mx, my, buttonNum);
 
         if (buttonNum >= 0) {
-            clickX = null;
-            clickY = null;
+            this.clickX = null;
+            this.clickY = null;
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenFontTest.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenFontTest.java
index 42302ef96..143ee02e9 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenFontTest.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenFontTest.java
@@ -2,7 +2,6 @@ package net.minecraft.client.gui;
 
 import net.minecraft.client.render.font.Alignment;
 import net.minecraft.client.render.font.Fonts;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.net.ChatEmotes;
 import net.minecraft.core.util.collection.NamespaceID;
 import net.minecraft.core.util.helper.ChatAllowedCharacters;
@@ -27,7 +26,7 @@ public class ScreenFontTest extends Screen{
 
         this.scroll += Mouse.getDWheel() * this.fontRenderer.getFont().fontHeight();
 
-        final int maxWidth = (int) (width/1.2);
+        final int maxWidth = (int) (this.width /1.2);
 
         drawRect((this.width - maxWidth)/2, 0, (this.width + maxWidth)/2, this.height, 0xFF232323);
         final long start = System.currentTimeMillis();
@@ -53,36 +52,36 @@ public class ScreenFontTest extends Screen{
         }
 
         builder.append("\n§bLorem ipsum dolor sit amet, §+§3consectetur adipiscing elit, sed do eiusmod tempor incididunt §+§1ut labore et §+§rdolore magna aliqua.§- Ut enim §-ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut §-aliquip ex ea commodo consequat. Duis aute irure dolor in §+§rreprehenderit in voluptate velit esse cillum dolore §-eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum. \nTest String1!");
-        this.fontRenderer.renderWidthConstrained(Tessellator.instance, builder, (this.width - maxWidth)/2, (int) (10 + this.scroll), maxWidth).setAlignment(Alignment.LEFT).setColor(0xFFAAFF).setShadow().call();
+        this.fontRenderer.renderWidthConstrained(builder, (this.width - maxWidth)/2, (int) (10 + this.scroll), maxWidth).setAlignment(Alignment.LEFT).setColor(0xFFAAFF).setShadow().call();
         final long bigStringRenderTime = System.currentTimeMillis() - start;
-        this.fontRenderer.render(Tessellator.instance, bigStringRenderTime/1000f + "s", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY() + 20).call();
+        this.fontRenderer.render(bigStringRenderTime/1000f + "s", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY() + 20).call();
 
         final long memTotal = Runtime.getRuntime().totalMemory();
         final long memFree = Runtime.getRuntime().freeMemory();
         final long memUsed = memTotal - memFree;
 
-        this.fontRenderer.render(Tessellator.instance, memUsed/(1024 * 1024) + "MB", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY()).call();
+        this.fontRenderer.render(memUsed/(1024 * 1024) + "MB", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY()).call();
 
-        this.fontRenderer.render(Tessellator.instance, "Unicode: Better than Adventure", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY()).setFont(Fonts.UNICODE).call();
-        this.fontRenderer.render(Tessellator.instance, "Default: Better than Adventure", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY()).setFont(Fonts.DEFAULT).call();
-        this.fontRenderer.render(Tessellator.instance, "Monospace: Better than Adventure", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY()).setFont(Fonts.MONOSPACE).call();
+        this.fontRenderer.render("Unicode: Better than Adventure", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY()).setFont(Fonts.UNICODE).call();
+        this.fontRenderer.render("Default: Better than Adventure", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY()).setFont(Fonts.DEFAULT).call();
+        this.fontRenderer.render("Monospace: Better than Adventure", (this.width - maxWidth)/2, this.fontRenderer.getLastEndingY()).setFont(Fonts.MONOSPACE).call();
 
         int y = this.fontRenderer.getLastEndingY() + 10;
-        this.fontRenderer.render(Tessellator.instance, "String: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, "Test String", this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "null (Object): ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, (Object) null, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "object: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, testId, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "boolean: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, true, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "int: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, 15, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "long: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, 1500L, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "char: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, 'a', this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "float: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, 0.5f, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "double: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, 0.5, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
-        this.fontRenderer.render(Tessellator.instance, "char array: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(Tessellator.instance, chars, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("String: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render("Test String", this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("null (Object): ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render((Object) null, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("object: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(testId, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("boolean: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(true, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("int: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(15, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("long: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(1500L, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("char: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render('a', this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("float: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(0.5f, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("double: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(0.5, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
+        this.fontRenderer.render("char array: ", (this.width - maxWidth)/2, y).setColor(0xFFAAFF).call(); this.fontRenderer.render(chars, this.fontRenderer.getLastEndingX(), y).call(); y = this.fontRenderer.getLastEndingY();
 
         final double mouseX = (double) (Mouse.getX() * this.mc.resolution.getScaledWidthScreenCoords()) / this.mc.resolution.getWidthScreenCoords();
         final double mouseY =  (this.mc.resolution.getScaledHeightScreenCoords() - (double) (Mouse.getY() * this.mc.resolution.getScaledHeightScreenCoords()) / this.mc.resolution.getHeightScreenCoords());
 
-        this.fontRenderer.renderDouble(Tessellator.instance, "Double Precision", mouseX - this.fontRenderer.stringWidthDouble("Double Precision") - 3, mouseY - 6).setShadow().call();
-        this.fontRenderer.render(Tessellator.instance, "Int Precision", (int) (mouseX + 3), (int) (mouseY - 5)).setShadow().call();
+        this.fontRenderer.renderDouble("Double Precision", mouseX - this.fontRenderer.stringWidthDouble("Double Precision") - 3, mouseY - 6).setShadow().call();
+        this.fontRenderer.render("Int Precision", (int) (mouseX + 3), (int) (mouseY - 5)).setShadow().call();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenGameOver.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenGameOver.java
index 0e10fbf8e..7713cee48 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenGameOver.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenGameOver.java
@@ -1,83 +1,73 @@
 package net.minecraft.client.gui;
 
 import net.minecraft.client.entity.player.PlayerLocalMultiplayer;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.net.packet.PacketKeepAlive;
 import net.minecraft.core.player.gamemode.Gamemode;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.core.net.command.TextFormatting;
 
-public class ScreenGameOver extends Screen
-{
+public class ScreenGameOver extends Screen {
     protected int tickCount = 0;
 
-    public ScreenGameOver()
-    {
+    public ScreenGameOver() {
     }
+
     @Override
-    public void tick(){
-        tickCount++;
-        if (mc.isMultiplayerWorld() && mc.thePlayer instanceof PlayerLocalMultiplayer && tickCount % 10 == 0){
-            PlayerLocalMultiplayer clientPlayerMP = (PlayerLocalMultiplayer) mc.thePlayer;
+    public void tick() {
+        this.tickCount++;
+        if (this.mc.isMultiplayerWorld() && this.mc.thePlayer instanceof PlayerLocalMultiplayer clientPlayerMP && this.tickCount % 10 == 0) {
             clientPlayerMP.sendQueue.addToSendQueue(new PacketKeepAlive());
         }
     }
 
     @Override
-	public void init()
-    {
+    public void init() {
         I18n i18n = I18n.getInstance();
-        buttons.clear();
-        String respawnKey = (mc.thePlayer.getGamemode() == Gamemode.hardcore || mc.thePlayer.getGamemode() == Gamemode.spectator) ? "gui.game_over.button.respawn.spectator" : "gui.game_over.button.respawn";
-        buttons.add(new ButtonElement(1, width / 2 - 100, height / 4 + 72, i18n.translateKey(respawnKey)));
-        buttons.add(new ButtonElement(2, width / 2 - 100, height / 4 + 96, i18n.translateKey("gui.game_over.button.title_screen")));
-        if(mc.session == null)
-        {
-            buttons.get(1).enabled = false;
+        this.buttons.clear();
+        String respawnKey = (this.mc.thePlayer.getGamemode() == Gamemode.hardcore || this.mc.thePlayer.getGamemode() == Gamemode.spectator) ? "gui.game_over.button.respawn.spectator" : "gui.game_over.button.respawn";
+        this.buttons.add(new ButtonElement(1, this.width / 2 - 100, this.height / 4 + 72, i18n.translateKey(respawnKey)));
+        this.buttons.add(new ButtonElement(2, this.width / 2 - 100, this.height / 4 + 96, i18n.translateKey("gui.game_over.button.title_screen")));
+        if (this.mc.session == null) {
+            this.buttons.get(1).enabled = false;
         }
     }
 
     @Override
-	public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
-    {
+    public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
     }
 
     @Override
-	protected void buttonClicked(@NotNull ButtonElement button)
-    {
-        if(button.id == 1)
-        {
-            mc.thePlayer.respawnPlayer();
-            mc.displayScreen(null);
+    protected void buttonClicked(@NotNull ButtonElement button) {
+        if (button.id == 1) {
+            this.mc.thePlayer.respawnPlayer();
+            this.mc.displayScreen(null);
         }
-        if(button.id == 2)
-        {
-            if (mc.isMultiplayerWorld()) {
-                mc.currentWorld.sendQuittingDisconnectingPacket();
+        if (button.id == 2) {
+            if (this.mc.isMultiplayerWorld()) {
+                this.mc.currentWorld.sendQuittingDisconnectingPacket();
             }
-            mc.changeWorld(null);
-            mc.displayScreen(new ScreenMainMenu());
+            this.mc.changeWorld(null);
+            this.mc.displayScreen(new ScreenMainMenu());
         }
     }
 
     @Override
-	public void render(int mx, int my, float partialTick)
-    {
+    public void render(int mx, int my, float partialTick) {
         I18n i18n = I18n.getInstance();
-        drawGradientRect(0, 0, width, height, 0x60500000, 0xa0803030);
-        GL11.glPushMatrix();
-        GL11.glScalef(2.0F, 2.0F, 2.0F);
-        drawStringCenteredShadow(fontRenderer, i18n.translateKey("gui.game_over.label.title"), width / 2 / 2, 30, 0xffffff);
-        GL11.glPopMatrix();
-        drawStringCenteredShadow(fontRenderer, i18n.translateKeyAndFormat("gui.game_over.label.score", TextFormatting.YELLOW.toString() + mc.thePlayer.getScore()), width / 2, 100, 0xffffff);
+        drawGradientRect(0, 0, this.width, this.height, 0x60500000, 0xa0803030);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().scale(2.0F, 2.0F, 2.0F);
+        drawStringCenteredShadow(this.fontRenderer, i18n.translateKey("gui.game_over.label.title"), this.width / 2 / 2, 30, 0xffffff);
+        GLRenderer.popFrame();
+        drawStringCenteredShadow(this.fontRenderer, i18n.translateKeyAndFormat("gui.game_over.label.score", TextFormatting.YELLOW.toString() + this.mc.thePlayer.getScore()), this.width / 2, 100, 0xffffff);
         super.render(mx, my, partialTick);
     }
 
     @Override
-	public boolean isPauseScreen()
-    {
+    public boolean isPauseScreen() {
         return false;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenHudDesigner.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenHudDesigner.java
index 3517e491a..3adbb7fc2 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenHudDesigner.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenHudDesigner.java
@@ -7,17 +7,17 @@ import net.minecraft.client.gui.hud.component.HudComponentMovable;
 import net.minecraft.client.gui.hud.component.layout.LayoutAbsolute;
 import net.minecraft.client.gui.hud.component.layout.Layout;
 import net.minecraft.client.gui.hud.component.layout.LayoutSnap;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.List;
 
-import static org.lwjgl.opengl.GL11.*;
-
 public class ScreenHudDesigner
     extends Screen {
     private static final int BOTTOM_SPACE = 28;
@@ -36,25 +36,25 @@ public class ScreenHudDesigner
     @Override
     public void init() {
         super.init();
-        this.screenPadding = mc.gameSettings.screenPadding.value;
-        mc.gameSettings.screenPadding.set(0.0f);
+        this.screenPadding = this.mc.gameSettings.screenPadding.value;
+        this.mc.gameSettings.screenPadding.set(0.0f);
 
-        add(new ButtonElement(0, width / 2 - 100, height - BOTTOM_SPACE + (BOTTOM_SPACE - 20) / 2, 178, 20, I18n.getInstance().translateKey("gui.hud_designer.button.done")));
-        add(resetButton = new ButtonElement(1, width / 2 + 80, height - BOTTOM_SPACE + (BOTTOM_SPACE - 20) / 2, 20, 20, "")
+        add(new ButtonElement(0, this.width / 2 - 100, this.height - BOTTOM_SPACE + (BOTTOM_SPACE - 20) / 2, 178, 20, I18n.getInstance().translateKey("gui.hud_designer.button.done")));
+        add(this.resetButton = new ButtonElement(1, this.width / 2 + 80, this.height - BOTTOM_SPACE + (BOTTOM_SPACE - 20) / 2, 20, 20, "")
             .setTextures("minecraft:gui/misc/button_reset", "minecraft:gui/misc/button_reset_highlighted", "minecraft:gui/misc/button_reset"));
     }
 
     @Override
     public void removed() {
         super.removed();
-        mc.gameSettings.screenPadding.set(screenPadding);
+        this.mc.gameSettings.screenPadding.set(this.screenPadding);
     }
 
     @Override
     protected void buttonClicked(@NotNull ButtonElement button) {
         super.buttonClicked(button);
         if (button.id == 0) {
-            mc.displayScreen(getParentScreen());
+            this.mc.displayScreen(getParentScreen());
         }
         if (button.id == 1) {
             HudComponents.INSTANCE.fromSettingsString(HudComponents.DEFAULT_LAYOUT);
@@ -66,60 +66,58 @@ public class ScreenHudDesigner
         updateComponentsUnderMouse(mx, my);
         boolean clickedComponent = false;
         if (buttonNum == 0) {
-            if (!componentsUnderMouse.isEmpty()) {
-                HudComponent componentUnderMouse = componentsUnderMouse.get(componentsUnderMouse.size() - 1);
+            if (!this.componentsUnderMouse.isEmpty()) {
+                HudComponent componentUnderMouse = this.componentsUnderMouse.get(this.componentsUnderMouse.size() - 1);
                 if (componentUnderMouse instanceof HudComponentMovable) {
                     Layout currentLayout = componentUnderMouse.getLayout();
                     ComponentAnchor anchor = getClosestAnchor(
-                        currentLayout.getComponentX(componentUnderMouse, width),
-                        currentLayout.getComponentY(componentUnderMouse, height - BOTTOM_SPACE),
+                        currentLayout.getComponentX(componentUnderMouse, this.width),
+                        currentLayout.getComponentY(componentUnderMouse, this.height - BOTTOM_SPACE),
                         componentUnderMouse, mx, my);
                     Layout layout = new LayoutAbsolute(0, 0, anchor);
                     ((HudComponentMovable) componentUnderMouse).setLayout(layout);
 
-                    heldComponent = componentUnderMouse;
-                    heldAnchor = anchor;
+                    this.heldComponent = componentUnderMouse;
+                    this.heldAnchor = anchor;
                     clickedComponent = true;
                 }
             }
         }
 
         if (!clickedComponent) {
-            heldComponent = null;
+            this.heldComponent = null;
             super.mouseClicked(mx, my, buttonNum);
         }
     }
 
     private void updateHeldComponent(int mouseX, int mouseY) {
-        if (heldComponent == null) return;
-
-        int xSize = heldComponent.getXSize();
-        int ySize = heldComponent.getYSize();
-        int xOffset = heldComponent.getAnchorX(heldAnchor);
-        int yOffset = heldComponent.getAnchorY(heldAnchor);
-        int newX = MathHelper.clamp(mouseX, xOffset, width - (xSize - xOffset));
-        int newY = MathHelper.clamp(mouseY, yOffset, height - BOTTOM_SPACE - (ySize - yOffset));
-
-        Layout layout = heldComponent.getLayout();
-        if (layout instanceof LayoutAbsolute) {
-            LayoutAbsolute absoluteLayout = (LayoutAbsolute) layout;
-            absoluteLayout.setXPosition((float) newX / width);
-            absoluteLayout.setYPosition((float) newY / (height - BOTTOM_SPACE));
+        if (this.heldComponent == null) return;
+
+        int xSize = this.heldComponent.getXSize();
+        int ySize = this.heldComponent.getYSize();
+        int xOffset = this.heldComponent.getAnchorX(this.heldAnchor);
+        int yOffset = this.heldComponent.getAnchorY(this.heldAnchor);
+        int newX = MathHelper.clamp(mouseX, xOffset, this.width - (xSize - xOffset));
+        int newY = MathHelper.clamp(mouseY, yOffset, this.height - BOTTOM_SPACE - (ySize - yOffset));
+
+        Layout layout = this.heldComponent.getLayout();
+        if (layout instanceof LayoutAbsolute absoluteLayout) {
+            absoluteLayout.setXPosition((float) newX / this.width);
+            absoluteLayout.setYPosition((float) newY / (this.height - BOTTOM_SPACE));
         }
 
         // Snap to other components
         int snapRadius = 10;
         boolean didSnap = false;
         for (HudComponent component : HudComponents.INSTANCE.getComponents()) {
-            if (component == heldComponent) continue;
+            if (component == this.heldComponent) continue;
             if (!component.isEnabled()) continue;
             Layout otherLayout = component.getLayout();
             boolean isNested = false;
             Layout nestedLayout = otherLayout;
             for (int i = 0; i < 10; i++) {
-                if (nestedLayout instanceof LayoutSnap) {
-                    LayoutSnap layoutSnap = (LayoutSnap) nestedLayout;
-                    if (layoutSnap.getParent() == heldComponent) {
+                if (nestedLayout instanceof LayoutSnap layoutSnap) {
+                    if (layoutSnap.getParent() == this.heldComponent) {
                         isNested = true;
                         break;
                     } else if (layoutSnap.getParent() != null) {
@@ -133,19 +131,19 @@ public class ScreenHudDesigner
             }
             if (isNested) continue;
 
-            int x = otherLayout.getComponentX(component, width);
-            int y = otherLayout.getComponentY(component, height - BOTTOM_SPACE);
+            int x = otherLayout.getComponentX(component, this.width);
+            int y = otherLayout.getComponentY(component, this.height - BOTTOM_SPACE);
 
             // Get mouse distance
             int mouseDistance = (int) Math.sqrt(Math.pow(mouseX - newX, 2) + Math.pow(mouseY - newY, 2));
 
             if (mouseDistance < 10) {
                 ComponentAnchor anchor = getAnchorInRadius(x, y, component, newX, newY, snapRadius);
-                if (anchor != null && heldAnchor.canConnectTo(anchor)) {
-                    snappedComponent = component;
-                    snappedAnchor = anchor;
-                    LayoutSnap newLayout = new LayoutSnap(component, anchor, heldAnchor);
-                    ((HudComponentMovable) heldComponent).setLayout(newLayout);
+                if (anchor != null && this.heldAnchor.canConnectTo(anchor)) {
+                    this.snappedComponent = component;
+                    this.snappedAnchor = anchor;
+                    LayoutSnap newLayout = new LayoutSnap(component, anchor, this.heldAnchor);
+                    ((HudComponentMovable) this.heldComponent).setLayout(newLayout);
                     didSnap = true;
                     break;
                 }
@@ -157,18 +155,18 @@ public class ScreenHudDesigner
             snapRadius = 20;
             ComponentAnchor anchor = getScreenAnchorInRadius(0, 0, newX, newY, snapRadius);
             if (anchor != null) {
-                snappedComponent = null;
-                snappedAnchor = anchor;
-                LayoutSnap newLayout = new LayoutSnap(null, snappedAnchor, heldAnchor);
-                ((HudComponentMovable) heldComponent).setLayout(newLayout);
+                this.snappedComponent = null;
+                this.snappedAnchor = anchor;
+                LayoutSnap newLayout = new LayoutSnap(null, this.snappedAnchor, this.heldAnchor);
+                ((HudComponentMovable) this.heldComponent).setLayout(newLayout);
                 didSnap = true;
             }
 
             if (!didSnap) {
-                LayoutAbsolute newLayout = new LayoutAbsolute((float) newX / width, (float) newY / (height - BOTTOM_SPACE), heldAnchor);
-                ((HudComponentMovable) heldComponent).setLayout(newLayout);
-                snappedComponent = null;
-                snappedAnchor = null;
+                LayoutAbsolute newLayout = new LayoutAbsolute((float) newX / this.width, (float) newY / (this.height - BOTTOM_SPACE), this.heldAnchor);
+                ((HudComponentMovable) this.heldComponent).setLayout(newLayout);
+                this.snappedComponent = null;
+                this.snappedAnchor = null;
             }
         }
     }
@@ -213,8 +211,8 @@ public class ScreenHudDesigner
         int minDistance = Integer.MAX_VALUE;
         for (ComponentAnchor componentAnchor : ComponentAnchor.values()) {
             if (componentAnchor == ComponentAnchor.CENTER) continue; // Center anchor is not valid
-            int xAnchor = (int) (componentAnchor.xPosition * width);
-            int yAnchor = (int) (componentAnchor.yPosition * (height - BOTTOM_SPACE));
+            int xAnchor = (int) (componentAnchor.xPosition * this.width);
+            int yAnchor = (int) (componentAnchor.yPosition * (this.height - BOTTOM_SPACE));
             int distance = (int) Math.sqrt(Math.pow(mouseX - (x + xAnchor), 2) + Math.pow(mouseY - (y + yAnchor), 2));
             if (distance < minDistance && distance <= radius) {
                 minDistance = distance;
@@ -227,10 +225,10 @@ public class ScreenHudDesigner
     @Override
     public void mouseReleased(int mx, int my, int buttonNum) {
         if (buttonNum == 0) {
-            heldComponent = null;
-            heldAnchor = null;
-            snappedComponent = null;
-            snappedAnchor = null;
+            this.heldComponent = null;
+            this.heldAnchor = null;
+            this.snappedComponent = null;
+            this.snappedAnchor = null;
         }
         super.mouseReleased(mx, my, buttonNum);
     }
@@ -239,7 +237,7 @@ public class ScreenHudDesigner
     public void render(int mx, int my, float partialTick) {
         updateComponentsUnderMouse(mx, my);
 
-        if (heldComponent != null) {
+        if (this.heldComponent != null) {
             updateHeldComponent(mx, my);
         }
 
@@ -247,23 +245,24 @@ public class ScreenHudDesigner
 
         drawHudComponents(mx, my);
 
-        Tessellator tessellator = Tessellator.instance;
-        GL11.glDisable(GL_DEPTH_TEST);
-        GL11.glDisable(GL_TEXTURE_2D);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.disableState(State.DEPTH_TEST);
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_I(0, 255);
-        tessellator.addVertexWithUV(0, height - BOTTOM_SPACE + 1, 0.0D, 0.0D, 1.0D);
-        tessellator.addVertexWithUV(width, height - BOTTOM_SPACE + 1, 0.0D, 1.0D, 1.0D);
-        tessellator.addVertexWithUV(width, height - BOTTOM_SPACE, 0.0D, 1.0D, 0.0D);
-        tessellator.addVertexWithUV(0, height - BOTTOM_SPACE, 0.0D, 0.0D, 0.0D);
+        tessellator.setColor2i(0, 255);
+        tessellator.addVertexWithUV(0, this.height - BOTTOM_SPACE + 1, 0.0D, 0.0D, 1.0D);
+        tessellator.addVertexWithUV(this.width, this.height - BOTTOM_SPACE + 1, 0.0D, 1.0D, 1.0D);
+        tessellator.addVertexWithUV(this.width, this.height - BOTTOM_SPACE, 0.0D, 1.0D, 0.0D);
+        tessellator.addVertexWithUV(0, this.height - BOTTOM_SPACE, 0.0D, 0.0D, 0.0D);
         tessellator.draw();
-        GL11.glEnable(GL_TEXTURE_2D);
+        GLRenderer.popFrame();
 
         // Draw all anchors for screen edges
-        if (heldComponent != null) {
+        if (this.heldComponent != null) {
             for (ComponentAnchor anchor : ComponentAnchor.values()) {
                 if (anchor == ComponentAnchor.CENTER) continue; // Center anchor is not valid
-                drawAnchor(0, 0, (int) (width * anchor.xPosition), (int) ((height - BOTTOM_SPACE) * anchor.yPosition), anchor);
+                drawAnchor(0, 0, (int) (this.width * anchor.xPosition), (int) ((this.height - BOTTOM_SPACE) * anchor.yPosition), anchor);
             }
         }
 
@@ -273,34 +272,36 @@ public class ScreenHudDesigner
     @Override
     public void renderTexturedBackground() {
         super.renderTexturedBackground();
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_FOG);
-        Tessellator tessellator = Tessellator.instance;
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/designer_bg.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.globalSetLightEnabled(false);
+//        GL11.glDisable(GL11.GL_FOG);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/designer_bg.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         float scale = 32F;
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(0.0D, height - BOTTOM_SPACE, 0.0D, 0.0D, (float)(height - BOTTOM_SPACE) / scale);
-        tessellator.addVertexWithUV(width, height - BOTTOM_SPACE, 0.0D, (float)width / scale, (float)(height - BOTTOM_SPACE) / scale);
-        tessellator.addVertexWithUV(width, 0.0D, 0.0D, (float)width / scale, 0);
+        tessellator.addVertexWithUV(0.0D, this.height - BOTTOM_SPACE, 0.0D, 0.0D, (float) (this.height - BOTTOM_SPACE) / scale);
+        tessellator.addVertexWithUV(this.width, this.height - BOTTOM_SPACE, 0.0D, (float) this.width / scale, (float) (this.height - BOTTOM_SPACE) / scale);
+        tessellator.addVertexWithUV(this.width, 0.0D, 0.0D, (float) this.width / scale, 0);
         tessellator.addVertexWithUV(0.0D, 0.0D, 0.0D, 0.0D, 0);
         tessellator.draw();
     }
 
     private void drawHudComponents(int mouseX, int mouseY) {
         HudComponent lastComponent = null;
-        if (!componentsUnderMouse.isEmpty()) {
-            lastComponent = componentsUnderMouse.get(componentsUnderMouse.size() - 1);
+        if (!this.componentsUnderMouse.isEmpty()) {
+            lastComponent = this.componentsUnderMouse.get(this.componentsUnderMouse.size() - 1);
         }
         for (HudComponent component : HudComponents.INSTANCE.getComponents()) {
-            if (component == heldComponent) continue;
+            if (component == this.heldComponent) continue;
             if (!component.isEnabled()) continue;
             Layout layout = component.getLayout();
-            component.renderPreview(this, layout, width, height - BOTTOM_SPACE);
-            if (heldComponent == null) {
-                if (!componentsUnderMouse.isEmpty() && component == lastComponent) {
-                    int x = layout.getComponentX(component, width);
-                    int y = layout.getComponentY(component, height - BOTTOM_SPACE);
+            GLRenderer.pushFrame();
+            component.renderPreview(this, layout, this.width, this.height - BOTTOM_SPACE);
+            GLRenderer.popFrame();
+            if (this.heldComponent == null) {
+                if (!this.componentsUnderMouse.isEmpty() && component == lastComponent) {
+                    int x = layout.getComponentX(component, this.width);
+                    int y = layout.getComponentY(component, this.height - BOTTOM_SPACE);
                     int xSize = component.getXSize();
                     int ySize = component.getYSize();
                     drawBox(x, y, x + xSize, y + ySize, 0xff00ff00, 1);
@@ -312,25 +313,27 @@ public class ScreenHudDesigner
                 }
             }
         }
-        if (heldComponent != null) {
-            Layout layout = heldComponent.getLayout();
-            heldComponent.renderPreview(this, layout, width, height - BOTTOM_SPACE);
-            int x = layout.getComponentX(heldComponent, width);
-            int y = layout.getComponentY(heldComponent, height - BOTTOM_SPACE);
-            int xSize = heldComponent.getXSize();
-            int ySize = heldComponent.getYSize();
-            int xAnchor = heldComponent.getAnchorX(heldAnchor);
-            int yAnchor = heldComponent.getAnchorY(heldAnchor);
+        if (this.heldComponent != null) {
+            Layout layout = this.heldComponent.getLayout();
+            GLRenderer.pushFrame();
+            this.heldComponent.renderPreview(this, layout, this.width, this.height - BOTTOM_SPACE);
+            GLRenderer.popFrame();
+            int x = layout.getComponentX(this.heldComponent, this.width);
+            int y = layout.getComponentY(this.heldComponent, this.height - BOTTOM_SPACE);
+            int xSize = this.heldComponent.getXSize();
+            int ySize = this.heldComponent.getYSize();
+            int xAnchor = this.heldComponent.getAnchorX(this.heldAnchor);
+            int yAnchor = this.heldComponent.getAnchorY(this.heldAnchor);
             drawBox(x, y, x + xSize, y + ySize, 0xffff0000, 1);
-            drawAnchor(x, y, xAnchor, yAnchor, heldAnchor);
+            drawAnchor(x, y, xAnchor, yAnchor, this.heldAnchor);
         }
-        if (snappedComponent != null && snappedAnchor != null) {
-            Layout layout = snappedComponent.getLayout();
-            int x = layout.getComponentX(snappedComponent, width);
-            int y = layout.getComponentY(snappedComponent, height - BOTTOM_SPACE);
-            int xAnchor = snappedComponent.getAnchorX(snappedAnchor);
-            int yAnchor = snappedComponent.getAnchorY(snappedAnchor);
-            drawAnchor(x, y, xAnchor, yAnchor, snappedAnchor);
+        if (this.snappedComponent != null && this.snappedAnchor != null) {
+            Layout layout = this.snappedComponent.getLayout();
+            int x = layout.getComponentX(this.snappedComponent, this.width);
+            int y = layout.getComponentY(this.snappedComponent, this.height - BOTTOM_SPACE);
+            int xAnchor = this.snappedComponent.getAnchorX(this.snappedAnchor);
+            int yAnchor = this.snappedComponent.getAnchorY(this.snappedAnchor);
+            drawAnchor(x, y, xAnchor, yAnchor, this.snappedAnchor);
         }
     }
 
@@ -338,7 +341,8 @@ public class ScreenHudDesigner
         int color = 0xff0000ff;
         int lineLength = 5;
 
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
+        GLRenderer.pushFrame();
+        GLRenderer.disableState(State.DEPTH_TEST);
         switch (anchor) {
             case TOP_LEFT:
                 drawRect(x + xAnchor, y + yAnchor, x + xAnchor + lineLength, y + yAnchor + 1, color);
@@ -373,21 +377,21 @@ public class ScreenHudDesigner
                 drawRect(x + xAnchor - 1, y + yAnchor - lineLength, x + xAnchor, y + yAnchor, color);
                 break;
         }
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        zLevel = 0;
+        GLRenderer.popFrame();
+        this.zLevel = 0;
     }
 
     private void updateComponentsUnderMouse(int mouseX, int mouseY) {
-        componentsUnderMouse.clear();
+        this.componentsUnderMouse.clear();
         for (HudComponent component : HudComponents.INSTANCE.getComponents()) {
             if (!component.isEnabled()) continue;
             Layout layout = component.getLayout();
-            int cx = layout.getComponentX(component, width);
-            int cy = layout.getComponentY(component, height - BOTTOM_SPACE);
+            int cx = layout.getComponentX(component, this.width);
+            int cy = layout.getComponentY(component, this.height - BOTTOM_SPACE);
             int cXSize = component.getXSize();
             int cYSize = component.getYSize();
             if (mouseX >= cx && mouseX < cx + cXSize && mouseY >= cy && mouseY < cy + cYSize) {
-                componentsUnderMouse.add(component);
+                this.componentsUnderMouse.add(component);
             }
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenLabelEditor.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenLabelEditor.java
index 286eb873d..86d3d761a 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenLabelEditor.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenLabelEditor.java
@@ -4,6 +4,7 @@ import net.minecraft.client.gui.keyboard.ScreenKeyboard;
 import net.minecraft.client.gui.text.ITextField;
 import net.minecraft.client.gui.text.TextFieldEditor;
 import net.minecraft.client.input.InputType;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.net.command.TextFormatting;
@@ -11,10 +12,8 @@ import net.minecraft.core.net.packet.PacketSetItemName;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 
-public class ScreenLabelEditor extends Screen implements ITextField
-{
+public class ScreenLabelEditor extends Screen implements ITextField {
     protected String screenTitle;
     protected ItemStack item;
     protected String text;
@@ -25,105 +24,96 @@ public class ScreenLabelEditor extends Screen implements ITextField
     protected int slot;
     protected int cursorCounter;
 
-    public ScreenLabelEditor(final ItemStack item, int slot)
-    {
-        screenTitle = I18n.getInstance().translateKey("gui.edit_label.label.title");
+    public ScreenLabelEditor(final ItemStack item, int slot) {
+        this.screenTitle = I18n.getInstance().translateKey("gui.edit_label.label.title");
         this.item = item;
-        if(item.hasCustomName()) {
-        	this.text = item.getCustomName();
+        if (item.hasCustomName()) {
+            this.text = item.getCustomName();
         } else {
-        	this.text = "";
+            this.text = "";
         }
         this.editor = new TextFieldEditor(this);
         this.color = item.getDisplayColor();
-        xSize = 176;
-        ySize = 166;
+        this.xSize = 176;
+        this.ySize = 166;
         this.slot = slot;
     }
 
     @Override
     public void tick() {
-        cursorCounter++;
-        if ((mc.gameSettings.forceOnscreenKeyboard.value || mc.inputType == InputType.CONTROLLER) && !(mc.currentScreen instanceof ScreenKeyboard)) {
-            buttonClicked(buttons.get(0)); // Close out of gui when exiting keyboard screen
+        this.cursorCounter++;
+        if ((this.mc.gameSettings.forceOnscreenKeyboard.value || this.mc.inputType == InputType.CONTROLLER) && !(this.mc.currentScreen instanceof ScreenKeyboard)) {
+            buttonClicked(this.buttons.get(0)); // Close out of gui when exiting keyboard screen
         }
     }
 
     @Override
-    protected void buttonClicked(final @NotNull ButtonElement button)
-    {
-        if (!button.enabled)
-        {
+    protected void buttonClicked(final @NotNull ButtonElement button) {
+        if (!button.enabled) {
             return;
         }
-        if (button.id == 0)
-        {
-        	item.setCustomName(text);
-            mc.displayScreen(null);
-
-            if (mc.currentWorld.isClientSide)
-            {
-                mc.getSendQueue().addToSendQueue(new PacketSetItemName(slot, text));
+        if (button.id == 0) {
+            this.item.setCustomName(this.text);
+            this.mc.displayScreen(null);
+
+            if (this.mc.currentWorld.isClientSide) {
+                this.mc.getSendQueue().addToSendQueue(new PacketSetItemName(this.slot, this.text));
             }
         }
     }
 
     @Override
-    public void render(final int mx, final int my, final float f)
-    {
+    public void render(final int mx, final int my, final float f) {
         renderBackground();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/scroll.png").bind();
-        final int widthBG = width / 2 - 56;
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/scroll.png").bind();
+        final int widthBG = this.width / 2 - 56;
         final int heightBG = 89;
         drawTexturedModalRect(widthBG, heightBG, 0, 0, 113, 34);
 
-        drawStringCenteredShadow(fontRenderer, screenTitle, width / 2, 40, 0xffffff);
+        drawStringCenteredShadow(this.fontRenderer, this.screenTitle, this.width / 2, 40, 0xffffff);
 
-        drawStringCenteredShadow(fontRenderer, TextFormatting.get(color) + "> " + text + " <", width / 2, 100, 0xffffff);
+        drawStringCenteredShadow(this.fontRenderer, TextFormatting.get(this.color) + "> " + this.text + " <", this.width / 2, 100, 0xffffff);
 
-        boolean drawCursor = !text.isEmpty() && (cursorCounter / 6) % 2 == 0;
-        if (drawCursor)
-        {
-            int width = MathHelper.ceil(fontRenderer.stringWidthDouble(editor.getText()));
-            if (editor.getCursor() < editor.getText().length())
-            {
-                width = MathHelper.ceil(fontRenderer.stringWidthDouble(editor.getText().substring(0, editor.getCursor())));
+        boolean drawCursor = !this.text.isEmpty() && (this.cursorCounter / 6) % 2 == 0;
+        if (drawCursor) {
+            int width = MathHelper.ceil(this.fontRenderer.stringWidthDouble(this.editor.getText()));
+            if (this.editor.getCursor() < this.editor.getText().length()) {
+                width = MathHelper.ceil(this.fontRenderer.stringWidthDouble(this.editor.getText().substring(0, this.editor.getCursor())));
             }
-            drawStringShadow(fontRenderer, "_", MathHelper.ceil(this.width - fontRenderer.stringWidthDouble(editor.getText())/2) + width, 101, 0xffffff);
+            drawStringShadow(this.fontRenderer, "_", MathHelper.ceil(this.width - this.fontRenderer.stringWidthDouble(this.editor.getText()) / 2) + width, 101, 0xffffff);
         }
         super.render(mx, my, f);
     }
 
     @Override
-    public void init()
-    {
-        buttons.clear();
+    public void init() {
+        this.buttons.clear();
         Keyboard.enableRepeatEvents(true);
-        buttons.add(new ButtonElement(0, width / 2 - 100, height / 4 + 120, I18n.getInstance().translateKey("gui.edit_label.button.done")));
-
-        if (mc.gameSettings.forceOnscreenKeyboard.value || mc.inputType == InputType.CONTROLLER) {
-            mc.displayScreen(new ScreenKeyboard(this, editor,
-                (s) -> {},
-                (c, k, s) -> {},
-                s -> {}));
+        this.buttons.add(new ButtonElement(0, this.width / 2 - 100, this.height / 4 + 120, I18n.getInstance().translateKey("gui.edit_label.button.done")));
+
+        if (this.mc.gameSettings.forceOnscreenKeyboard.value || this.mc.inputType == InputType.CONTROLLER) {
+            this.mc.displayScreen(new ScreenKeyboard(this, this.editor,
+                (s) -> {
+                },
+                (c, k, s) -> {
+                },
+                s -> {
+                }));
         }
     }
 
     @Override
-	public void keyPressed(final char eventCharacter, final int eventKey, int mx, int my)
-    {
-        if (eventKey == Keyboard.KEY_RETURN || eventKey == Keyboard.KEY_NUMPADENTER || eventKey == Keyboard.KEY_ESCAPE)
-        {
-            buttonClicked(buttons.get(0));
+    public void keyPressed(final char eventCharacter, final int eventKey, int mx, int my) {
+        if (eventKey == Keyboard.KEY_RETURN || eventKey == Keyboard.KEY_NUMPADENTER || eventKey == Keyboard.KEY_ESCAPE) {
+            buttonClicked(this.buttons.get(0));
             return;
         }
-        editor.handleInput(eventKey, eventCharacter);
+        this.editor.handleInput(eventKey, eventCharacter);
     }
 
     @Override
-    public void removed()
-    {
+    public void removed() {
         Keyboard.enableRepeatEvents(false);
     }
 
@@ -134,7 +124,7 @@ public class ScreenLabelEditor extends Screen implements ITextField
 
     @Override
     public String getText() {
-        return text;
+        return this.text;
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenMainMenu.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenMainMenu.java
index 794f9735e..6ad285d9e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenMainMenu.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenMainMenu.java
@@ -21,15 +21,19 @@ import net.minecraft.client.gui.hud.HudIngameDoom;
 import net.minecraft.client.gui.server.ScreenSelectServer;
 import net.minecraft.client.holiday.Holidays;
 import net.minecraft.client.render.Lighting;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.CullFace;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.client.util.helper.UrlHelper;
 import net.minecraft.core.Version;
 import org.jetbrains.annotations.NotNull;
+import org.joml.Math;
 import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.util.glu.GLU;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.options.ScreenOptions;
@@ -39,41 +43,41 @@ import net.minecraft.core.block.Blocks;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.sound.SoundCategory;
 import net.minecraft.core.util.helper.MathHelper;
+import org.lwjgl.opengl.GL41;
 import org.slf4j.Logger;
 
-public class ScreenMainMenu extends Screen
-{
+public class ScreenMainMenu extends Screen {
     private static final Logger LOGGER = LogUtils.getLogger();
 
     private static final Block<?>[] BLOCKS_TO_DRAW = {
-    		Blocks.STONE, Blocks.DIRT, Blocks.PLANKS_OAK, Blocks.COBBLE_STONE, Blocks.COBBLE_STONE_MOSSY, Blocks.BASALT, Blocks.LIMESTONE,
-    		Blocks.GRANITE, Blocks.BRICK_CLAY, Blocks.ICE, Blocks.WOOL, Blocks.BLOCK_SNOW, Blocks.OBSIDIAN, Blocks.COBBLE_NETHERRACK
+        Blocks.STONE, Blocks.DIRT, Blocks.PLANKS_OAK, Blocks.COBBLE_STONE, Blocks.COBBLE_STONE_MOSSY, Blocks.BASALT, Blocks.LIMESTONE,
+        Blocks.GRANITE, Blocks.BRICK_CLAY, Blocks.ICE, Blocks.WOOL, Blocks.BLOCK_SNOW, Blocks.OBSIDIAN, Blocks.COBBLE_NETHERRACK
     };
     private static String[] logoBlockLayers = null;
-    
+
     private static final int[] KEY_CHAIN = {
-            Keyboard.KEY_I, Keyboard.KEY_D, Keyboard.KEY_S, Keyboard.KEY_P, Keyboard.KEY_I, Keyboard.KEY_S,
-            Keyboard.KEY_P, Keyboard.KEY_O, Keyboard.KEY_P, Keyboard.KEY_D, Keyboard.KEY_RETURN
+        Keyboard.KEY_I, Keyboard.KEY_D, Keyboard.KEY_S, Keyboard.KEY_P, Keyboard.KEY_I, Keyboard.KEY_S,
+        Keyboard.KEY_P, Keyboard.KEY_O, Keyboard.KEY_P, Keyboard.KEY_D, Keyboard.KEY_RETURN
     };
-    
+
     private static final Random rand = new Random();
-    
+
     private String splashText = "missingno";
     private ButtonElement multiplayerButton;
     private LogoBlock[][] logoBlocks;
-    private Snowflake[] snowflakes = new Snowflake[50];
+    private final Snowflake[] snowflakes = new Snowflake[50];
     private int logoClickCounter = 0;
     private int indexToDraw = 0;
     private int codeProgress = 0;
     private boolean showBuildTime = false;
-    private String buildTimeString = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date(Version.BUILD_TIME));
+    private final String buildTimeString = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date(Version.BUILD_TIME));
 
     static {
-    	loadLogo();
+        loadLogo();
     }
 
-	public ScreenMainMenu() {
-		ScreenPause.photoModeDisabled = false;
+    public ScreenMainMenu() {
+        ScreenPause.photoModeDisabled = false;
 
         try (InputStream stream = Minecraft.getMinecraft().texturePackList.getResourceAsStream("/assets/minecraft/textures/gui/title/splashes.txt")) {
 
@@ -94,120 +98,93 @@ public class ScreenMainMenu extends Screen
                     allSplashes.add(line);
                 }
             }
-            splashText = allSplashes.get(rand.nextInt(allSplashes.size()));
+            this.splashText = allSplashes.get(rand.nextInt(allSplashes.size()));
         } catch (Exception e) {
             LOGGER.error("Failed to load splash texts!", e);
         }
-	}
+    }
 
     @Override
-	public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
-    {
-        if (eventKey == KEY_CHAIN[codeProgress])
-        {
-            codeProgress++;
-            if (codeProgress == KEY_CHAIN.length)
-            {
-                if (mc.hudIngame instanceof HudIngameDoom)
-                {
-                    mc.hudIngame = new HudIngame(mc);
-                }
-                else
-                {
-                    mc.hudIngame = new HudIngameDoom(mc);
+    public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
+        if (eventKey == KEY_CHAIN[this.codeProgress]) {
+            this.codeProgress++;
+            if (this.codeProgress == KEY_CHAIN.length) {
+                if (this.mc.hudIngame instanceof HudIngameDoom) {
+                    this.mc.hudIngame = new HudIngame(this.mc);
+                } else {
+                    this.mc.hudIngame = new HudIngameDoom(this.mc);
                 }
-                mc.sndManager.playSound("mob.pig", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
-                codeProgress = 0;
+                this.mc.sndManager.playSound("mob.pig", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
+                this.codeProgress = 0;
             }
-        }
-        else if (eventKey != -1)
-        {
-            codeProgress = 0;
+        } else if (eventKey != -1) {
+            this.codeProgress = 0;
         }
     }
 
     @Override
-	public void init()
-    {
+    public void init() {
         I18n i18n = I18n.getInstance();
 
-        for(int i = 0; i < snowflakes.length; i++){
-            snowflakes[i] = new Snowflake(rand.nextInt(width), rand.nextInt(height),1 + rand.nextInt(4), height);
+        for (int i = 0; i < this.snowflakes.length; i++) {
+            this.snowflakes[i] = new Snowflake(rand.nextInt(this.width), rand.nextInt(this.height), 1 + rand.nextInt(4), this.height);
         }
 
-        if (Holidays.ANNIVERSARY_JONKADELIC.isActive())
-        {
-            splashText = i18n.translateKey("gui.main_menu.label.splash.jonkadelic_birthday");
-        }
-        else if (Holidays.ANNIVERSARY_MAGGANDGEEZ.isActive())
-        {
-            splashText = i18n.translateKey("gui.main_menu.label.splash.maggandgeez_birthday");
-        }
-        else if (Holidays.ANNIVERSARY_MINECRAFT.isActive())
-        {
-            splashText = i18n.translateKey("gui.main_menu.label.splash.minecraft_birthday");
-        }
-        else if (Holidays.ANNIVERSARY_BTA.isActive())
-        {
-            splashText = i18n.translateKey("gui.main_menu.label.splash.bta_birthday");
-        }
-        else if (Holidays.XMAS.isActive())
-        {
-            splashText = i18n.translateKey("gui.main_menu.label.splash.xmas");
-        }
-        else if (Holidays.NEW_YEAR.isActive())
-        {
-            splashText = i18n.translateKey("gui.main_menu.label.splash.new_year");
-        }
-        else if (Holidays.HALLOWEEN.isActive())
-        {
-            splashText = i18n.translateKey("gui.main_menu.label.splash.halloween");
+        if (Holidays.ANNIVERSARY_JONKADELIC.isActive()) {
+            this.splashText = i18n.translateKey("gui.main_menu.label.splash.jonkadelic_birthday");
+        } else if (Holidays.ANNIVERSARY_MAGGANDGEEZ.isActive()) {
+            this.splashText = i18n.translateKey("gui.main_menu.label.splash.maggandgeez_birthday");
+        } else if (Holidays.ANNIVERSARY_MINECRAFT.isActive()) {
+            this.splashText = i18n.translateKey("gui.main_menu.label.splash.minecraft_birthday");
+        } else if (Holidays.ANNIVERSARY_BTA.isActive()) {
+            this.splashText = i18n.translateKey("gui.main_menu.label.splash.bta_birthday");
+        } else if (Holidays.XMAS.isActive()) {
+            this.splashText = i18n.translateKey("gui.main_menu.label.splash.xmas");
+        } else if (Holidays.NEW_YEAR.isActive()) {
+            this.splashText = i18n.translateKey("gui.main_menu.label.splash.new_year");
+        } else if (Holidays.HALLOWEEN.isActive()) {
+            this.splashText = i18n.translateKey("gui.main_menu.label.splash.halloween");
         }
 
-        int i = height / 4 + 48;
-        buttons.add(new ButtonElement(1, width / 2 - 100, i, i18n.translateKey("gui.main_menu.button.singleplayer")));
-        buttons.add(multiplayerButton = new ButtonElement(2, width / 2 - 100, i + 24, i18n.translateKey("gui.main_menu.button.multiplayer")));
-        buttons.add(new ButtonElement(3, width / 2 - 100, i + 48, i18n.translateKey("gui.main_menu.button.asset_packs")));
-        if(mc.hideQuitButton)
-        {
-            buttons.add(new ButtonElement(0, width / 2 - 100, i + 72, i18n.translateKey("gui.main_menu.button.options")));
-        } else
-        {
-            buttons.add(new ButtonElement(0, width / 2 - 100, i + 72 + 12, 98, 20, i18n.translateKey("gui.main_menu.button.options")));
-            buttons.add(new ButtonElement(4, width / 2 + 2, i + 72 + 12, 98, 20, i18n.translateKey("gui.main_menu.button.quit_game")));
+        int i = this.height / 4 + 48;
+        this.buttons.add(new ButtonElement(1, this.width / 2 - 100, i, i18n.translateKey("gui.main_menu.button.singleplayer")));
+        this.buttons.add(this.multiplayerButton = new ButtonElement(2, this.width / 2 - 100, i + 24, i18n.translateKey("gui.main_menu.button.multiplayer")));
+        this.buttons.add(new ButtonElement(3, this.width / 2 - 100, i + 48, i18n.translateKey("gui.main_menu.button.asset_packs")));
+        if (this.mc.hideQuitButton) {
+            this.buttons.add(new ButtonElement(0, this.width / 2 - 100, i + 72, i18n.translateKey("gui.main_menu.button.options")));
+        } else {
+            this.buttons.add(new ButtonElement(0, this.width / 2 - 100, i + 72 + 12, 98, 20, i18n.translateKey("gui.main_menu.button.options")));
+            this.buttons.add(new ButtonElement(4, this.width / 2 + 2, i + 72 + 12, 98, 20, i18n.translateKey("gui.main_menu.button.quit_game")));
         }
         int d = 1; // Move away from the edge of the screen to prevent unintentional activation because the cursor defaults to 0, 0
-        buttons.add(new ClickableLabelElement(5, d, height - 48 - d, i18n.translateKey("gui.main_menu.button.credits"), 0xFF9F9F9F, "minecraft:gui/screen/main_menu/icon_credits"));
-        buttons.add(new ClickableLabelElement(6, d, height - 36 - d, i18n.translateKey("gui.main_menu.button.website"), 0xFF5AA938, "minecraft:gui/screen/main_menu/icon_website"));
-        buttons.add(new ClickableLabelElement(7, d, height - 24 - d, i18n.translateKey("gui.main_menu.button.discord"), 0xFF5865F2, "minecraft:gui/screen/main_menu/icon_discord"));
-        buttons.add(new ClickableLabelElement(8, d, height - 12 - d, i18n.translateKey("gui.main_menu.button.youtube"), 0xFFFF0000, "minecraft:gui/screen/main_menu/icon_youtube"));
-        buttons.add(new ButtonElement(9, width / 2 + 104, i + 72 + 12, 20, 20, "")
+        this.buttons.add(new ClickableLabelElement(5, d, this.height - 48 - d, i18n.translateKey("gui.main_menu.button.credits"), 0xFF9F9F9F, "minecraft:gui/screen/main_menu/icon_credits"));
+        this.buttons.add(new ClickableLabelElement(6, d, this.height - 36 - d, i18n.translateKey("gui.main_menu.button.website"), 0xFF5AA938, "minecraft:gui/screen/main_menu/icon_website"));
+        this.buttons.add(new ClickableLabelElement(7, d, this.height - 24 - d, i18n.translateKey("gui.main_menu.button.discord"), 0xFF5865F2, "minecraft:gui/screen/main_menu/icon_discord"));
+        this.buttons.add(new ClickableLabelElement(8, d, this.height - 12 - d, i18n.translateKey("gui.main_menu.button.youtube"), 0xFFFF0000, "minecraft:gui/screen/main_menu/icon_youtube"));
+        this.buttons.add(new ButtonElement(9, this.width / 2 + 104, i + 72 + 12, 20, 20, "")
             .setTextures("minecraft:gui/misc/button_language", "minecraft:gui/misc/button_language_highlighted", "minecraft:gui/misc/button_language"));
-        ButtonElement debugButton = new ButtonElement(10, width - 8, height - 8, 8, 8, "");
+        ButtonElement debugButton = new ButtonElement(10, this.width - 8, this.height - 8, 8, 8, "");
         debugButton.visible = false;
-        buttons.add(debugButton);
-        buttons.add(new ButtonElement(11, width / 2 - 104 - 20, i + 72 + 12, 20, 20, "")
+        this.buttons.add(debugButton);
+        this.buttons.add(new ButtonElement(11, this.width / 2 - 104 - 20, i + 72 + 12, 20, 20, "")
             .setTextures("minecraft:gui/misc/button_support", "minecraft:gui/misc/button_support_highlighted", "minecraft:gui/misc/button_support"));
-        if(mc.session == null)
-        {
-            multiplayerButton.enabled = false;
+        if (this.mc.session == null) {
+            this.multiplayerButton.enabled = false;
         }
-        if (Minecraft.isMultiplayerDisabled)
-        {
-        	multiplayerButton.enabled = false;
-        	multiplayerButton.displayString = i18n.translateKey("gui.main_menu.button.multiplayer.disabled");
+        if (Minecraft.isMultiplayerDisabled) {
+            this.multiplayerButton.enabled = false;
+            this.multiplayerButton.displayString = i18n.translateKey("gui.main_menu.button.multiplayer.disabled");
         }
     }
 
     @Override
-    protected void buttonClicked(@NotNull ButtonElement button)
-    {
+    protected void buttonClicked(@NotNull ButtonElement button) {
         switch (button.id) {
             case 0:
-                mc.displayScreen(new ScreenOptions(this));
+                this.mc.displayScreen(new ScreenOptions(this));
                 break;
             case 1:
-                mc.displayScreen(new ScreenSelectWorld(this));
+                this.mc.displayScreen(new ScreenSelectWorld(this));
                 break;
             case 2:
                 boolean hasJCE;
@@ -216,20 +193,20 @@ public class ScreenMainMenu extends Screen
                 } catch (final Exception ignored) {
                     hasJCE = false;
                 }
-                if (!(hasJCE) && mc.gameSettings.doJCECheck.value) {
-                    mc.displayScreen(new ScreenMissingJCE(this, new ScreenSelectServer(this)));
+                if (!(hasJCE) && this.mc.gameSettings.doJCECheck.value) {
+                    this.mc.displayScreen(new ScreenMissingJCE(this, new ScreenSelectServer(this)));
                 } else {
-                    mc.displayScreen(new ScreenSelectServer(this));
+                    this.mc.displayScreen(new ScreenSelectServer(this));
                 }
                 break;
             case 3:
-                mc.displayScreen(new ScreenOptions(this, OptionsPages.ASSET_PACKS));
+                this.mc.displayScreen(new ScreenOptions(this, OptionsPages.ASSET_PACKS));
                 break;
             case 4:
-                mc.shutdown();
+                this.mc.shutdown();
                 break;
             case 5:
-                mc.displayScreen(new ScreenCredits(this));
+                this.mc.displayScreen(new ScreenCredits(this));
                 break;
             case 6:
                 // Website
@@ -248,32 +225,30 @@ public class ScreenMainMenu extends Screen
                 UrlHelper.openURL("https://bugs.betterthanadventure.net/");
                 break;
             case 9:
-                mc.displayScreen(new ScreenOptions(this, OptionsPages.LANGUAGE));
+                this.mc.displayScreen(new ScreenOptions(this, OptionsPages.LANGUAGE));
                 break;
             case 10:
-                mc.displayScreen(new ScreenOptions(this, OptionsPages.DEBUG));
+                this.mc.displayScreen(new ScreenOptions(this, OptionsPages.DEBUG));
                 break;
         }
     }
 
-	@Override
-	public void renderTexturedBackground() {
-		if(mc.mainMenuBackground.isEnabled() && !mc.gameSettings.alphaMenu.value) {
-			mc.mainMenuBackground.draw();
-		}else {
-			super.renderTexturedBackground();
-		}
-	}
+    @Override
+    public void renderTexturedBackground() {
+        if (this.mc.mainMenuBackground.isEnabled() && !this.mc.gameSettings.alphaMenu.value) {
+            this.mc.mainMenuBackground.draw();
+        } else {
+            super.renderTexturedBackground();
+        }
+    }
 
     @Override
-    public void tick()
-    {
-        for (Snowflake snowflake : snowflakes) {
+    public void tick() {
+        for (Snowflake snowflake : this.snowflakes) {
             snowflake.updateEffects();
         }
 
-        if(this.logoBlocks != null)
-        {
+        if (this.logoBlocks != null) {
             for (LogoBlock[] logoBlock : this.logoBlocks) {
                 for (LogoBlock block : logoBlock) {
                     block.updateLogoEffects();
@@ -281,213 +256,195 @@ public class ScreenMainMenu extends Screen
             }
         }
 
-        if (mc.gameSettings.playTitleScreenMusic.value) {
-            mc.sndManager.playTitleScreenMusic();
+        if (this.mc.gameSettings.playTitleScreenMusic.value) {
+            this.mc.sndManager.playTitleScreenMusic();
         }
     }
 
     @Override
-    public void mouseClicked(int mx, int my, int buttonNum)
-    {
+    public void mouseClicked(int mx, int my, int buttonNum) {
         super.mouseClicked(mx, my, buttonNum);
 
         int logoWidth = 274;
-        int logoX = width / 2 - logoWidth / 2;
+        int logoX = this.width / 2 - logoWidth / 2;
         int logoHeight = 30;
         int p = 8;
-        if (mx >= logoX + p && mx <= logoX + 270 - p && my >= logoHeight + p && my <= logoHeight + 48 - p)
-        {
-            if (logoClickCounter >= 0)
-            {
-                indexToDraw = rand.nextInt(BLOCKS_TO_DRAW.length);
-                mc.gameSettings.alphaMenu.toggle();
-                if (mc.gameSettings.alphaMenu.value) logoBlocks = null;
-                logoClickCounter = 0;
-            }
-            else
-            {
-                logoClickCounter++;
+        if (mx >= logoX + p && mx <= logoX + 270 - p && my >= logoHeight + p && my <= logoHeight + 48 - p) {
+            if (this.logoClickCounter >= 0) {
+                this.indexToDraw = rand.nextInt(BLOCKS_TO_DRAW.length);
+                this.mc.gameSettings.alphaMenu.toggle();
+                if (this.mc.gameSettings.alphaMenu.value) this.logoBlocks = null;
+                this.logoClickCounter = 0;
+            } else {
+                this.logoClickCounter++;
             }
         }
-        if (my >= 2 && my <= 12)
-        {
-            if (mx >= 2 && mx <= 40)
-            {
-                showBuildTime = !showBuildTime;
+        if (my >= 2 && my <= 12) {
+            if (mx >= 2 && mx <= 40) {
+                this.showBuildTime = !this.showBuildTime;
             }
         }
     }
 
     @Override
-    public void render(int mx, int my, float partialTick)
-    {
+    public void render(int mx, int my, float partialTick) {
         I18n i18n = I18n.getInstance();
         renderBackground();
         int c = 274;
-        int k = width / 2 - c / 2;
+        int k = this.width / 2 - c / 2;
         byte byte0 = 30;
-        if (!mc.gameSettings.alphaMenu.value)
-        {
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/title/mclogo.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-            drawTexturedModalRect(k, byte0, 0, 0, 274, 50, 1d/274, 1d/50);
-        }
-        else
-        {
+        if (!this.mc.gameSettings.alphaMenu.value) {
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/title/mclogo.png").bind();
+            GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+            drawTexturedModalRect(k, byte0, 0, 0, 274, 50, 1d / 274, 1d / 50);
+        } else {
             drawLogo(partialTick);
         }
 
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/title/snowflake.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/title/snowflake.png").bind();
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
 
         // Render snow particles on title screen on Christmas
-        if(Holidays.getCurrentThemedHoliday() == Holidays.XMAS) {
-            for (Snowflake snowflake : snowflakes) {
+        if (Holidays.getCurrentThemedHoliday() == Holidays.XMAS) {
+            for (Snowflake snowflake : this.snowflakes) {
                 drawTexturedModalRectDouble(snowflake.flakeX, snowflake.flakeY, 0, 4 * snowflake.texIndex, 4, 4, 1d / 4, 1d / 16);
             }
         }
 
-        GL11.glPushMatrix();
-        GL11.glTranslatef(width / 2 + 140, 80F, 0.0F);
-        GL11.glRotatef(-20F, 0.0F, 0.0F, 1.0F);
-        float f1 = 1.8F - MathHelper.abs(MathHelper.sin(((float)(System.currentTimeMillis() % 1000L) / 1000F) * MathHelper.PI * 2.0F) * 0.1F);
-        f1 = (f1 * 100F) / (float)(fontRenderer.stringWidthDouble(splashText) + 32);
-        GL11.glScalef(f1, f1, f1);
-        drawStringCenteredShadow(fontRenderer, splashText, 0, -8, 0xffff00);
-        GL11.glPopMatrix();
-        int versionTextColor = mc.gameSettings.alphaMenu.value || !mc.mainMenuBackground.isEnabled() ? 0x505050 : 0xFFFFFF;
-        if (showBuildTime) {
-            drawStringShadow(fontRenderer, buildTimeString, 2, 2, versionTextColor);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate(this.width / 2 + 140, 80F, 0.0F);
+        GLRenderer.modelM4f().rotateZ(Math.toRadians(-20F));
+        float scalar = 1.8F - MathHelper.abs(MathHelper.sin(((float) (System.currentTimeMillis() % 1000L) / 1000F) * MathHelper.PI * 2.0F) * 0.1F);
+        scalar = (scalar * 100F) / (float) (this.fontRenderer.stringWidthDouble(this.splashText) + 32);
+        GLRenderer.modelM4f().scale(scalar, scalar, scalar);
+        drawStringCenteredShadow(this.fontRenderer, this.splashText, 0, -8, 0xffff00);
+        GLRenderer.popFrame();
+        int versionTextColor = this.mc.gameSettings.alphaMenu.value || !this.mc.mainMenuBackground.isEnabled() ? 0x505050 : 0xFFFFFF;
+        if (this.showBuildTime) {
+            drawStringShadow(this.fontRenderer, this.buildTimeString, 2, 2, versionTextColor);
         } else {
-            drawStringShadow(fontRenderer, "Better than Adventure! " + Minecraft.VERSION, 2, 2, versionTextColor);
+            drawStringShadow(this.fontRenderer, "Better than Adventure! " + Minecraft.VERSION, 2, 2, versionTextColor);
         }
         String disclaimer1 = i18n.translateKey("gui.main_menu.label.disclaimer.1");
-        drawStringShadow(fontRenderer, disclaimer1, width - MathHelper.ceil(fontRenderer.stringWidthDouble(disclaimer1)) - 2, height - 20, 0xffffff);
+        drawStringShadow(this.fontRenderer, disclaimer1, this.width - MathHelper.ceil(this.fontRenderer.stringWidthDouble(disclaimer1)) - 2, this.height - 20, 0xffffff);
         String disclaimer2 = i18n.translateKey("gui.main_menu.label.disclaimer.2");
-        drawStringShadow(fontRenderer, disclaimer2, width - MathHelper.ceil(fontRenderer.stringWidthDouble(disclaimer2)) - 2, height - 10, 0xffffff);
+        drawStringShadow(this.fontRenderer, disclaimer2, this.width - MathHelper.ceil(this.fontRenderer.stringWidthDouble(disclaimer2)) - 2, this.height - 10, 0xffffff);
         super.render(mx, my, partialTick);
     }
 
     private void drawLogo(final float partialTick) {
-        int var3;
-        if(this.logoBlocks == null) {
+        if (this.logoBlocks == null) {
             this.logoBlocks = new LogoBlock[logoBlockLayers[0].length()][logoBlockLayers.length];
 
-            for(int x = 0; x < this.logoBlocks.length; ++x) {
-                for(int y = 0; y < this.logoBlocks[x].length; ++y) {
+            for (int x = 0; x < this.logoBlocks.length; ++x) {
+                for (int y = 0; y < this.logoBlocks[x].length; ++y) {
                     this.logoBlocks[x][y] = new LogoBlock(x, y);
                 }
             }
         }
 
-        GL11.glMatrixMode(GL11.GL_PROJECTION);
-        GL11.glPushMatrix();
-        GL11.glLoadIdentity();
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.WORLD);
         final int delta = this.mc.gameWindow.getWidthPixels() / this.mc.resolution.getScaledWidthScreenCoords();
-        var3 = 120 * delta;
-        GLU.gluPerspective(70.0F, (float)this.mc.gameWindow.getWidthPixels() / (float)var3, 0.05F, 100.0F);
-        GL11.glViewport(0, this.mc.gameWindow.getHeightPixels() - var3, this.mc.gameWindow.getWidthPixels(), var3);
-        GL11.glMatrixMode(GL11.GL_MODELVIEW);
-        GL11.glPushMatrix();
-        GL11.glLoadIdentity();
-        GL11.glDisable(GL11.GL_CULL_FACE);
-        GL11.glCullFace(GL11.GL_BACK);
-        GL11.glDepthMask(true);
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
+        int var3 = 120 * delta;
+        GLRenderer.projectionM4f().identity().perspective(70.0F, (float) this.mc.gameWindow.getWidthPixels() / (float) var3, 0.05F, 100.0F);
+        GLRenderer.viewM4f().identity();
+        GL41.glViewport(0, this.mc.gameWindow.getHeightPixels() - var3, this.mc.gameWindow.getWidthPixels(), var3);
+
+        GLRenderer.modelM4f().identity();
+        GLRenderer.disableState(State.CULL_FACE);
+        GLRenderer.setCullFace(CullFace.BACK);
+        GLRenderer.setDepthMask(true);
+        GLRenderer.enableState(State.DEPTH_TEST);
         Lighting.enableLight(0.5f, 0.16f);
 
-        for(int renderPass = 0; renderPass < 3; ++renderPass) {
-            GL11.glPushMatrix();
-            GL11.glTranslatef(0.4F, 0.6F, -12.0F);
+        for (int renderPass = 0; renderPass < 3; ++renderPass) {
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().translate(0.4F, 0.6F, -12.0F);
             switch (renderPass) {
                 case 0:
-                    GL11.glClear(GL11.GL_DEPTH_BUFFER_BIT);
-                    GL11.glTranslatef(0.0F, -0.4F, 0.0F);
-                    GL11.glScalef(0.98F, 1.0F, 1.0F);
-                    GL11.glEnable(GL11.GL_BLEND);
-                    GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+                    GL41.glClear(GL41.GL_DEPTH_BUFFER_BIT);
+                    GLRenderer.modelM4f().translate(0.0F, -0.4F, 0.0F);
+                    GLRenderer.modelM4f().scale(0.98F, 1.0F, 1.0F);
+                    GLRenderer.enableState(State.BLEND);
+                    GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
                     break;
                 case 1:
-                    GL11.glDisable(GL11.GL_BLEND);
-                    GL11.glClear(GL11.GL_DEPTH_BUFFER_BIT);
+                    GLRenderer.disableState(State.BLEND);
+                    GL41.glClear(GL41.GL_DEPTH_BUFFER_BIT);
                     break;
                 case 2:
-                    GL11.glEnable(GL11.GL_BLEND);
-                    GL11.glBlendFunc(GL11.GL_SRC_COLOR, GL11.GL_ONE);
+                    GLRenderer.enableState(State.BLEND);
+                    GLRenderer.setBlendFunc(BlendFactor.SRC_COLOR, BlendFactor.ONE);
                     break;
             }
 
-            GL11.glScalef(1.0F, -1.0F, 1.0F);
-            GL11.glRotatef(15.0F, 1.0F, 0.0F, 0.0F);
-            GL11.glScalef(0.89F, 1.0F, 0.4F);
-            GL11.glTranslatef((float)(-logoBlockLayers[0].length()) * 0.5F, (float)(-logoBlockLayers.length) * 0.5F, 0.0F);
-            TextureRegistry.blockAtlas.bind();
-            if(renderPass == 0) {
+            GLRenderer.modelM4f().scale(1.0F, -1.0F, 1.0F);
+            GLRenderer.modelM4f().rotateX(Math.toRadians(15.0F));
+            GLRenderer.modelM4f().scale(0.89F, 1.0F, 0.4F);
+            GLRenderer.modelM4f().translate((float) (-logoBlockLayers[0].length()) * 0.5F, (float) (-logoBlockLayers.length) * 0.5F, 0.0F);
+            TextureRegistry.worldAtlas.bind();
+            if (renderPass == 0) {
                 this.mc.textureManager.loadTexture("/title/black.png").bind();
             }
 
-            for(int y = 0; y < logoBlockLayers.length; ++y) {
-                for(int x = 0; x < logoBlockLayers[y].length(); ++x) {
+            for (int y = 0; y < logoBlockLayers.length; ++y) {
+                for (int x = 0; x < logoBlockLayers[y].length(); ++x) {
                     char c = logoBlockLayers[y].charAt(x);
-                    if(c != ' ') {
-                        GL11.glPushMatrix();
+                    if (c != ' ') {
+                        GLRenderer.pushFrame();
                         final LogoBlock logoBlock = this.logoBlocks[x][y];
-                        float z = (float)(logoBlock.prevHeight + (logoBlock.height - logoBlock.prevHeight) * (double)partialTick);
+                        float z = (float) (logoBlock.prevHeight + (logoBlock.height - logoBlock.prevHeight) * (double) partialTick);
                         float scale = 1.0F;
                         float alpha = 1.0F;
-                        if(renderPass == 0) {
+                        if (renderPass == 0) {
                             scale = z * 0.04F + 1.0F;
                             alpha = 1.0F / scale;
                             z = 0.0F;
                         }
 
-                        GL11.glTranslatef(x, y, z);
-                        GL11.glScalef(scale, scale, scale);
-                        BlockModelDispatcher.getInstance().getDispatch(BLOCKS_TO_DRAW[this.indexToDraw]).renderStandalone(Tessellator.instance, 0, 1f, alpha, null);
-                        GL11.glPopMatrix();
+                        GLRenderer.setColor4f(1f, 1f, 1f, alpha);
+                        GLRenderer.modelM4f().translate(x, y, z);
+                        GLRenderer.modelM4f().scale(scale, scale, scale);
+                        BlockModelDispatcher.getInstance().getDispatch(BLOCKS_TO_DRAW[this.indexToDraw]).renderStandalone(GLRenderer.getTessellator(), 0, LightmapHelper.getLightmapCoord(15, 15));
+                        GLRenderer.popFrame();
                     }
                 }
             }
 
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         }
         Lighting.disable();
-
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glMatrixMode(GL11.GL_PROJECTION);
-        GL11.glPopMatrix();
-        GL11.glMatrixMode(GL11.GL_MODELVIEW);
-        GL11.glPopMatrix();
-        GL11.glViewport(0, 0, this.mc.gameWindow.getWidthPixels(), this.mc.gameWindow.getHeightPixels());
-        GL11.glEnable(GL11.GL_CULL_FACE);
+        GLRenderer.popFrame();
+        GL41.glViewport(0, 0, this.mc.gameWindow.getWidthPixels(), this.mc.gameWindow.getHeightPixels());
     }
 
     public static void loadLogo() {
-    	try {
-    		InputStream inputStream = ScreenMainMenu.class.getResourceAsStream("/assets/minecraft/textures/gui/title/retrologo.png");
-    		BufferedImage image = ImageIO.read(inputStream);
-    		inputStream.close();
-
-    		logoBlockLayers = new String[image.getHeight()];
-    		
-    		for(int i=0; i < image.getHeight(); i++) {
-    			StringBuilder builder = new StringBuilder();
-    			
-    			for(int j=0; j < image.getWidth(); j++) {
-    				int rgb = image.getRGB(j, i);
-    				
-    				if(((rgb >> 16) & 0xFF) > 0x80) {
-    					builder.append('*');
-    				}else {
-    					builder.append(' ');
-    				}
-    			}
-    			
-    			logoBlockLayers[i] = builder.toString();
-    		}
-    	}catch (Exception e) {
+        try {
+            InputStream inputStream = ScreenMainMenu.class.getResourceAsStream("/assets/minecraft/textures/gui/title/retrologo.png");
+            BufferedImage image = ImageIO.read(inputStream);
+            inputStream.close();
+
+            logoBlockLayers = new String[image.getHeight()];
+
+            for (int i = 0; i < image.getHeight(); i++) {
+                StringBuilder builder = new StringBuilder();
+
+                for (int j = 0; j < image.getWidth(); j++) {
+                    int rgb = image.getRGB(j, i);
+
+                    if (((rgb >> 16) & 0xFF) > 0x80) {
+                        builder.append('*');
+                    } else {
+                        builder.append(' ');
+                    }
+                }
+
+                logoBlockLayers[i] = builder.toString();
+            }
+        } catch (Exception e) {
             LOGGER.error("Exception while loading retro logo!", e);
-		}
+        }
     }
 
     static class Snowflake {
@@ -513,32 +470,32 @@ public class ScreenMainMenu extends Screen
         public void updateEffects() {
             this.flakeY += this.dropSpeed * 0.3f;
             this.flakeX += this.verticalSpeed * 1.5f;
-            if(this.flakeY > maxHeight) {
+            if (this.flakeY > this.maxHeight) {
                 this.flakeY = 0;
-                this.flakeX = flakeXO;
+                this.flakeX = this.flakeXO;
             }
         }
     }
-    
+
     static class LogoBlock {
-    	
+
         public double height;
         public double prevHeight;
         public double dropSpeed;
 
         public LogoBlock(int x, int y) {
-            this.height = this.prevHeight = (double)(10 + y) + rand.nextDouble() * 32.0D + (double)x;
+            this.height = this.prevHeight = (double) (10 + y) + rand.nextDouble() * 32.0D + (double) x;
         }
 
         public void updateLogoEffects() {
             this.prevHeight = this.height;
-            if(this.height > 0.0D) {
+            if (this.height > 0.0D) {
                 this.dropSpeed -= 0.6D;
             }
 
             this.height += this.dropSpeed;
             this.dropSpeed *= 0.9D;
-            if(this.height < 0.0D) {
+            if (this.height < 0.0D) {
                 this.height = 0.0D;
                 this.dropSpeed = 0.0D;
             }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenPaintingPicker.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenPaintingPicker.java
index 7fc9bbcc5..15313eae4 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenPaintingPicker.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenPaintingPicker.java
@@ -1,146 +1,129 @@
 package net.minecraft.client.gui;
 
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.player.Player;
 import net.minecraft.core.enums.ArtType;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.List;
 
-import static org.lwjgl.opengl.GL11.*;
-
 public class ScreenPaintingPicker
-    extends Screen
-{
+    extends Screen {
     private final Player player;
     private final List<ArtEntry> artEntries = new ArrayList<>();
     private ArtType centerArt = ArtType.Kebab;
     private int tallestSize = 0;
 
-    public ScreenPaintingPicker(Player player)
-    {
+    public ScreenPaintingPicker(Player player) {
         this.player = player;
-        for (ArtType art : ArtType.values){
-            if (art.sizeY > tallestSize) tallestSize = art.sizeY;
+        for (ArtType art : ArtType.values) {
+            if (art.sizeY > this.tallestSize) this.tallestSize = art.sizeY;
         }
     }
 
     @Override
     public void init() {
         super.init();
-        centerArt = player.getSelectedArt();
+        this.centerArt = this.player.getSelectedArt();
         updateArtEntries();
     }
 
     @Override
-    public void render(int mx, int my, float partialTick)
-    {
+    public void render(int mx, int my, float partialTick) {
         super.render(mx, my, partialTick);
 
         float dWheel = Mouse.getDWheel();
-        if (dWheel < 0)
-        {
-            centerArt = ArtType.getNext(centerArt);
+        if (dWheel < 0) {
+            this.centerArt = ArtType.getNext(this.centerArt);
             updateArtEntries();
-        }
-        else if (dWheel > 0)
-        {
-            centerArt = ArtType.getPrevious(centerArt);
+        } else if (dWheel > 0) {
+            this.centerArt = ArtType.getPrevious(this.centerArt);
             updateArtEntries();
         }
 
-        drawPaintings(width, height, mx, my);
+        drawPaintings(this.width, this.height, mx, my);
     }
 
     @Override
-    public void mouseClicked(int mx, int my, int buttonNum)
-    {
+    public void mouseClicked(int mx, int my, int buttonNum) {
         super.mouseClicked(mx, my, buttonNum);
-        int scale = getScale(width, height);
-
-        if (buttonNum == 0)
-        {
-            for (ArtEntry artEntry : artEntries)
-            {
-                if (mx >= artEntry.x && mx <= artEntry.x + artEntry.art.sizeX * scale && my >= artEntry.y && my <= artEntry.y + artEntry.art.sizeY * scale)
-                {
-                    mc.playerController.setPaintingType(artEntry.art);
-                    mc.displayScreen(null);
+        int scale = getScale(this.width, this.height);
+
+        if (buttonNum == 0) {
+            for (ArtEntry artEntry : this.artEntries) {
+                if (mx >= artEntry.x && mx <= artEntry.x + artEntry.art.sizeX * scale && my >= artEntry.y && my <= artEntry.y + artEntry.art.sizeY * scale) {
+                    this.mc.playerController.setPaintingType(artEntry.art);
+                    this.mc.displayScreen(null);
                     break;
                 }
             }
         }
     }
 
-    private void updateArtEntries()
-    {
-        int centerX = width / 2;
-        int centerY = height / 2;
+    private void updateArtEntries() {
+        int centerX = this.width / 2;
+        int centerY = this.height / 2;
 
-        int scale = getScale(width, height);
+        int scale = getScale(this.width, this.height);
         int offsetX = 32 * scale;
         int artGap = 2;
 
-        artEntries.clear();
+        this.artEntries.clear();
 
-        artEntries.add(new ArtEntry(centerArt, centerX - offsetX, centerY - ((centerArt.sizeY  * scale) / 2), 1.0f));
+        this.artEntries.add(new ArtEntry(this.centerArt, centerX - offsetX, centerY - ((this.centerArt.sizeY * scale) / 2), 1.0f));
 
-        ArtType currentArt = ArtType.getNext(centerArt);
+        ArtType currentArt = ArtType.getNext(this.centerArt);
 
-        int dy = ((centerArt.sizeY * scale) / 2 + artGap) + 28;
-        while (currentArt != centerArt)
-        {
+        int dy = ((this.centerArt.sizeY * scale) / 2 + artGap) + 28;
+        while (currentArt != this.centerArt) {
             int pCenterY = dy;
-            float alpha = 1 - (float) pCenterY / (height / 2f);
+            float alpha = 1 - (float) pCenterY / (this.height / 2f);
 
-            artEntries.add(new ArtEntry(currentArt, centerX - offsetX, centerY + dy, alpha * 0.75f));
+            this.artEntries.add(new ArtEntry(currentArt, centerX - offsetX, centerY + dy, alpha * 0.75f));
             dy += ((currentArt.sizeY * scale) + artGap);
             currentArt = ArtType.getNext(currentArt);
         }
 
-        currentArt = ArtType.getPrevious(centerArt);
-        dy = -((centerArt.sizeY  * scale) / 2);
-        while (currentArt != centerArt)
-        {
-            dy -= ((currentArt.sizeY  * scale) + artGap);
+        currentArt = ArtType.getPrevious(this.centerArt);
+        dy = -((this.centerArt.sizeY * scale) / 2);
+        while (currentArt != this.centerArt) {
+            dy -= ((currentArt.sizeY * scale) + artGap);
             int pCenterY = dy + currentArt.sizeY * scale;
-            float alpha = 1 - (float) -pCenterY / (height / 2f);
+            float alpha = 1 - (float) -pCenterY / (this.height / 2f);
 
-            artEntries.add(new ArtEntry(currentArt, centerX - offsetX, centerY + dy, alpha * 0.75f));
+            this.artEntries.add(new ArtEntry(currentArt, centerX - offsetX, centerY + dy, alpha * 0.75f));
             currentArt = ArtType.getPrevious(currentArt);
         }
     }
 
-    private void drawPaintings(int screenWidth, int screenHeight, int mouseX, int mouseY)
-    {
+    private void drawPaintings(int screenWidth, int screenHeight, int mouseX, int mouseY) {
         int centerX = screenWidth / 2;
         int centerY = screenHeight / 2;
 
         int scale = getScale(screenWidth, screenHeight);
         int offsetX = 32 * scale;
 
-        glEnable(GL_TEXTURE_2D);
-
-        drawStringShadow(fontRenderer, centerArt.title, centerX - offsetX, centerY + (centerArt.sizeY / 2) * scale + 4, 0xFFFFFFFF);
-        drawStringShadow(fontRenderer, centerArt.artist, centerX - offsetX, centerY + (centerArt.sizeY / 2) * scale + 16, 0x7F7F7F7F);
+        drawStringShadow(this.fontRenderer, this.centerArt.title, centerX - offsetX, centerY + (this.centerArt.sizeY / 2) * scale + 4, 0xFFFFFFFF);
+        drawStringShadow(this.fontRenderer, this.centerArt.artist, centerX - offsetX, centerY + (this.centerArt.sizeY / 2) * scale + 16, 0x7F7F7F7F);
 
-        glEnable(GL_BLEND);
-        glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
 
-        for (ArtEntry entry : artEntries)
-        {
-            if (entry.alpha > 0)
-            {
-                GL11.glColor4f(1f, 1f, 1f, 1f);
-                if (mouseX > entry.x && mouseX < entry.x + entry.art.sizeX * scale && mouseY > entry.y && mouseY < entry.y + entry.art.sizeY * scale)
-                {
-                    GL11.glDisable(GL11.GL_TEXTURE_2D);
+        for (ArtEntry entry : this.artEntries) {
+            if (entry.alpha > 0) {
+                GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+                if (mouseX > entry.x && mouseX < entry.x + entry.art.sizeX * scale && mouseY > entry.y && mouseY < entry.y + entry.art.sizeY * scale) {
+                    GLRenderer.setShader(Shaders.COLOR);
                     drawRectWidthHeight(entry.x - scale, entry.y - scale, (entry.art.sizeX + 2) * scale, (entry.art.sizeY + 2) * scale, 0xFFFFFFFF);
-                    GL11.glEnable(GL11.GL_TEXTURE_2D);
+                    GLRenderer.setShader(Shaders.INTERFACE);
                     drawPainting(entry.art, entry.x, entry.y, entry.art.sizeX, entry.art.sizeY, 1f);
                 } else {
                     drawPainting(entry.art, entry.x, entry.y, entry.art.sizeX, entry.art.sizeY, entry.alpha);
@@ -148,43 +131,37 @@ public class ScreenPaintingPicker
 
             }
         }
-
-        glDisable(GL_TEXTURE_2D);
-        glDisable(GL_BLEND);
+        GLRenderer.popFrame();
     }
 
-    private void drawPainting(ArtType art, int x, int y, int width, int height, float alpha)
-    {
+    private void drawPainting(ArtType art, int x, int y, int width, int height, float alpha) {
         int scale = getScale(this.width, this.height);
-        drawTexturedIconPainting(x, y, width * scale, height * scale,TextureRegistry.getTexture(art.texture), alpha);
+        drawTexturedIconPainting(x, y, width * scale, height * scale, TextureRegistry.getTexture(art.texture), alpha);
     }
 
-    public void drawTexturedIconPainting(int x, int y, int width, int height, IconCoordinate coordinate, float alpha)
-    {
+    public void drawTexturedIconPainting(int x, int y, int width, int height, IconCoordinate coordinate, float alpha) {
         coordinate.parentAtlas.bind();
-        Tessellator tessellator = Tessellator.instance;
-        GL11.glColor4f(1f, 1f, 1f, alpha);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        GLRenderer.setColor4f(1f, 1f, 1f, alpha);
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(x + 0,      y + height, zLevel, coordinate.getIconUMin(), coordinate.getIconVMax());
-        tessellator.addVertexWithUV(x + width,  y + height, zLevel, coordinate.getIconUMax(), coordinate.getIconVMax());
-        tessellator.addVertexWithUV(x + width,  y + 0,      zLevel, coordinate.getIconUMax(), coordinate.getIconVMin());
-        tessellator.addVertexWithUV(x + 0,      y + 0,      zLevel, coordinate.getIconUMin(), coordinate.getIconVMin());
+        tessellator.addVertexWithUV(x, y + height, this.zLevel, coordinate.getIconUMin(), coordinate.getIconVMax());
+        tessellator.addVertexWithUV(x + width, y + height, this.zLevel, coordinate.getIconUMax(), coordinate.getIconVMax());
+        tessellator.addVertexWithUV(x + width, y, this.zLevel, coordinate.getIconUMax(), coordinate.getIconVMin());
+        tessellator.addVertexWithUV(x, y, this.zLevel, coordinate.getIconUMin(), coordinate.getIconVMin());
         tessellator.draw();
     }
-    public int getScale(int width, int height)
-    {
-        return Math.min((int)((height * 0.9f)/tallestSize), mc.resolution.getScale());
+
+    public int getScale(int width, int height) {
+        return Math.min((int) ((height * 0.9f) / this.tallestSize), this.mc.resolution.getScale());
     }
 
-    private static final class ArtEntry
-    {
+    private static final class ArtEntry {
         public final ArtType art;
         public final int x;
         public final int y;
         public final float alpha;
 
-        public ArtEntry(ArtType art, int x, int y, float alpha)
-        {
+        public ArtEntry(ArtType art, int x, int y, float alpha) {
             this.art = art;
             this.x = x;
             this.y = y;
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenPhotoMode.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenPhotoMode.java
index 3157f9b9c..3f70c7f8b 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenPhotoMode.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenPhotoMode.java
@@ -2,6 +2,7 @@ package net.minecraft.client.gui;
 
 import net.minecraft.client.gui.modelviewer.elements.ListenerButtonElement;
 import net.minecraft.client.input.controller.ControllerInput;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.util.helper.FileOpener;
 import net.minecraft.core.Global;
 import net.minecraft.core.util.helper.MathHelper;
@@ -10,20 +11,18 @@ import net.minecraft.core.world.season.Seasons;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.client.render.Renderer;
 import net.minecraft.client.render.shader.PhotoModeRenderer;
-import net.minecraft.client.render.shader.Shaders;
 import net.minecraft.client.util.helper.ScreenShot;
+import org.lwjgl.opengl.GL41;
 
 import java.io.File;
 import java.util.Locale;
 
-public class ScreenPhotoMode extends Screen
-{
+public class ScreenPhotoMode extends Screen {
     private ButtonElement buttonRotateLeft;
     private ButtonElement buttonRotateRight;
     private ButtonElement buttonCenterScreen;
@@ -75,439 +74,353 @@ public class ScreenPhotoMode extends Screen
     public float intensityValue = 1.0f;
 
     protected boolean shouldScreenshot = false;
-    
+
     protected PhotoModeRenderer photoModeRenderer;
-    
+
     public Renderer previousRenderer;
-    
+
     protected boolean showHelpText = true;
 
-    public ScreenPhotoMode()
-    {
+    public ScreenPhotoMode() {
         Minecraft mc = Minecraft.getMinecraft();
 
-        if(Shaders.enableShaders) {
-            photoModeRenderer = new PhotoModeRenderer(mc, this);
-        }
-        
+        this.photoModeRenderer = new PhotoModeRenderer(mc, this);
+
         this.previousRenderer = mc.renderer;
         mc.currentWorld.updateSeasonAndLight();
-        originalTOD = mc.currentWorld.getWorldTime();
+        this.originalTOD = mc.currentWorld.getWorldTime();
     }
 
-    public float getRotation(float partialTick)
-    {
-        return lastIRotation + (iRotation - lastIRotation) * partialTick;
+    public float getRotation(float partialTick) {
+        return this.lastIRotation + (this.iRotation - this.lastIRotation) * partialTick;
     }
 
-    public float getZoom(float partialTick)
-    {
-        return lastIZoom + (iZoom - lastIZoom) * partialTick;
+    public float getZoom(float partialTick) {
+        return this.lastIZoom + (this.iZoom - this.lastIZoom) * partialTick;
     }
 
-    public float getTilt(float partialTick)
-    {
-        return lastITilt + (iTilt - lastITilt) * partialTick;
+    public float getTilt(float partialTick) {
+        return this.lastITilt + (this.iTilt - this.lastITilt) * partialTick;
     }
 
-    public float getFog(float partialTick)
-    {
-        return lastIFog + (iFog - lastIFog) * partialTick;
+    public float getFog(float partialTick) {
+        return this.lastIFog + (this.iFog - this.lastIFog) * partialTick;
     }
 
-    public float getPanX(float partialTick)
-    {
-        return lastIPanX + (iPanX - lastIPanX) * partialTick;
+    public float getPanX(float partialTick) {
+        return this.lastIPanX + (this.iPanX - this.lastIPanX) * partialTick;
     }
 
-    public float getPanY(float partialTick)
-    {
-        return lastIPanY + (iPanY - lastIPanY) * partialTick;
+    public float getPanY(float partialTick) {
+        return this.lastIPanY + (this.iPanY - this.lastIPanY) * partialTick;
     }
 
     @Override
-    public void init()
-    {
+    public void init() {
         super.init();
 
         I18n i18n = I18n.getInstance();
 
-        buttonExit = new ButtonElement(5, 0, 0, 20, 20, "X");
+        this.buttonExit = new ButtonElement(5, 0, 0, 20, 20, "X");
 
-        buttonRotateLeft = new ButtonElement(0, width / 2 - 59 - 2 - 20, height - 20, 20, 20, "<");
-        buttonRotateRight = new ButtonElement(1, width / 2 + 59 + 2 + 1, height - 20, 20, 20, ">");
-        buttonTakeScreenshot = new ButtonElement(4, width / 2 - 59, height - 20, 98, 20, i18n.translateKey("gui.photo_mode.button.take_screenshot"));
-        buttonOpenScreenshotFolder = (ListenerButtonElement) new ListenerButtonElement(30, buttonTakeScreenshot.getWidth() + buttonTakeScreenshot.getX() + 1, buttonTakeScreenshot.getY(), 20, 20, "")
+        this.buttonRotateLeft = new ButtonElement(0, this.width / 2 - 59 - 2 - 20, this.height - 20, 20, 20, "<");
+        this.buttonRotateRight = new ButtonElement(1, this.width / 2 + 59 + 2 + 1, this.height - 20, 20, 20, ">");
+        this.buttonTakeScreenshot = new ButtonElement(4, this.width / 2 - 59, this.height - 20, 98, 20, i18n.translateKey("gui.photo_mode.button.take_screenshot"));
+        this.buttonOpenScreenshotFolder = (ListenerButtonElement) new ListenerButtonElement(30, this.buttonTakeScreenshot.getWidth() + this.buttonTakeScreenshot.getX() + 1, this.buttonTakeScreenshot.getY(), 20, 20, "")
             .setTextures("minecraft:gui/misc/button_folder", "minecraft:gui/misc/button_folder_highlighted", "minecraft:gui/misc/button_folder");
-        buttonOpenScreenshotFolder.setActionListener(() -> {
-            File f = new File(mc.getMinecraftDir(), "screenshots");
+        this.buttonOpenScreenshotFolder.setActionListener(() -> {
+            File f = new File(this.mc.getMinecraftDir(), "screenshots");
             f.mkdirs();
             FileOpener.open(f);
         });
 
-        buttonCenterScreen = new ButtonElement(10, width - 120, 0, 120, 20, i18n.translateKey("gui.photo_mode.button.center_camera"));
-        buttonShowPlayer = new ButtonElement(11, width - 120, 0, 120, 20, "");
-        sliderTimeOfDay = new SliderElement(2, width - 120, 0, 120, 20, "", 0.0f);
-        buttonSeason = new ButtonElement(3, width - 120, 0, 120, 20, "");
-        sliderFog = new SliderElement(6, width - 120, 0, 120, 20, "", 1.0f);
-        sliderTilt = new SliderElement(7, width - 120, 0, 120, 20, "", 30f / 90f);
-        if(Shaders.enableShaders) {
-            buttonShaders = new ButtonElement(8, width - 120, 0, 120, 20, "");
-            sliderIntensity = new SliderElement(9, width - 120, 0, 120, 20, "", intensityValue);
-            
-            if (photoModeRenderer.getActiveShader() == null) {
-                sliderIntensity.enabled = false;
-            }
-        }
+        this.buttonCenterScreen = new ButtonElement(10, this.width - 120, 0, 120, 20, i18n.translateKey("gui.photo_mode.button.center_camera"));
+        this.buttonShowPlayer = new ButtonElement(11, this.width - 120, 0, 120, 20, "");
+        this.sliderTimeOfDay = new SliderElement(2, this.width - 120, 0, 120, 20, "", 0.0f);
+        this.buttonSeason = new ButtonElement(3, this.width - 120, 0, 120, 20, "");
+        this.sliderFog = new SliderElement(6, this.width - 120, 0, 120, 20, "", 0.5f);
+        this.sliderTilt = new SliderElement(7, this.width - 120, 0, 120, 20, "", 30f / 90f);
+        this.buttonShaders = new ButtonElement(8, this.width - 120, 0, 120, 20, "");
+        this.sliderIntensity = new SliderElement(9, this.width - 120, 0, 120, 20, "", this.intensityValue);
 
-        buttons.add(buttonCenterScreen);
-        buttons.add(buttonShowPlayer);
-        buttons.add(sliderTilt);
-        
-        if(Shaders.enableShaders) {
-            mc.setRenderer(photoModeRenderer);
+        if (this.photoModeRenderer.getActiveShader() == null) {
+            this.sliderIntensity.enabled = false;
         }
 
-        if (!mc.currentWorld.isClientSide) {
-            buttons.add(sliderTimeOfDay);
-            buttons.add(sliderFog);
-            buttons.add(buttonSeason);
-        }
-        
-        if(Shaders.enableShaders) {
-            buttons.add(buttonShaders);
-            buttons.add(sliderIntensity);
+        this.buttons.add(this.buttonCenterScreen);
+        this.buttons.add(this.buttonShowPlayer);
+        this.buttons.add(this.sliderTilt);
+
+        this.mc.setRenderer(this.photoModeRenderer);
+
+        if (!this.mc.currentWorld.isClientSide) {
+            this.buttons.add(this.sliderTimeOfDay);
+            this.buttons.add(this.sliderFog);
+            this.buttons.add(this.buttonSeason);
         }
 
-        int i=0;
-        for(ButtonElement button : buttons) {
+        this.buttons.add(this.buttonShaders);
+        this.buttons.add(this.sliderIntensity);
+
+        int i = 0;
+        for (ButtonElement button : this.buttons) {
             button.yPosition = i++ * 21;
         }
 
-        buttons.add(buttonRotateLeft);
-        buttons.add(buttonRotateRight);
-        buttons.add(buttonTakeScreenshot);
-        buttons.add(buttonOpenScreenshotFolder);
-        buttons.add(buttonExit);
+        this.buttons.add(this.buttonRotateLeft);
+        this.buttons.add(this.buttonRotateRight);
+        this.buttons.add(this.buttonTakeScreenshot);
+        this.buttons.add(this.buttonOpenScreenshotFolder);
+        this.buttons.add(this.buttonExit);
 
-        if (desiredTOD == -1)
-        {
-            desiredTOD = originalTOD % Global.DAY_LENGTH_TICKS;
-        }
-        else
-        {
-            sliderTimeOfDay.sliderValue = desiredTOD / (float) Global.DAY_LENGTH_TICKS;
+        if (this.desiredTOD == -1) {
+            this.desiredTOD = this.originalTOD % Global.DAY_LENGTH_TICKS;
+        } else {
+            this.sliderTimeOfDay.sliderValue = this.desiredTOD / (float) Global.DAY_LENGTH_TICKS;
         }
 
-        if (desiredDay == -1) desiredDay = originalTOD / Global.DAY_LENGTH_TICKS;
+        if (this.desiredDay == -1) this.desiredDay = this.originalTOD / Global.DAY_LENGTH_TICKS;
 
         updateButtonsText();
     }
 
     @Override
-    public void removed()
-    {
-        mc.currentWorld.setWorldTimeUpdateTicks(originalTOD);
-        
-        if(Shaders.enableShaders) {
-            mc.setRenderer(previousRenderer);
-        }
+    public void removed() {
+        this.mc.currentWorld.setWorldTimeUpdateTicks(this.originalTOD);
 
-        mc.currentWorld.updateSeasonAndLight();
+        this.mc.setRenderer(this.previousRenderer);
+
+        this.mc.currentWorld.updateSeasonAndLight();
     }
 
     @Override
-    protected void buttonClicked(@NotNull ButtonElement button)
-    {
-        if (button == buttonRotateLeft)
-        {
-            iRotationGoal += 1;
-            iRotationGoal = (int) iRotationGoal;
-        }
-        else if (button == buttonRotateRight)
-        {
-            iRotationGoal -= 1;
-            iRotationGoal = (int) iRotationGoal;
-        }
-        else if (button == buttonSeason)
-        {
-            desiredSeason++;
-            if (desiredSeason > 3) desiredSeason = -1;
-
-            if (desiredSeason == -1)
-            {
-                desiredDay = originalTOD / Global.DAY_LENGTH_TICKS;
-            }
-            else
-            {
-                desiredDay = (long) Global.DAY_LENGTH_TICKS * 7 * desiredSeason + Global.DAY_LENGTH_TICKS * 3L;
+    protected void buttonClicked(@NotNull ButtonElement button) {
+        if (button == this.buttonRotateLeft) {
+            this.iRotationGoal += 1;
+            this.iRotationGoal = (int) this.iRotationGoal;
+        } else if (button == this.buttonRotateRight) {
+            this.iRotationGoal -= 1;
+            this.iRotationGoal = (int) this.iRotationGoal;
+        } else if (button == this.buttonSeason) {
+            this.desiredSeason++;
+            if (this.desiredSeason > 3) this.desiredSeason = -1;
+
+            if (this.desiredSeason == -1) {
+                this.desiredDay = this.originalTOD / Global.DAY_LENGTH_TICKS;
+            } else {
+                this.desiredDay = (long) Global.DAY_LENGTH_TICKS * 7 * this.desiredSeason + Global.DAY_LENGTH_TICKS * 3L;
             }
 
-            mc.currentWorld.setWorldTimeUpdateTicks(desiredDay + desiredTOD);
-            mc.currentWorld.updateSeasonAndLight();
-        }
-        else if (button == buttonTakeScreenshot)
-        {
-            shouldScreenshot = true;
-        }
-        else if (button == buttonExit)
-        {
-            mc.displayScreen(null);
-        }
-        else if (button == buttonShaders)
-        {
+            this.mc.currentWorld.setWorldTimeUpdateTicks(this.desiredDay + this.desiredTOD);
+            this.mc.currentWorld.updateSeasonAndLight();
+        } else if (button == this.buttonTakeScreenshot) {
+            this.shouldScreenshot = true;
+        } else if (button == this.buttonExit) {
+            this.mc.displayScreen(null);
+        } else if (button == this.buttonShaders) {
             boolean ctrl = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
-            if (ctrl)
-            {
-                photoModeRenderer.first();
-            }
-            else
-            {
-                photoModeRenderer.next();
+            if (ctrl) {
+                this.photoModeRenderer.first();
+            } else {
+                this.photoModeRenderer.next();
             }
-            sliderIntensity.enabled = photoModeRenderer.getActiveShader() != null;
-        }
-        else if (button == buttonCenterScreen)
-        {
-            iPanXGoal = 0;
-            iPanYGoal = 0;
-        }
-        else if (button == buttonShowPlayer)
-        {
-            showPlayer = !showPlayer;
+            this.sliderIntensity.enabled = this.photoModeRenderer.getActiveShader() != null;
+        } else if (button == this.buttonCenterScreen) {
+            this.iPanXGoal = 0;
+            this.iPanYGoal = 0;
+        } else if (button == this.buttonShowPlayer) {
+            this.showPlayer = !this.showPlayer;
         }
         updateButtonsText();
     }
 
     @Override
-    public void mouseClicked(int mx, int my, int buttonNum)
-    {
+    public void mouseClicked(int mx, int my, int buttonNum) {
         super.mouseClicked(mx, my, buttonNum);
 
-        if (!isMouseDown && clickedButton == null)
-        {
-            showHelpText = false;
-            isMouseDown = true;
-            mouseDownX = mx;
-            mouseDownY = my;
-            lastEndPanX = iPanX;
-            lastEndPanY = iPanY;
-            lastEndRotation = iRotation;
+        if (!this.isMouseDown && this.clickedButton == null) {
+            this.showHelpText = false;
+            this.isMouseDown = true;
+            this.mouseDownX = mx;
+            this.mouseDownY = my;
+            this.lastEndPanX = this.iPanX;
+            this.lastEndPanY = this.iPanY;
+            this.lastEndRotation = this.iRotation;
             this.mouseButton = buttonNum;
         }
     }
 
     @Override
-    public void mouseReleased(int mx, int my, int buttonNum)
-    {
+    public void mouseReleased(int mx, int my, int buttonNum) {
         super.mouseReleased(mx, my, buttonNum);
 
-        if (isMouseDown && buttonNum != -1)
-        {
-            isMouseDown = false;
-        }
-        else if (isMouseDown)
-        {
-            if (this.mouseButton == 0)
-            {
-                float div = (float)Math.pow(2, iZoom) / 3;
-                iPanXGoal = lastEndPanX + (mx - mouseDownX) / div;
-                iPanYGoal = lastEndPanY + (my - mouseDownY) / div;
-            }
-            else
-            {
-                iRotationGoal = lastEndRotation + (mx - mouseDownX) / 128f;
+        if (this.isMouseDown && buttonNum != -1) {
+            this.isMouseDown = false;
+        } else if (this.isMouseDown) {
+            if (this.mouseButton == 0) {
+                float div = (float) Math.pow(2, this.iZoom) / 3;
+                this.iPanXGoal = this.lastEndPanX + (mx - this.mouseDownX) / div;
+                this.iPanYGoal = this.lastEndPanY + (my - this.mouseDownY) / div;
+            } else {
+                this.iRotationGoal = this.lastEndRotation + (mx - this.mouseDownX) / 128f;
             }
         }
     }
 
     protected long lastUpdateTime = 0;
+
     @Override
-    public void render(int mx, int my, float partialTick)
-    {
-        GL11.glViewport(0, 0, mc.gameWindow.getWidthPixels(), mc.gameWindow.getHeightPixels());
-        GL11.glMatrixMode(GL11.GL_PROJECTION);
-        GL11.glLoadIdentity();
-        GL11.glMatrixMode(GL11.GL_MODELVIEW);
-        GL11.glLoadIdentity();
-        GL11.glClear(256);
-        GL11.glMatrixMode(GL11.GL_PROJECTION);
-        GL11.glLoadIdentity();
-        GL11.glOrtho(0.0D, mc.resolution.getExactScaledWidthScreenCoords(), mc.resolution.getExactScaledHeightScreenCoords(), 0.0D, 1000D, 3000D);
-        GL11.glMatrixMode(GL11.GL_MODELVIEW);
-        GL11.glLoadIdentity();
-        GL11.glTranslatef(0.0F, 0.0F, -2000F);
-
-        if (mc.controllerInput != null) {
-            if (mc.controllerInput.buttonLeftShoulder.isPressed()) {
-                float div = (float)Math.pow(2, iZoom) / 3;
-                iPanXGoal -= mc.controllerInput.joyRight.getX() / div;
-                iPanYGoal -= mc.controllerInput.joyRight.getY() / div;
-            } else if (mc.controllerInput.buttonLeftTrigger.isPressed()) {
-                iTiltGoal -= mc.controllerInput.joyRight.getY() / 2f;
-                iTiltGoal = MathHelper.clamp(iTiltGoal, 0.0f, 90.0f);
+    public void render(int mx, int my, float partialTick) {
+        GL41.glViewport(0, 0, this.mc.gameWindow.getWidthPixels(), this.mc.gameWindow.getHeightPixels());
+        GLRenderer.projectionM4f().identity().ortho(0.0f, (float) this.mc.resolution.getExactScaledWidthScreenCoords(), (float) this.mc.resolution.getExactScaledHeightScreenCoords(), 0.0f, 1000f, 3000f);
+        GLRenderer.viewM4f().identity();
+        GLRenderer.modelM4f().identity();
+        GL41.glClear(GL41.GL_DEPTH_BUFFER_BIT);
+        GLRenderer.modelM4f().translate(0.0F, 0.0F, -2000F);
+
+        if (this.mc.controllerInput != null) {
+            if (this.mc.controllerInput.buttonLeftShoulder.isPressed()) {
+                float div = (float) Math.pow(2, this.iZoom) / 3;
+                this.iPanXGoal -= this.mc.controllerInput.joyRight.getX() / div;
+                this.iPanYGoal -= this.mc.controllerInput.joyRight.getY() / div;
+            } else if (this.mc.controllerInput.buttonLeftTrigger.isPressed()) {
+                this.iTiltGoal -= this.mc.controllerInput.joyRight.getY() / 2f;
+                this.iTiltGoal = MathHelper.clamp(this.iTiltGoal, 0.0f, 90.0f);
                 updateButtonsText();
             } else {
-                iRotationGoal -= mc.controllerInput.joyRight.getX() / 64f;
-                iZoomGoal -= mc.controllerInput.joyRight.getY() / 128f;
+                this.iRotationGoal -= this.mc.controllerInput.joyRight.getX() / 64f;
+                this.iZoomGoal -= this.mc.controllerInput.joyRight.getY() / 128f;
             }
         }
 
         long currentTime = System.currentTimeMillis();
-        if (currentTime > lastUpdateTime + 5)
-        {
-            lastIZoom = iZoom;
-            if (iZoom != iZoomGoal)
-            {
-                iZoom += (iZoomGoal - iZoom) * 0.08f;
-                if (Math.abs(iZoom - iZoomGoal) < 0.0005f) iZoom = iZoomGoal;
+        if (currentTime > this.lastUpdateTime + 5) {
+            this.lastIZoom = this.iZoom;
+            if (this.iZoom != this.iZoomGoal) {
+                this.iZoom += (this.iZoomGoal - this.iZoom) * 0.08f;
+                if (Math.abs(this.iZoom - this.iZoomGoal) < 0.0005f) this.iZoom = this.iZoomGoal;
             }
 
-            lastIRotation = iRotation;
-            if (iRotation != iRotationGoal)
-            {
-                iRotation += (iRotationGoal - iRotation) * 0.08f;
-                if (Math.abs(iRotation - iRotationGoal) < 0.0005f) iRotation = iRotationGoal;
+            this.lastIRotation = this.iRotation;
+            if (this.iRotation != this.iRotationGoal) {
+                this.iRotation += (this.iRotationGoal - this.iRotation) * 0.08f;
+                if (Math.abs(this.iRotation - this.iRotationGoal) < 0.0005f) this.iRotation = this.iRotationGoal;
             }
 
-            lastITilt = iTilt;
-            if (iTilt != iTiltGoal)
-            {
-                iTilt += (iTiltGoal - iTilt) * 0.08f;
-                if (Math.abs(iTilt - iTiltGoal) < 0.01f) iTilt = iTiltGoal;
+            this.lastITilt = this.iTilt;
+            if (this.iTilt != this.iTiltGoal) {
+                this.iTilt += (this.iTiltGoal - this.iTilt) * 0.08f;
+                if (Math.abs(this.iTilt - this.iTiltGoal) < 0.01f) this.iTilt = this.iTiltGoal;
             }
 
-            lastIFog = iFog;
-            if (iFog != iFogGoal)
-            {
-                iFog += (iFogGoal - iFog) * 0.08f;
-                if (Math.abs(iFog - iFogGoal) < 0.00005f) iFog = iFogGoal;
+            this.lastIFog = this.iFog;
+            if (this.iFog != this.iFogGoal) {
+                this.iFog += (this.iFogGoal - this.iFog) * 0.08f;
+                if (Math.abs(this.iFog - this.iFogGoal) < 0.00005f) this.iFog = this.iFogGoal;
             }
 
-            lastIPanX = iPanX;
-            if (iPanX != iPanXGoal)
-            {
-                iPanX += (iPanXGoal - iPanX) * 0.4f;
-                if (Math.abs(iPanX - iPanXGoal) < 0.01f) iPanX = iPanXGoal;
+            this.lastIPanX = this.iPanX;
+            if (this.iPanX != this.iPanXGoal) {
+                this.iPanX += (this.iPanXGoal - this.iPanX) * 0.4f;
+                if (Math.abs(this.iPanX - this.iPanXGoal) < 0.01f) this.iPanX = this.iPanXGoal;
             }
 
-            lastIPanY = iPanY;
-            if (iPanY != iPanYGoal)
-            {
-                iPanY += (iPanYGoal - iPanY) * 0.4f;
-                if (Math.abs(iPanY - iPanYGoal) < 0.01f) iPanY = iPanYGoal;
+            this.lastIPanY = this.iPanY;
+            if (this.iPanY != this.iPanYGoal) {
+                this.iPanY += (this.iPanYGoal - this.iPanY) * 0.4f;
+                if (Math.abs(this.iPanY - this.iPanYGoal) < 0.01f) this.iPanY = this.iPanYGoal;
             }
-            lastUpdateTime = currentTime;
+            this.lastUpdateTime = currentTime;
         }
 
-        buttonCenterScreen.enabled = (iPanX != 0 || iPanY != 0) && !(iPanXGoal == 0 && iPanYGoal == 0);
+        this.buttonCenterScreen.enabled = (this.iPanX != 0 || this.iPanY != 0) && !(this.iPanXGoal == 0 && this.iPanYGoal == 0);
 
-        if (!shouldScreenshot)
-        {
+        if (!this.shouldScreenshot) {
             super.render(mx, my, partialTick);
-        }
-        else
-        {
-            ScreenShot.saveScreenshot(Global.accessor.getMinecraftDir(), mc.gameWindow.getWidthPixels(), mc.gameWindow.getHeightPixels());
-            shouldScreenshot = false;
+        } else {
+            ScreenShot.saveScreenshot(Global.accessor.getMinecraftDir(), this.mc.gameWindow.getWidthPixels(), this.mc.gameWindow.getHeightPixels());
+            this.shouldScreenshot = false;
         }
         scroll(Mouse.getDWheel());
 
-        if (sliderTimeOfDay.dragging)
-        {
-            long sliderTOD = (long)(sliderTimeOfDay.sliderValue * Global.DAY_LENGTH_TICKS);
-            if (sliderTimeOfDay.sliderValue == 0.0f)
-            {
-                desiredTOD = originalTOD % Global.DAY_LENGTH_TICKS;
-            }
-            else
-            {
-                desiredTOD = sliderTOD;
+        if (this.sliderTimeOfDay.dragging) {
+            long sliderTOD = (long) (this.sliderTimeOfDay.sliderValue * Global.DAY_LENGTH_TICKS);
+            if (this.sliderTimeOfDay.sliderValue == 0.0f) {
+                this.desiredTOD = this.originalTOD % Global.DAY_LENGTH_TICKS;
+            } else {
+                this.desiredTOD = sliderTOD;
             }
 
-            mc.currentWorld.setWorldTimeUpdateTicks(desiredDay + desiredTOD);
-            mc.currentWorld.updateSeasonAndLight();
+            this.mc.currentWorld.setWorldTimeUpdateTicks(this.desiredDay + this.desiredTOD);
+            this.mc.currentWorld.updateSeasonAndLight();
 
             updateButtonsText();
         }
-        if (sliderTilt.dragging)
-        {
-            iTiltGoal = (float) (int)(sliderTilt.sliderValue * 90.0f);
+        if (this.sliderTilt.dragging) {
+            this.iTiltGoal = (float) (int) (this.sliderTilt.sliderValue * 90.0f);
 
             updateButtonsText();
         }
-        if (sliderFog.dragging)
-        {
+        if (this.sliderFog.dragging) {
             // y=2^(8x - 8)
-            iFogGoal = (float)Math.pow(2, (8 * sliderFog.sliderValue) - 8);
+            this.iFogGoal = (float) Math.pow(2, (8 * this.sliderFog.sliderValue * 2) - 8);
             updateButtonsText();
         }
-        if(Shaders.enableShaders) {
-            if (sliderIntensity.dragging)
-            {
-                intensityValue = (float) sliderIntensity.sliderValue;
-                updateButtonsText();
-            }
+        if (this.sliderIntensity.dragging) {
+            this.intensityValue = (float) this.sliderIntensity.sliderValue;
+            updateButtonsText();
         }
-        
-        if (showHelpText) drawStringCenteredShadow(fontRenderer, I18n.getInstance().translateKey("gui.photo_mode.label.mouse_hint"), width / 2, height - 36, 0xFFFFFF);
+
+        if (this.showHelpText)
+            drawStringCenteredShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.photo_mode.label.mouse_hint"), this.width / 2, this.height - 36, 0xFFFFFF);
     }
 
-    private void updateButtonsText()
-    {
+    private void updateButtonsText() {
         I18n i18n = I18n.getInstance();
-        if(buttonSeason != null) {
-            Season[] seasons = new Season[] {Seasons.OVERWORLD_SPRING, Seasons.OVERWORLD_SUMMER, Seasons.OVERWORLD_FALL, Seasons.OVERWORLD_WINTER };
+        if (this.buttonSeason != null) {
+            Season[] seasons = new Season[]{Seasons.OVERWORLD_SPRING, Seasons.OVERWORLD_SUMMER, Seasons.OVERWORLD_FALL, Seasons.OVERWORLD_WINTER};
             String seasonName = i18n.translateKey("gui.photo_mode.button.season.default");
-            if (desiredSeason >= 0) {
-                seasonName = seasons[desiredSeason].getTranslatedName().toUpperCase(Locale.ROOT);
+            if (this.desiredSeason >= 0) {
+                seasonName = seasons[this.desiredSeason].getTranslatedName().toUpperCase(Locale.ROOT);
             }
-            buttonSeason.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.season", seasonName);
+            this.buttonSeason.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.season", seasonName);
         }
 
         // Update time of day slider
         String timeOfDay = i18n.translateKey("gui.photo_mode.button.time_of_day.default");
-        if (sliderTimeOfDay.sliderValue != 0.0f)
-        {
-            timeOfDay = String.valueOf((long)(sliderTimeOfDay.sliderValue * Global.DAY_LENGTH_TICKS));
+        if (this.sliderTimeOfDay.sliderValue != 0.0f) {
+            timeOfDay = String.valueOf((long) (this.sliderTimeOfDay.sliderValue * Global.DAY_LENGTH_TICKS));
         }
-        sliderTimeOfDay.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.time_of_day", timeOfDay);
+        this.sliderTimeOfDay.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.time_of_day", timeOfDay);
 
         // Update fog slider
-        sliderFog.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.fog", (int)(sliderFog.sliderValue * 100) + "%");
+        this.sliderFog.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.fog", (int) (this.sliderFog.sliderValue * 200) + "%");
 
         // Update tilt slider
         String tilt = i18n.translateKey("gui.photo_mode.button.tilt.default");
-        if ((int)(sliderTilt.sliderValue * 90.0f) != 30)
-        {
-            tilt = (int)(sliderTilt.sliderValue * 90.0f) + " degrees";
+        if ((int) (this.sliderTilt.sliderValue * 90.0f) != 30) {
+            tilt = (int) (this.sliderTilt.sliderValue * 90.0f) + " degrees";
         }
-        sliderTilt.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.tilt", tilt);
+        this.sliderTilt.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.tilt", tilt);
 
         // Update shader button
-        if(Shaders.enableShaders) {
-            String activeShader = photoModeRenderer.getActiveShader();
-            if (activeShader == null) activeShader = i18n.translateKey("gui.photo_mode.button.shader.none");
-            activeShader = activeShader.toUpperCase(Locale.ROOT);
-            buttonShaders.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.shader", activeShader);
-            
-            // Update intensity slider
-            sliderIntensity.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.intensity", (int)(sliderIntensity.sliderValue * 100) + "%");
-        }
+        String activeShader = this.photoModeRenderer.getActiveShader();
+        if (activeShader == null) activeShader = i18n.translateKey("gui.photo_mode.button.shader.none");
+        activeShader = activeShader.toUpperCase(Locale.ROOT);
+        this.buttonShaders.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.shader", activeShader);
+
+        // Update intensity slider
+        this.sliderIntensity.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.intensity", (int) (this.sliderIntensity.sliderValue * 100) + "%");
 
         // Update show player button
-        buttonShowPlayer.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.show_player", showPlayer ? i18n.translateKey("gui.photo_mode.button.show_player.on") : i18n.translateKey("gui.photo_mode.button.show_player.off"));
+        this.buttonShowPlayer.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.show_player", this.showPlayer ? i18n.translateKey("gui.photo_mode.button.show_player.on") : i18n.translateKey("gui.photo_mode.button.show_player.off"));
     }
 
-    public void scroll(int i)
-    {
-        if (i < 0)
-        {
-            iZoomGoal -= 0.25f;
-        }
-        else if (i > 0)
-        {
-            iZoomGoal += 0.25f;
+    public void scroll(int i) {
+        if (i < 0) {
+            this.iZoomGoal -= 0.25f;
+        } else if (i > 0) {
+            this.iZoomGoal += 0.25f;
         }
     }
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenSelectWorld.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenSelectWorld.java
index e4821053f..2f3353b6e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenSelectWorld.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenSelectWorld.java
@@ -3,8 +3,7 @@ package net.minecraft.client.gui;
 import com.mojang.nbt.tags.CompoundTag;
 import net.minecraft.client.gui.popup.PopupScreen;
 import net.minecraft.client.gui.popup.PopupBuilder;
-import net.minecraft.client.gui.worldsettings.ScreenWorldSettings;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.Global;
 import net.minecraft.core.net.command.TextFormatting;
 import net.minecraft.core.player.gamemode.Gamemode;
@@ -29,8 +28,7 @@ import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
 
-public class ScreenSelectWorld extends Screen
-{
+public class ScreenSelectWorld extends Screen {
     private final DateFormat dateFormatter = new SimpleDateFormat();
     protected String stringTitle;
     private boolean selected;
@@ -45,27 +43,24 @@ public class ScreenSelectWorld extends Screen
     private ButtonElement buttonSelect;
     private ButtonElement buttonDelete;
 
-    public ScreenSelectWorld(Screen parent)
-    {
+    public ScreenSelectWorld(Screen parent) {
         super(parent);
-        stringTitle = "Select world";
-        selected = false;
-        selectedWorld = -1;
+        this.stringTitle = "Select world";
+        this.selected = false;
+        this.selectedWorld = -1;
     }
 
     @Override
-    public void init()
-    {
+    public void init() {
         I18n i18n = I18n.getInstance();
-        stringTitle = i18n.translateKey("gui.select_world.label.title");
-        stringWorld = i18n.translateKey("gui.select_world.label.world");
-        stringConversion = i18n.translateKey("gui.select_world.label.must_be_converted");
-        if (Global.DISABLE_OLD_WORLDS)
-        {
-            stringConversion = i18n.translateKey("gui.select_world.label.outdated");
+        this.stringTitle = i18n.translateKey("gui.select_world.label.title");
+        this.stringWorld = i18n.translateKey("gui.select_world.label.world");
+        this.stringConversion = i18n.translateKey("gui.select_world.label.must_be_converted");
+        if (Global.DISABLE_OLD_WORLDS) {
+            this.stringConversion = i18n.translateKey("gui.select_world.label.outdated");
         }
         loadSaves();
-        worldSlotContainer = new WorldSlot();
+        this.worldSlotContainer = new WorldSlot();
         initButtons();
     }
 
@@ -73,13 +68,13 @@ public class ScreenSelectWorld extends Screen
     public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
         super.keyPressed(eventCharacter, eventKey, mx, my);
         if (eventKey == Keyboard.KEY_UP) {
-            if (selectedWorld > 0) {
-                worldSlotContainer.selectItem(selectedWorld - 1, false);
+            if (this.selectedWorld > 0) {
+                this.worldSlotContainer.selectItem(this.selectedWorld - 1, false);
             }
         }
         if (eventKey == Keyboard.KEY_DOWN) {
-            if (selectedWorld < saveList.size() - 1) {
-                worldSlotContainer.selectItem(selectedWorld + 1, false);
+            if (this.selectedWorld < this.saveList.size() - 1) {
+                this.worldSlotContainer.selectItem(this.selectedWorld + 1, false);
             }
         }
         if (eventKey == Keyboard.KEY_DELETE) {
@@ -87,64 +82,55 @@ public class ScreenSelectWorld extends Screen
         }
     }
 
-    private void loadSaves()
-    {
-        ISaveFormat saveFormat = mc.getSaveFormat();
-        saveList = saveFormat.getSaveFileList();
-        userTags = new HashMap<>();
-        for (SaveFile file : saveList) {
+    private void loadSaves() {
+        ISaveFormat saveFormat = this.mc.getSaveFormat();
+        this.saveList = saveFormat.getSaveFileList();
+        this.userTags = new HashMap<>();
+        for (SaveFile file : this.saveList) {
             LevelStorage levelStorage = saveFormat.getSaveHandler(file.getFileName(), false);
             LevelData data = levelStorage.getLevelData();
             if (data != null && data.getLastPlayerUUID() != null) {
-                userTags.put(file, levelStorage.getPlayerData(null, data.getLastPlayerUUID()));
+                this.userTags.put(file, levelStorage.getPlayerData(null, data.getLastPlayerUUID()));
             } else {
-                userTags.put(file, levelStorage.getPlayerData(mc.session.username, mc.session.uuid));
+                this.userTags.put(file, levelStorage.getPlayerData(this.mc.session.username, this.mc.session.uuid));
             }
         }
-        Collections.sort(saveList);
-        if (selectedWorld >= saveList.size())
-        {
-            selectedWorld = -1;
+        Collections.sort(this.saveList);
+        if (this.selectedWorld >= this.saveList.size()) {
+            this.selectedWorld = -1;
         }
     }
 
-    protected String getSaveFileName(int i)
-    {
-        return saveList.get(i).getFileName();
+    protected String getSaveFileName(int i) {
+        return this.saveList.get(i).getFileName();
     }
 
-    protected String getSaveName(int i)
-    {
-        String s = saveList.get(i).getDisplayName();
-        if(MathHelper.stringNullOrLengthZero(s))
-        {
+    protected String getSaveName(int i) {
+        String s = this.saveList.get(i).getDisplayName();
+        if (MathHelper.stringNullOrLengthZero(s)) {
             I18n i18n = I18n.getInstance();
-            s = i18n.translateKeyAndFormat(stringWorld, i + 1);
+            s = i18n.translateKeyAndFormat(this.stringWorld, i + 1);
         }
         return s;
     }
 
-    public void initButtons()
-    {
+    public void initButtons() {
         I18n i18n = I18n.getInstance();
-        buttons.add(buttonSelect = new ButtonElement(1, width / 2 - 154, height - 52, 150, 20, i18n.translateKey("gui.select_world.button.play_selected_world")));
-        buttons.add(buttonRename = new ButtonElement(6, width / 2 - 154, height - 28, 70, 20, i18n.translateKey("gui.select_world.button.rename")));
-        buttons.add(buttonDelete = new ButtonElement(2, width / 2 - 74, height - 28, 70, 20, i18n.translateKey("gui.select_world.button.delete")));
-        buttons.add(new ButtonElement(3, width / 2 + 4, height - 52, 150, 20, i18n.translateKey("gui.select_world.button.create_new_world")));
-        buttons.add(new ButtonElement(0, width / 2 + 4, height - 28, 150, 20, i18n.translateKey("gui.select_world.button.cancel")));
-        buttonSelect.enabled = false;
-        buttonRename.enabled = false;
-        buttonDelete.enabled = false;
+        this.buttons.add(this.buttonSelect = new ButtonElement(1, this.width / 2 - 154, this.height - 52, 150, 20, i18n.translateKey("gui.select_world.button.play_selected_world")));
+        this.buttons.add(this.buttonRename = new ButtonElement(6, this.width / 2 - 154, this.height - 28, 70, 20, i18n.translateKey("gui.select_world.button.rename")));
+        this.buttons.add(this.buttonDelete = new ButtonElement(2, this.width / 2 - 74, this.height - 28, 70, 20, i18n.translateKey("gui.select_world.button.delete")));
+        this.buttons.add(new ButtonElement(3, this.width / 2 + 4, this.height - 52, 150, 20, i18n.translateKey("gui.select_world.button.create_new_world")));
+        this.buttons.add(new ButtonElement(0, this.width / 2 + 4, this.height - 28, 150, 20, i18n.translateKey("gui.select_world.button.cancel")));
+        this.buttonSelect.enabled = false;
+        this.buttonRename.enabled = false;
+        this.buttonDelete.enabled = false;
     }
 
-    public void deletePresetWorld(String name)
-    {
-        for (int i = 0; i < saveList.size(); i++)
-        {
-            SaveFile save = saveList.get(i);
-            if (save.getDisplayName().equals(name))
-            {
-                deleting = true;
+    public void deletePresetWorld(String name) {
+        for (int i = 0; i < this.saveList.size(); i++) {
+            SaveFile save = this.saveList.get(i);
+            if (save.getDisplayName().equals(name)) {
+                this.deleting = true;
                 deleteWorld(true, i);
                 i--;
             }
@@ -152,13 +138,12 @@ public class ScreenSelectWorld extends Screen
     }
 
     void tryDeleteWorld(boolean skipConfirm) {
-        if (selectedWorld < 0 || selectedWorld >= saveList.size()) return;
-        String s = getSaveName(selectedWorld);
-        if(s != null)
-        {
-            deleting = true;
+        if (this.selectedWorld < 0 || this.selectedWorld >= this.saveList.size()) return;
+        String s = getSaveName(this.selectedWorld);
+        if (s != null) {
+            this.deleting = true;
             if (skipConfirm) {
-                deleteWorld(true, selectedWorld);
+                deleteWorld(true, this.selectedWorld);
             } else {
                 I18n i18n = I18n.getInstance();
                 PopupScreen popup = new PopupBuilder(this, 250)
@@ -167,170 +152,147 @@ public class ScreenSelectWorld extends Screen
                     .withLabel("gui.select_world.label.delete_confirm.1")
                     .withLabelLiteral(i18n.translateKeyAndFormat("gui.select_world.label.delete_confirm.2", s))
                     .withLabelLiteral("")
-                    .withButtonGroup("endButtons", new String[] { "gui.select_world.button.delete", "gui.select_world.button.cancel" }, new int[] { 1, 0 })
+                    .withButtonGroup("endButtons", new String[]{"gui.select_world.button.delete", "gui.select_world.button.cancel"}, new int[]{1, 0})
                     .withOnCloseListener((statusCode, results) -> {
-                        if (statusCode == 1)
-                        {
-                            deleteWorld(true, selectedWorld);
+                        if (statusCode == 1) {
+                            deleteWorld(true, this.selectedWorld);
                         }
                     })
                     .build();
-                mc.displayScreen(popup);
+                this.mc.displayScreen(popup);
             }
         }
 
     }
 
     @Override
-    protected void buttonClicked(@NotNull ButtonElement button)
-    {
-        if(!button.enabled) {
+    protected void buttonClicked(@NotNull ButtonElement button) {
+        if (!button.enabled) {
             return;
         }
-        if(button.id == 2) {
+        if (button.id == 2) {
             tryDeleteWorld(false);
-        }
-        else if(button.id == 1) {
-            selectWorld(selectedWorld);
-        }
-        else if(button.id == 3) {
-            mc.displayScreen(new ScreenCreateWorld(this));
-        }
-        else if(button.id == 6) {
+        } else if (button.id == 1) {
+            selectWorld(this.selectedWorld);
+        } else if (button.id == 3) {
+            this.mc.displayScreen(new ScreenCreateWorld(this));
+        } else if (button.id == 6) {
             PopupScreen popup = new PopupBuilder(this, 140)
-                    .closeOnEsc(0)
-                    .closeOnEnter(1)
-                    .withLabel("gui.select_world.label.rename_title")
-                    .withLabel("gui.select_world.label.world_name")
-                    .withTextField("nameField", getSaveName(selectedWorld))
-                    .withButtonGroup("endButtons", new String[] { "gui.select_world.button.rename", "gui.select_world.button.cancel" }, new int[] { 1, 0 })
-                    .withOnCloseListener(((statusCode, results) -> {
-                        if (statusCode == 1)
-                        {
-                            String text = (String) results.get("nameField");
-                            ISaveFormat format = mc.getSaveFormat();
-                            format.renameWorld(getSaveFileName(selectedWorld), text);
-                            loadSaves();
-                        }
-                    }))
-                    .build();
-            mc.displayScreen(popup);
-        }
-        else if(button.id == 0)
-        {
-            mc.displayScreen(parentScreen);
+                .closeOnEsc(0)
+                .closeOnEnter(1)
+                .withLabel("gui.select_world.label.rename_title")
+                .withLabel("gui.select_world.label.world_name")
+                .withTextField("nameField", getSaveName(this.selectedWorld))
+                .withButtonGroup("endButtons", new String[]{"gui.select_world.button.rename", "gui.select_world.button.cancel"}, new int[]{1, 0})
+                .withOnCloseListener(((statusCode, results) -> {
+                    if (statusCode == 1) {
+                        String text = (String) results.get("nameField");
+                        ISaveFormat format = this.mc.getSaveFormat();
+                        format.renameWorld(getSaveFileName(this.selectedWorld), text);
+                        loadSaves();
+                    }
+                }))
+                .build();
+            this.mc.displayScreen(popup);
+        } else if (button.id == 0) {
+            this.mc.displayScreen(this.parentScreen);
         }
     }
 
-    public void selectWorld(int i)
-    {
-        SaveFile save = saveList.get(i);
+    public void selectWorld(int i) {
+        SaveFile save = this.saveList.get(i);
         if (save.isCorrupted()) return;
-        if (save.getNeedsConversion() && Global.DISABLE_OLD_WORLDS)
-        {
+        if (save.getNeedsConversion() && Global.DISABLE_OLD_WORLDS) {
             return;
         }
 
-        mc.displayScreen(null);
-        if(selected)
-        {
+        this.mc.displayScreen(null);
+        if (this.selected) {
             return;
         }
-        selected = true;
-        mc.playerController = new PlayerControllerSP(mc);
+        this.selected = true;
+        this.mc.playerController = new PlayerControllerSP(this.mc);
         String s = getSaveFileName(i);
-        if(s == null)
-        {
+        if (s == null) {
             s = "World" + i;
         }
-        mc.startWorld(s);
-        mc.displayScreen(null);
+        this.mc.startWorld(s);
+        this.mc.displayScreen(null);
     }
 
-    public void deleteWorld(boolean flag, int i)
-    {
-        if(deleting)
-        {
-            deleting = false;
-            if(flag)
-            {
-                ISaveFormat isaveformat = mc.getSaveFormat();
+    public void deleteWorld(boolean flag, int i) {
+        if (this.deleting) {
+            this.deleting = false;
+            if (flag) {
+                ISaveFormat isaveformat = this.mc.getSaveFormat();
                 isaveformat.flushCache();
                 isaveformat.deleteSave(getSaveFileName(i));
                 loadSaves();
-                selectedWorld = -1;
+                this.selectedWorld = -1;
             }
-            mc.displayScreen(this);
+            this.mc.displayScreen(this);
         }
     }
 
     @Override
-    public void render(int mx, int my, float partialTick)
-    {
-        worldSlotContainer.render(mx, my, partialTick);
-        drawStringCenteredShadow(fontRenderer, stringTitle, width / 2, 20, 0xffffff);
+    public void render(int mx, int my, float partialTick) {
+        this.worldSlotContainer.render(mx, my, partialTick);
+        drawStringCenteredShadow(this.fontRenderer, this.stringTitle, this.width / 2, 20, 0xffffff);
         super.render(mx, my, partialTick);
     }
 
-    class WorldSlot extends ScrolledSelectionList
-    {
+    class WorldSlot extends ScrolledSelectionList {
         private final @NotNull StringBuilder nameBuilder = new StringBuilder();
         private final @NotNull StringBuilder descBuilder1 = new StringBuilder();
         private final @NotNull StringBuilder descBuilder2 = new StringBuilder();
+
         public WorldSlot() {
-            super(mc, width, height, 32, height - 64, 36);
+            super(ScreenSelectWorld.this.mc, ScreenSelectWorld.this.width, ScreenSelectWorld.this.height, 32, ScreenSelectWorld.this.height - 64, 36);
         }
 
         @Override
-        protected int getItemCount()
-        {
-            return saveList.size();
+        protected int getItemCount() {
+            return ScreenSelectWorld.this.saveList.size();
         }
 
         @Override
-        protected void selectItem(int itemIndex, boolean doubleClicked)
-        {
-            selectedWorld = itemIndex;
-            boolean flag1 = selectedWorld >= 0 && selectedWorld < getItemCount();
-            boolean corrupted = saveList.get(itemIndex) == null || saveList.get(itemIndex).isCorrupted();
-            buttonSelect.enabled = flag1 && !corrupted;
-            buttonRename.enabled = flag1 && !corrupted;
-            buttonDelete.enabled = flag1;
-            if(doubleClicked && flag1)
-            {
+        protected void selectItem(int itemIndex, boolean doubleClicked) {
+            ScreenSelectWorld.this.selectedWorld = itemIndex;
+            boolean flag1 = ScreenSelectWorld.this.selectedWorld >= 0 && ScreenSelectWorld.this.selectedWorld < getItemCount();
+            boolean corrupted = ScreenSelectWorld.this.saveList.get(itemIndex) == null || ScreenSelectWorld.this.saveList.get(itemIndex).isCorrupted();
+            ScreenSelectWorld.this.buttonSelect.enabled = flag1 && !corrupted;
+            ScreenSelectWorld.this.buttonRename.enabled = flag1 && !corrupted;
+            ScreenSelectWorld.this.buttonDelete.enabled = flag1;
+            if (doubleClicked && flag1) {
                 selectWorld(itemIndex);
             }
         }
 
         @Override
-        protected boolean isSelectedItem(int itemIndex)
-        {
-            return itemIndex == selectedWorld;
+        protected boolean isSelectedItem(int itemIndex) {
+            return itemIndex == ScreenSelectWorld.this.selectedWorld;
         }
 
         @Override
-        protected int getMaxPosition()
-        {
-            return saveList.size() * 36;
+        protected int getMaxPosition() {
+            return ScreenSelectWorld.this.saveList.size() * 36;
         }
 
         @Override
-        protected void renderHoleBackground()
-        {
+        protected void renderHoleBackground() {
             renderBackground();
         }
 
         @Override
-        protected void renderItem(int index, int x, int y, int height, @NotNull Tessellator t)
-        {
-            nameBuilder.setLength(0);
-            descBuilder1.setLength(0);
-            descBuilder2.setLength(0);
+        protected void renderItem(int index, int x, int y, int height, @NotNull TessellatorGeneral t) {
+            this.nameBuilder.setLength(0);
+            this.descBuilder1.setLength(0);
+            this.descBuilder2.setLength(0);
 
             I18n i18n = I18n.getInstance();
-            SaveFile saveFile = saveList.get(index);
+            SaveFile saveFile = ScreenSelectWorld.this.saveList.get(index);
 
-            CompoundTag userTag = userTags.get(saveFile);
+            CompoundTag userTag = ScreenSelectWorld.this.userTags.get(saveFile);
             Gamemode gamemode;
             if (userTag != null) {
                 gamemode = Gamemode.gamemodesList[userTag.getInteger("Gamemode")];
@@ -339,44 +301,42 @@ public class ScreenSelectWorld extends Screen
             }
 
             final String saveName = saveFile.getDisplayName();
-            if (saveFile.isCorrupted()) nameBuilder.append(TextFormatting.RED);
-            if(MathHelper.stringNullOrLengthZero(saveName)) {
-                nameBuilder.append(i18n.translateKeyAndFormat(stringWorld, index + 1));
+            if (saveFile.isCorrupted()) this.nameBuilder.append(TextFormatting.RED);
+            if (MathHelper.stringNullOrLengthZero(saveName)) {
+                this.nameBuilder.append(i18n.translateKeyAndFormat(ScreenSelectWorld.this.stringWorld, index + 1));
             } else {
-                nameBuilder.append(saveName);
+                this.nameBuilder.append(saveName);
             }
 
             long sizeBytes = saveFile.getSizeOnDisk();
-            descBuilder1.append(saveFile.getFileName());
-            descBuilder1.append(" (").append(dateFormatter.format(new Date(saveFile.getLastTimePlayed())));
-            descBuilder1.append(", ").append((float) (((sizeBytes / 1024L) * 100L) / 1024L) / 100F).append(" MB)");
+            this.descBuilder1.append(saveFile.getFileName());
+            this.descBuilder1.append(" (").append(ScreenSelectWorld.this.dateFormatter.format(new Date(saveFile.getLastTimePlayed())));
+            this.descBuilder1.append(", ").append((float) (((sizeBytes / 1024L) * 100L) / 1024L) / 100F).append(" MB)");
 
-            if(saveFile.getNeedsConversion())
-            {
-                descBuilder2.append(stringConversion).append(" ");
-            }
-            else
-            {
+            if (saveFile.getNeedsConversion()) {
+                this.descBuilder2.append(ScreenSelectWorld.this.stringConversion).append(" ");
+            } else {
                 I18n st = I18n.getInstance();
                 LevelData ld = saveFile.getLevelData();
                 DimensionData dd = saveFile.getDimensionData().get(0);
-                if (dd == null){
-                    descBuilder2.append(TextFormatting.RED).append(st.translateKey("gui.select_world.label.dimension_corrupted"));
+                if (dd == null) {
+                    this.descBuilder2.append(TextFormatting.RED).append(st.translateKey("gui.select_world.label.dimension_corrupted"));
                 } else {
-                    descBuilder2.append(st.translateKey(gamemode.getLanguageKey() + ".name"));
-                    if (ld != null && ld.getCheatsEnabled()) descBuilder2.append(" | ").append(st.translateKey("gui.select_world.label.cheats"));
+                    this.descBuilder2.append(st.translateKey(gamemode.getLanguageKey() + ".name"));
+                    if (ld != null && ld.getCheatsEnabled())
+                        this.descBuilder2.append(" | ").append(st.translateKey("gui.select_world.label.cheats"));
                     WorldType worldType = dd.getWorldType();
                     if (worldType != null) {
-                        descBuilder2.append(" | ").append(st.translateKey(dd.getWorldType().getLanguageKey() + ".name"));
+                        this.descBuilder2.append(" | ").append(st.translateKey(dd.getWorldType().getLanguageKey() + ".name"));
                     } else {
-                        descBuilder2.append(" | ").append(TextFormatting.RED).append(st.translateKey("gui.select_world.label.unknown"));
+                        this.descBuilder2.append(" | ").append(TextFormatting.RED).append(st.translateKey("gui.select_world.label.unknown"));
                     }
                 }
             }
 
-            drawStringShadow(fontRenderer, nameBuilder, x + 2, y + 1, 0xffffff);
-            drawStringShadow(fontRenderer, descBuilder1, x + 2, y + 12, 0x808080);
-            drawStringShadow(fontRenderer, descBuilder2, x + 2, y + 12 + 10, 0x808080);
+            drawStringShadow(ScreenSelectWorld.this.fontRenderer, this.nameBuilder, x + 2, y + 1, 0xffffff);
+            drawStringShadow(ScreenSelectWorld.this.fontRenderer, this.descBuilder1, x + 2, y + 12, 0x808080);
+            drawStringShadow(ScreenSelectWorld.this.fontRenderer, this.descBuilder2, x + 2, y + 12 + 10, 0x808080);
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenSignEditor.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenSignEditor.java
index df5ce47a4..7fb04b990 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenSignEditor.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenSignEditor.java
@@ -5,7 +5,8 @@ import net.minecraft.client.gui.modelviewer.elements.ListenerButtonElement;
 import net.minecraft.client.input.InputType;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.render.TileEntityRenderDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicSign;
 import net.minecraft.core.block.Blocks;
@@ -15,196 +16,184 @@ import net.minecraft.core.lang.I18n;
 import net.minecraft.core.net.packet.PacketSignUpdate;
 import net.minecraft.core.util.helper.ChatAllowedCharacters;
 import org.jetbrains.annotations.NotNull;
+import org.joml.Math;
 import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 
-public class ScreenSignEditor extends Screen
-{
+public class ScreenSignEditor extends Screen {
     private boolean inKeyboard = false;
-    public ScreenSignEditor(@NotNull TileEntitySign sign)
-    {
-        screenTitle = I18n.getInstance().translateKey("gui.edit_sign.label.title");
-        editLine = 0;
-        entitySign = sign;
+
+    public ScreenSignEditor(@NotNull TileEntitySign sign) {
+        this.screenTitle = I18n.getInstance().translateKey("gui.edit_sign.label.title");
+        this.editLine = 0;
+        this.entitySign = sign;
     }
 
     @Override
-	public void init()
-    {
-        buttons.clear();
+    public void init() {
+        this.buttons.clear();
         Keyboard.enableRepeatEvents(true);
 
-        Block<?> block = entitySign.getBlock();
-        if(block == Blocks.SIGN_POST_PLANKS_OAK)
-        {
-            yOffset = 36;
+        Block<?> block = this.entitySign.getBlock();
+        if (block == Blocks.SIGN_POST_PLANKS_OAK) {
+            this.yOffset = 36;
         }
 
-        buttons.add(new ButtonElement(0, width / 2 - 100, 150 + 50 + yOffset, I18n.getInstance().translateKey("gui.edit_sign.button.done")));
-        
-        buttons.add(new ButtonElement(1, width / 2 - 20, 120 + 50 + yOffset, 20, 20, "<"));
-        buttons.add(new ButtonElement(2, width / 2, 120 + 50 + yOffset, 20, 20, ">"));
+        this.buttons.add(new ButtonElement(0, this.width / 2 - 100, 150 + 50 + this.yOffset, I18n.getInstance().translateKey("gui.edit_sign.button.done")));
+
+        this.buttons.add(new ButtonElement(1, this.width / 2 - 20, 120 + 50 + this.yOffset, 20, 20, "<"));
+        this.buttons.add(new ButtonElement(2, this.width / 2, 120 + 50 + this.yOffset, 20, 20, ">"));
 
         boolean wallSign = false;
         if (Block.hasLogicClass(block, BlockLogicSign.class)) {
             wallSign = !((BlockLogicSign) block.getLogic()).isFreeStanding;
         }
 
-        add(new ListenerButtonElement(30, width/2 - 50, 12 * 0 + 67 + (wallSign ? 31 : 0), 100, 12, "")
-            .setActionListener(() -> {editLine = 0; inKeyboard = true;})).mute().hide();
-        add(new ListenerButtonElement(30, width/2 - 50, 12 * 1 + 67 + (wallSign ? 31 : 0), 100, 12, "")
-            .setActionListener(() -> {editLine = 1;inKeyboard = true;})).mute().hide();
-        add(new ListenerButtonElement(30, width/2 - 50, 12 * 2 + 67 + (wallSign ? 31 : 0), 100, 12, "")
-            .setActionListener(() -> {editLine = 2;inKeyboard = true;})).mute().hide();
-        add(new ListenerButtonElement(30, width/2 - 50, 12 * 3 + 67 + (wallSign ? 31 : 0), 100, 12, "")
-            .setActionListener(() -> {editLine = 3;inKeyboard = true;})).mute().hide();
-
-        inKeyboard = (mc.gameSettings.forceOnscreenKeyboard.value || mc.inputType == InputType.CONTROLLER) && !(mc.currentScreen instanceof ScreenKeyboard);
+        add(new ListenerButtonElement(30, this.width / 2 - 50, 67 + (wallSign ? 31 : 0), 100, 12, "")
+            .setActionListener(() -> {
+                this.editLine = 0;
+                this.inKeyboard = true;
+            })).mute().hide();
+        add(new ListenerButtonElement(30, this.width / 2 - 50, 12 + 67 + (wallSign ? 31 : 0), 100, 12, "")
+            .setActionListener(() -> {
+                this.editLine = 1;
+                this.inKeyboard = true;
+            })).mute().hide();
+        add(new ListenerButtonElement(30, this.width / 2 - 50, 12 * 2 + 67 + (wallSign ? 31 : 0), 100, 12, "")
+            .setActionListener(() -> {
+                this.editLine = 2;
+                this.inKeyboard = true;
+            })).mute().hide();
+        add(new ListenerButtonElement(30, this.width / 2 - 50, 12 * 3 + 67 + (wallSign ? 31 : 0), 100, 12, "")
+            .setActionListener(() -> {
+                this.editLine = 3;
+                this.inKeyboard = true;
+            })).mute().hide();
+
+        this.inKeyboard = (this.mc.gameSettings.forceOnscreenKeyboard.value || this.mc.inputType == InputType.CONTROLLER) && !(this.mc.currentScreen instanceof ScreenKeyboard);
     }
 
     @Override
-	public void removed()
-    {
+    public void removed() {
         Keyboard.enableRepeatEvents(false);
         // I have no idea how the hell the world is null sometimes
         // but thaboard was getting a crash from the world being null
-        if(mc.currentWorld != null && mc.currentWorld.isClientSide)
-        {
-            mc.getSendQueue().addToSendQueue(new PacketSignUpdate(entitySign.x, entitySign.y, entitySign.z, entitySign.signText, entitySign.getPicture().getId(), entitySign.getColor().id));
+        if (this.mc.currentWorld != null && this.mc.currentWorld.isClientSide) {
+            this.mc.getSendQueue().addToSendQueue(new PacketSignUpdate(this.entitySign.x, this.entitySign.y, this.entitySign.z, this.entitySign.signText, this.entitySign.getPicture().getId(), this.entitySign.getColor().id));
         }
     }
 
     @Override
-	public void tick()
-    {
-        updateCounter++;
+    public void tick() {
+        this.updateCounter++;
     }
 
     @Override
-	protected void buttonClicked(@NotNull ButtonElement button)
-    {
-        if(!button.enabled)
-        {
+    protected void buttonClicked(@NotNull ButtonElement button) {
+        if (!button.enabled) {
             return;
         }
-        if(button.id == 0)
-        {
-            entitySign.setChanged();
-            mc.displayScreen(null);
+        if (button.id == 0) {
+            this.entitySign.setChanged();
+            this.mc.displayScreen(null);
         }
-        if (button.id == 1)
-        {
-            int id = entitySign.getPicture().getId();
+        if (button.id == 1) {
+            int id = this.entitySign.getPicture().getId();
             int lastId = id - 1;
             if (lastId < 0) lastId = EnumSignPicture.values().length - 1;
-            entitySign.setPicture(EnumSignPicture.values()[lastId]);
-            entitySign.setChanged();
+            this.entitySign.setPicture(EnumSignPicture.values()[lastId]);
+            this.entitySign.setChanged();
         }
-        if (button.id == 2)
-        {
-            int id = entitySign.getPicture().getId();
+        if (button.id == 2) {
+            int id = this.entitySign.getPicture().getId();
             int nextId = id + 1;
             if (nextId >= EnumSignPicture.values().length) nextId = 0;
-            entitySign.setPicture(EnumSignPicture.values()[nextId]);
-            entitySign.setChanged();
+            this.entitySign.setPicture(EnumSignPicture.values()[nextId]);
+            this.entitySign.setChanged();
         }
     }
 
     @Override
-	public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
-    {
-    	if(eventKey == Keyboard.KEY_ESCAPE)
-    	{
-            entitySign.setChanged();
-    		mc.displayScreen(null);
-    	}
-        if(eventKey == Keyboard.KEY_UP)
-        {
-            editLine = editLine - 1 & 3;
-        }
-        if(eventKey == Keyboard.KEY_DOWN || eventKey == Keyboard.KEY_PRINT_SCREEN || eventKey == Keyboard.KEY_NUMPADENTER)
-        {
-            editLine = editLine + 1 & 3;
-        }
-        if(eventKey == Keyboard.KEY_BACK && !entitySign.signText[editLine].isEmpty())
-        {
-            entitySign.signText[editLine] = entitySign.signText[editLine].substring(0, entitySign.signText[editLine].length() - 1);
-        }
-        if ((allowedCharacters.indexOf(eventCharacter) >= 0 || Character.isLetterOrDigit(eventCharacter)) && entitySign.signText[editLine].length() < TileEntitySign.MAX_LINE_SIZE)
-        {
-            entitySign.signText[editLine] += eventCharacter;
+    public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
+        if (eventKey == Keyboard.KEY_ESCAPE) {
+            this.entitySign.setChanged();
+            this.mc.displayScreen(null);
+        }
+        if (eventKey == Keyboard.KEY_UP) {
+            this.editLine = this.editLine - 1 & 3;
+        }
+        if (eventKey == Keyboard.KEY_DOWN || eventKey == Keyboard.KEY_PRINT_SCREEN || eventKey == Keyboard.KEY_NUMPADENTER) {
+            this.editLine = this.editLine + 1 & 3;
+        }
+        if (eventKey == Keyboard.KEY_BACK && !this.entitySign.signText[this.editLine].isEmpty()) {
+            this.entitySign.signText[this.editLine] = this.entitySign.signText[this.editLine].substring(0, this.entitySign.signText[this.editLine].length() - 1);
+        }
+        if ((allowedCharacters.indexOf(eventCharacter) >= 0 || Character.isLetterOrDigit(eventCharacter)) && this.entitySign.signText[this.editLine].length() < TileEntitySign.MAX_LINE_SIZE) {
+            this.entitySign.signText[this.editLine] += eventCharacter;
         }
     }
 
     @Override
-	public void render(int mx, int my, float partialTick)
-    {
-        GL11.glColor4f(1f, 1f, 1f, 1f);
-        if (inKeyboard && (mc.gameSettings.forceOnscreenKeyboard.value || mc.inputType == InputType.CONTROLLER) && !(mc.currentScreen instanceof ScreenKeyboard)) {
-            if (editLine < entitySign.signText.length) {
+    public void render(int mx, int my, float partialTick) {
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+        if (this.inKeyboard && (this.mc.gameSettings.forceOnscreenKeyboard.value || this.mc.inputType == InputType.CONTROLLER) && !(this.mc.currentScreen instanceof ScreenKeyboard)) {
+            if (this.editLine < this.entitySign.signText.length) {
                 ScreenKeyboard keyboard = new ScreenKeyboard(this, null,
                     (s) -> {
-                        entitySign.signText[editLine] = s;
-                        if (editLine < entitySign.signText.length - 1) {
-                            editLine++;
+                        this.entitySign.signText[this.editLine] = s;
+                        if (this.editLine < this.entitySign.signText.length - 1) {
+                            this.editLine++;
                         } else {
-                            inKeyboard = false;
+                            this.inKeyboard = false;
                         }
                     },
-                    (c, k, s) -> entitySign.signText[editLine] = s,
-                    s -> entitySign.signText[editLine] = s);
-                keyboard.editor.setText(entitySign.signText[editLine]);
+                    (c, k, s) -> this.entitySign.signText[this.editLine] = s,
+                    s -> this.entitySign.signText[this.editLine] = s);
+                keyboard.editor.setText(this.entitySign.signText[this.editLine]);
                 keyboard.editor.setCursor(Integer.MAX_VALUE);
-                mc.displayScreen(keyboard);
+                this.mc.displayScreen(keyboard);
             }
         }
         renderBackground();
-        drawStringCenteredShadow(fontRenderer, screenTitle, width / 2, 40, 0xffffff);
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float) width / 2, 0.0F, 50F);
+        drawStringCenteredShadow(this.fontRenderer, this.screenTitle, this.width / 2, 40, 0xffffff);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) this.width / 2, 0.0F, 50F);
         float scale = 93.75F;
-        GL11.glScalef(-scale, -scale, -scale);
-        GL11.glRotatef(180F, 0.0F, 1.0F, 0.0F);
-        Block<?> block = entitySign.getBlock();
+        GLRenderer.modelM4f().scale(-scale, -scale, -scale);
+        GLRenderer.modelM4f().rotateY(Math.PI_f);
+        Block<?> block = this.entitySign.getBlock();
         if (Block.hasLogicClass(block, BlockLogicSign.class)) {
             BlockLogicSign sign = (BlockLogicSign) block.getLogic();
-            if(sign.isFreeStanding)
-            {
-                float signAngle = (float)((entitySign.getBlockMeta() & BlockLogicSign.MASK_SIDE) * 360) / 16F;
-                GL11.glRotatef(signAngle, 0.0F, 1.0F, 0.0F);
-                GL11.glTranslatef(0.0F, -1.0625F, 0.0F);
-            } else
-            {
-                int meta = entitySign.getBlockMeta() & BlockLogicSign.MASK_SIDE;
+            if (sign.isFreeStanding) {
+                float signAngle = (float) ((this.entitySign.getBlockMeta() & BlockLogicSign.MASK_SIDE) * 360) / 16F;
+                GLRenderer.modelM4f().rotateY(Math.toRadians(signAngle));
+                GLRenderer.modelM4f().translate(0.0F, -1.0625F, 0.0F);
+            } else {
+                int meta = this.entitySign.getBlockMeta() & BlockLogicSign.MASK_SIDE;
                 float signAngle = 0.0F;
-                if(meta == 2)
-                {
+                if (meta == 2) {
                     signAngle = 180F;
                 }
-                if(meta == 4)
-                {
+                if (meta == 4) {
                     signAngle = 90F;
                 }
-                if(meta == 5)
-                {
+                if (meta == 5) {
                     signAngle = -90F;
                 }
-                GL11.glRotatef(signAngle, 0.0F, 1.0F, 0.0F);
-                GL11.glTranslatef(0.0F, -1.0625F, 0.0F);
+                GLRenderer.modelM4f().rotateY(Math.toRadians(signAngle));
+                GLRenderer.modelM4f().translate(0.0F, -1.0625F, 0.0F);
             }
         }
 
-        if((updateCounter / 6) % 2 == 0)
-        {
-            entitySign.lineBeingEdited = editLine;
+        if ((this.updateCounter / 6) % 2 == 0) {
+            this.entitySign.lineBeingEdited = this.editLine;
         }
-        GL11.glEnable(GL11.GL_BLEND);
-        TileEntityRenderDispatcher.instance.renderTileEntity(Tessellator.instance, entitySign, -0.5D, -0.75D, -0.5D, 0.0F);
-        entitySign.lineBeingEdited = -1;
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glPopMatrix();
-        
-        drawStringCenteredShadow(fontRenderer, I18n.getInstance().translateKey(entitySign.getPicture().getLanguageKey()), width / 2, 100 + 50 + yOffset, 0xFFFFFF);
+        GLRenderer.enableState(State.BLEND);
+        TileEntityRenderDispatcher.instance.renderTileEntity(GLRenderer.getTessellator(), this.entitySign, -0.5D, -0.75D, -0.5D, 0.0F);
+        this.entitySign.lineBeingEdited = -1;
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.popFrame();
+
+        drawStringCenteredShadow(this.fontRenderer, I18n.getInstance().translateKey(this.entitySign.getPicture().getLanguageKey()), this.width / 2, 100 + 50 + this.yOffset, 0xFFFFFF);
 
         super.render(mx, my, partialTick);
     }
@@ -213,10 +202,10 @@ public class ScreenSignEditor extends Screen
     public void guiSpecificControllerInput(@NotNull ControllerInput controller) {
         super.guiSpecificControllerInput(controller);
         if (controller.digitalPad.up.pressedThisFrame()) {
-            editLine = editLine - 1 & 3;
+            this.editLine = this.editLine - 1 & 3;
         }
         if (controller.digitalPad.down.pressedThisFrame()) {
-            editLine = editLine + 1 & 3;
+            this.editLine = this.editLine + 1 & 3;
         }
     }
 
@@ -227,8 +216,7 @@ public class ScreenSignEditor extends Screen
     private int yOffset = 0;
     private static final String allowedCharacters;
 
-    static 
-    {
+    static {
         allowedCharacters = ChatAllowedCharacters.ALLOWED_CHARACTERS;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenSoundTest.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenSoundTest.java
index 8153e701b..f8719f5ed 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenSoundTest.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenSoundTest.java
@@ -3,8 +3,8 @@ package net.minecraft.client.gui;
 import net.minecraft.client.gui.modelviewer.elements.ListenerButtonElement;
 import net.minecraft.client.gui.modelviewer.elements.ListenerTextFieldElement;
 import net.minecraft.client.gui.modelviewer.elements.IListenerElement;
-import net.minecraft.client.render.font.Alignment;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.sound.SoundEngine;
 import net.minecraft.client.sound.SoundEvent;
 import net.minecraft.client.sound.SoundRepository;
@@ -15,7 +15,6 @@ import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 import paulscode.sound.SoundSystem;
 
 import java.io.File;
@@ -45,112 +44,117 @@ public class ScreenSoundTest extends Screen {
         initRepos();
     }
 
-    public void initRepos(){
-        allEntries = SoundRepository.SOUNDS.getAllEvents();
+    public void initRepos() {
+        this.allEntries = SoundRepository.SOUNDS.getAllEvents();
 
-        currentEntry = allEntries.get(0);
-        entryIndex = 0;
+        this.currentEntry = this.allEntries.get(0);
+        this.entryIndex = 0;
     }
+
     @Override
-    public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
-    {
+    public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
         if (eventKey == Keyboard.KEY_ESCAPE) {
-            mc.displayScreen(parentScreen);
+            this.mc.displayScreen(this.parentScreen);
         }
-        List<ButtonElement> _buttons = new ArrayList<>(buttons);
-        for (ButtonElement button : _buttons){
-            if (button instanceof IListenerElement && button.isHovered(mx, my)){
-                ((IListenerElement) button).onKeyTyped(eventCharacter, eventKey);
+        List<ButtonElement> _buttons = new ArrayList<>(this.buttons);
+        for (ButtonElement button : _buttons) {
+            if (button instanceof IListenerElement<?> element && button.isHovered(mx, my)) {
+                element.onKeyTyped(eventCharacter, eventKey);
             }
         }
     }
+
     @Override
-    public void tick(){
-        List<ButtonElement> _buttons = new ArrayList<>(buttons);
-        for (ButtonElement button : _buttons){
-            if (button instanceof ListenerButtonElement){
-                ((ListenerButtonElement) button).tick();
+    public void tick() {
+        List<ButtonElement> _buttons = new ArrayList<>(this.buttons);
+        for (ButtonElement button : _buttons) {
+            if (button instanceof ListenerButtonElement element) {
+                element.tick();
             }
         }
     }
-    public void init()
-    {
 
-        top = TOP_SPACING;
-        bottom = height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
-        add(new ListenerButtonElement(0, width/2 - 100, height - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.sound_test.button.done")).setActionListener(() -> {
+    public void init() {
+
+        this.top = TOP_SPACING;
+        this.bottom = this.height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
+        add(new ListenerButtonElement(0, this.width / 2 - 100, this.height - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.sound_test.button.done")).setActionListener(() -> {
             removed();
-            mc.displayScreen(null);
+            this.mc.displayScreen(null);
         }));
 
-        leftEntry = add(new ListenerButtonElement(11, width - (20 + BUTTON_SPACING) * 2, bottom - (BUTTON_SPACING + 20) * 2, 20, 20, "<")
+        this.leftEntry = add(new ListenerButtonElement(11, this.width - (20 + BUTTON_SPACING) * 2, this.bottom - (BUTTON_SPACING + 20) * 2, 20, 20, "<")
             .setActionListener(() -> cycleEntry(-1)));
-        add(new ListenerButtonElement(12, width - (20 + BUTTON_SPACING) * 1, bottom - (BUTTON_SPACING + 20) * 2, 20, 20, ">")
+        add(new ListenerButtonElement(12, this.width - (20 + BUTTON_SPACING), this.bottom - (BUTTON_SPACING + 20) * 2, 20, 20, ">")
             .setActionListener(() -> cycleEntry(1)));
 
-        ListenerButtonElement b = add(new ListenerButtonElement(20, width/2 - 100, bottom - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.sound_test.button.play"))
+        ListenerButtonElement b = add(new ListenerButtonElement(20, this.width / 2 - 100, this.bottom - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.sound_test.button.play"))
             .setActionListener(this::playEntry)
         );
         b.playSound = false;
-        add(new ListenerButtonElement(22, width/2 + 100 + BUTTON_SPACING, bottom - (BUTTON_SPACING + 20), 20, 20, "X")
+        add(new ListenerButtonElement(22, this.width / 2 + 100 + BUTTON_SPACING, this.bottom - (BUTTON_SPACING + 20), 20, 20, "X")
             .setActionListener(this::stopSound)
         );
 
 
-        add(new ListenerButtonElement(30, BUTTON_SPACING, bottom - (BUTTON_SPACING + 20), 20, 20, "")
-            .setActionListener(() -> FileOpener.open(new File(mc.getMinecraftDir(), "resources")))
+        add(new ListenerButtonElement(30, BUTTON_SPACING, this.bottom - (BUTTON_SPACING + 20), 20, 20, "")
+            .setActionListener(() -> FileOpener.open(new File(this.mc.getMinecraftDir(), "resources")))
             .setTextures("minecraft:gui/misc/button_folder", "minecraft:gui/misc/button_folder_highlighted", "minecraft:gui/misc/button_folder"));
 
-        add(new ListenerButtonElement(31, 20 + BUTTON_SPACING * 2, bottom - (BUTTON_SPACING + 20), 20, 20, "V"))
-            .setActionListener(() -> showURL = !showURL);
+        add(new ListenerButtonElement(31, 20 + BUTTON_SPACING * 2, this.bottom - (BUTTON_SPACING + 20), 20, 20, "V"))
+            .setActionListener(() -> this.showURL = !this.showURL);
 
-        add(new ListenerButtonElement(32, 40 + BUTTON_SPACING * 3, bottom - (BUTTON_SPACING + 20), 40, 20, I18n.getInstance().translateKey("gui.sound_test.button.reload")))
+        add(new ListenerButtonElement(32, 40 + BUTTON_SPACING * 3, this.bottom - (BUTTON_SPACING + 20), 40, 20, I18n.getInstance().translateKey("gui.sound_test.button.reload")))
             .setActionListener(() -> {
-                mc.sndManager = new SoundEngine();
-                mc.sndManager.init(mc.gameSettings);
+                this.mc.sndManager = new SoundEngine();
+                this.mc.sndManager.init(this.mc.gameSettings);
                 initRepos();
             });
 
-        ListenerTextFieldElement volumeField = new ListenerTextFieldElement(parentScreen, mc.font, width - BUTTON_SPACING - 60, bottom - (BUTTON_SPACING + 20) * 3, 60, 20, String.valueOf(volume), "Volume");
+        ListenerTextFieldElement volumeField = new ListenerTextFieldElement(this.parentScreen, this.mc.font, this.width - BUTTON_SPACING - 60, this.bottom - (BUTTON_SPACING + 20) * 3, 60, 20, String.valueOf(this.volume), "Volume");
         add(volumeField)
             .setPrefaceText("Vol: ")
             .setKeyListener(key -> {
                 try {
-                    volume = Float.parseFloat(volumeField.getText());
-                } catch (Exception ignored){}})
+                    this.volume = Float.parseFloat(volumeField.getText());
+                } catch (Exception ignored) {
+                }
+            })
             .setActionListener(() -> {
-                if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)){
+                if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)) {
                     volumeField.setText(String.valueOf(1));
-                    volume = 1;
-                }});
+                    this.volume = 1;
+                }
+            });
 
-        ListenerTextFieldElement pitchField = new ListenerTextFieldElement(parentScreen, mc.font, width - BUTTON_SPACING - 60, bottom - (BUTTON_SPACING + 20) * 4, 60, 20, String.valueOf(pitch), "Pitch");
+        ListenerTextFieldElement pitchField = new ListenerTextFieldElement(this.parentScreen, this.mc.font, this.width - BUTTON_SPACING - 60, this.bottom - (BUTTON_SPACING + 20) * 4, 60, 20, String.valueOf(this.pitch), "Pitch");
         add(pitchField)
             .setPrefaceText("Pitch: ")
             .setKeyListener(key -> {
                 try {
-                    pitch = Float.parseFloat(pitchField.getText());
-                } catch (Exception ignored){}})
+                    this.pitch = Float.parseFloat(pitchField.getText());
+                } catch (Exception ignored) {
+                }
+            })
             .setActionListener(() -> {
-                if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)){
+                if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)) {
                     pitchField.setText(String.valueOf(1));
-                    pitch = 1;
-                }});
+                    this.pitch = 1;
+                }
+            });
     }
 
-    protected void buttonClicked(@NotNull ButtonElement button)
-    {
+    protected void buttonClicked(@NotNull ButtonElement button) {
     }
 
-    protected void buttonReleased(@NotNull ButtonElement button)
-    {
+    protected void buttonReleased(@NotNull ButtonElement button) {
     }
 
     protected void cycleEntry(int offset) {
-        if (allEntries.size() <= 0) return;
-        int index = (entryIndex + offset + allEntries.size()) % allEntries.size();
-        currentEntry = allEntries.get(index);
-        entryIndex = index;
+        if (this.allEntries.size() <= 0) return;
+        int index = (this.entryIndex + offset + this.allEntries.size()) % this.allEntries.size();
+        this.currentEntry = this.allEntries.get(index);
+        this.entryIndex = index;
     }
 
     public void render(int mx, int my, float partialTick) {
@@ -158,47 +162,45 @@ public class ScreenSoundTest extends Screen {
 
         super.render(mx, my, partialTick);
 
-        drawStringCenteredNoShadow(fontRenderer, I18n.getInstance().translateKey("gui.sound_test.label.title"), width/2, 5, 0xFFFFFF);
+        drawStringCenteredNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.sound_test.label.title"), this.width / 2, 5, 0xFFFFFF);
 
         final String msg = I18n.getInstance().translateKey("gui.sound_test.label.select_entry");
-        drawStringNoShadow(this.fontRenderer, msg, leftEntry.getX() - BUTTON_SPACING - MathHelper.ceil(fontRenderer.stringWidthDouble(msg)), leftEntry.getY() + 6, 0xFFFFFF);
+        drawStringNoShadow(this.fontRenderer, msg, this.leftEntry.getX() - BUTTON_SPACING - MathHelper.ceil(this.fontRenderer.stringWidthDouble(msg)), this.leftEntry.getY() + 6, 0xFFFFFF);
 
         StringBuilder builder = new StringBuilder();
-        builder.append(I18n.getInstance().translateKeyAndFormat("gui.sound_test.label.id", currentEntry == null ? null : currentEntry.getEventID())).append("\n");
-        builder.append(I18n.getInstance().translateKeyAndFormat("gui.sound_test.label.subtitle", currentEntry == null ? null : currentEntry.getSubtitleKey(), currentEntry == null ? null : currentEntry.getSubtitleTranslated())).append("\n");
+        builder.append(I18n.getInstance().translateKeyAndFormat("gui.sound_test.label.id", this.currentEntry == null ? null : this.currentEntry.getEventID())).append("\n");
+        builder.append(I18n.getInstance().translateKeyAndFormat("gui.sound_test.label.subtitle", this.currentEntry == null ? null : this.currentEntry.getSubtitleKey(), this.currentEntry == null ? null : this.currentEntry.getSubtitleTranslated())).append("\n");
 //        builder.append(I18n.getInstance().translateKeyAndFormat("gui.sound_test.label.url", String.valueOf(currentEntry == null ? null : (showURL ? currentEntry.url : "REDACTED")))).append("\n");
-        this.fontRenderer.renderWidthConstrained(Tessellator.instance, builder, 5, this.top + 30, this.width - 10).setShadow().setColor(0xBBBBBB).call();
+        this.fontRenderer.renderWidthConstrained(builder, 5, this.top + 30, this.width - 10).setShadow().setColor(0xBBBBBB).call();
     }
+
     @Override
     public void renderBackground() {
         super.renderBackground();
 
-        if (mc.currentWorld == null)
-        {
-            Tessellator tessellator = Tessellator.instance;
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        if (this.mc.currentWorld == null) {
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
             float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x202020);
+            tessellator.setColorOpaque1i(0x202020);
 
-            tessellator.addVertexWithUV(0,      bottom, 0.0D,   0,              bottom / scale);
-            tessellator.addVertexWithUV(width,  bottom, 0.0D,   width / scale,  bottom / scale);
-            tessellator.addVertexWithUV(width,  top,    0.0D,   width / scale,  top / scale);
-            tessellator.addVertexWithUV(0,      top,    0.0D,   0,              top / scale);
+            tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0, this.bottom / scale);
+            tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, this.width / scale, this.bottom / scale);
+            tessellator.addVertexWithUV(this.width, this.top, 0.0D, this.width / scale, this.top / scale);
+            tessellator.addVertexWithUV(0, this.top, 0.0D, 0, this.top / scale);
 
             tessellator.draw();
-        }
-        else
-        {
-            drawRect(0, 0, width, top, 0x5F000000);
-            drawRect(0, bottom, width, height, 0x5F000000);
+        } else {
+            drawRect(0, 0, this.width, this.top, 0x5F000000);
+            drawRect(0, this.bottom, this.width, this.height, 0x5F000000);
         }
     }
 
     public void playEntry() {
-        if (currentEntry == null) return;
-        mc.sndManager.playSoundWithIdAtPos(currentEntry.getRandomEntry(), SoundCategory.ENTITY_SOUNDS, 0, 0, 0, 1, 1, "debug");
+        if (this.currentEntry == null) return;
+        this.mc.sndManager.playSoundWithIdAtPos(this.currentEntry.getRandomEntry(), SoundCategory.ENTITY_SOUNDS, 0, 0, 0, 1, 1, "debug");
     }
 
     public void stopSound() {
@@ -207,19 +209,17 @@ public class ScreenSoundTest extends Screen {
         soundSystem.stop("debug");
     }
 
-    private void overlayBackground(int minX, int maxX, int minY, int maxY)
-    {
-        if (mc.currentWorld == null)
-        {
-            Tessellator tessellator = Tessellator.instance;
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+    private void overlayBackground(int minX, int maxX, int minY, int maxY) {
+        if (this.mc.currentWorld == null) {
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
             float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x404040);
+            tessellator.setColorOpaque1i(0x404040);
             tessellator.addVertexWithUV(minX, maxY, 0.0D, (float) minX / scale, (float) maxY / scale);
             tessellator.addVertexWithUV(maxX, maxY, 0.0D, (float) maxX / scale, (float) maxY / scale);
-            tessellator.setColorOpaque_I(0x404040);
+            tessellator.setColorOpaque1i(0x404040);
             tessellator.addVertexWithUV(maxX, minY, 0.0D, (float) maxX / scale, (float) minY / scale);
             tessellator.addVertexWithUV(minX, minY, 0.0D, (float) minX / scale, (float) minY / scale);
             tessellator.draw();
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenStats.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenStats.java
index aa5eab8f5..c61d9f810 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenStats.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenStats.java
@@ -1,8 +1,11 @@
 package net.minecraft.client.gui;
 
 import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.achievement.stat.*;
 import net.minecraft.core.lang.I18n;
@@ -12,8 +15,6 @@ import net.minecraft.core.sound.SoundCategory;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 
 import java.util.*;
 
@@ -33,164 +34,136 @@ public class ScreenStats extends Screen {
     private final StatsCounter statsCounter;
     private ScrolledSelectionList selectionList;
 
-    public ScreenStats(Screen parent, StatsCounter statsCounter)
-    {
-        title = I18n.getInstance().translateKey("gui.statistics.label.title");
-        selectionList = null;
+    public ScreenStats(Screen parent, StatsCounter statsCounter) {
+        this.title = I18n.getInstance().translateKey("gui.statistics.label.title");
+        this.selectionList = null;
         this.parent = parent;
         this.statsCounter = statsCounter;
-        tooltip = new TooltipElement(Minecraft.getMinecraft());
+        this.tooltip = new TooltipElement(Minecraft.getMinecraft());
     }
 
     @Override
-	public void init()
-    {
-        generalStatisticsList = new GeneralStatisticsList();
-        itemStatisticsList = new ItemStatisticsList();
-        blockStatisticsList = new BlockStatisticsList();
-        selectionList = generalStatisticsList;
+    public void init() {
+        this.generalStatisticsList = new GeneralStatisticsList();
+        this.itemStatisticsList = new ItemStatisticsList();
+        this.blockStatisticsList = new BlockStatisticsList();
+        this.selectionList = this.generalStatisticsList;
         createButtons();
     }
 
-    public void createButtons()
-    {
+    public void createButtons() {
         I18n i18n = I18n.getInstance();
-        buttons.add(new ButtonElement(0, width / 2 + 4, height - 28, 150, 20, i18n.translateKey("gui.statistics.button.done")));
-        buttons.add(new ButtonElement(1, width / 2 - 154, height - 52, 100, 20, i18n.translateKey("gui.statistics.button.general")));
+        this.buttons.add(new ButtonElement(0, this.width / 2 + 4, this.height - 28, 150, 20, i18n.translateKey("gui.statistics.button.done")));
+        this.buttons.add(new ButtonElement(1, this.width / 2 - 154, this.height - 52, 100, 20, i18n.translateKey("gui.statistics.button.general")));
         ButtonElement blocksButton;
-        buttons.add(blocksButton = new ButtonElement(2, width / 2 - 46, height - 52, 100, 20, i18n.translateKey("gui.statistics.button.blocks")));
+        this.buttons.add(blocksButton = new ButtonElement(2, this.width / 2 - 46, this.height - 52, 100, 20, i18n.translateKey("gui.statistics.button.blocks")));
         ButtonElement itemsButton;
-        buttons.add(itemsButton = new ButtonElement(3, width / 2 + 62, height - 52, 100, 20, i18n.translateKey("gui.statistics.button.items")));
-        if(blockStatisticsList.getItemCount() == 0)
-        {
+        this.buttons.add(itemsButton = new ButtonElement(3, this.width / 2 + 62, this.height - 52, 100, 20, i18n.translateKey("gui.statistics.button.items")));
+        if (this.blockStatisticsList.getItemCount() == 0) {
             blocksButton.enabled = false;
         }
-        if(itemStatisticsList.getItemCount() == 0)
-        {
+        if (this.itemStatisticsList.getItemCount() == 0) {
             itemsButton.enabled = false;
         }
     }
 
     @Override
-	protected void buttonClicked(@NotNull ButtonElement button)
-    {
-        if(!button.enabled)
-        {
+    protected void buttonClicked(@NotNull ButtonElement button) {
+        if (!button.enabled) {
             return;
         }
-        if(button.id == 0)
-        {
-            mc.displayScreen(parent);
-        } else
-        if(button.id == 1)
-        {
-            selectionList = generalStatisticsList;
-        } else
-        if(button.id == 3)
-        {
-            selectionList = itemStatisticsList;
-        } else
-        if(button.id == 2)
-        {
-            selectionList = blockStatisticsList;
+        if (button.id == 0) {
+            this.mc.displayScreen(this.parent);
+        } else if (button.id == 1) {
+            this.selectionList = this.generalStatisticsList;
+        } else if (button.id == 3) {
+            this.selectionList = this.itemStatisticsList;
+        } else if (button.id == 2) {
+            this.selectionList = this.blockStatisticsList;
         }
     }
 
     @Override
-	public void render(int mx, int my, float partialTick)
-    {
-        selectionList.render(mx, my, partialTick);
-        drawStringCenteredShadow(fontRenderer, title, width / 2, 20, 0xffffff);
+    public void render(int mx, int my, float partialTick) {
+        this.selectionList.render(mx, my, partialTick);
+        drawStringCenteredShadow(this.fontRenderer, this.title, this.width / 2, 20, 0xffffff);
         super.render(mx, my, partialTick);
     }
 
-    private void renderItemAsIcon(int x, int y, int itemID)
-    {
+    private void renderItemAsIcon(int x, int y, int itemID) {
         renderBackgroundIcon(x + 1, y + 1);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
         Lighting.enableInventoryLight();
         Item item = Item.itemsList[itemID];
-        ItemModelDispatcher.getInstance().getDispatch(item).renderGui(Tessellator.instance, null, item.getDefaultStack(), x + 2, y + 2, 1f, 1f, 1f);
+        ItemModelDispatcher.getInstance().getDispatch(item).renderGui(GLRenderer.getTessellator(), null, item.getDefaultStack(), x + 2, y + 2, LightmapHelper.getLightmapCoord(15, 15), 1f);
         Lighting.disable();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 
-    private void renderBackgroundIcon(int x, int y)
-    {
-        GL11.glColor4f(1f, 1f, 1f, 1f);
+    private void renderBackgroundIcon(int x, int y) {
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
         drawGuiIcon(x, y, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/slot"));
     }
 
-    abstract class StatsSelectionList extends ScrolledSelectionList
-    {
+    abstract class StatsSelectionList extends ScrolledSelectionList {
         protected int clickedColumn;
         protected List<StatItem> statsList;
         protected Comparator<StatItem> statsSorter;
         public int sortingColumn;
         public int sortingMode;
 
-        protected StatsSelectionList()
-        {
-            super(mc, width, height, 32, height - 64, 20);
-            clickedColumn = -1;
-            sortingColumn = -1;
-            sortingMode = 0;
+        protected StatsSelectionList() {
+            super(ScreenStats.this.mc, ScreenStats.this.width, ScreenStats.this.height, 32, ScreenStats.this.height - 64, 20);
+            this.clickedColumn = -1;
+            this.sortingColumn = -1;
+            this.sortingMode = 0;
             setRenderSelection(false);
             setRenderHeader(true, 20);
         }
 
         @Override
-        protected void selectItem(int itemIndex, boolean doubleClicked)
-        {
+        protected void selectItem(int itemIndex, boolean doubleClicked) {
         }
 
         @Override
-        protected boolean isSelectedItem(int itemIndex)
-        {
+        protected boolean isSelectedItem(int itemIndex) {
             return false;
         }
 
         @Override
-        protected void renderHoleBackground()
-        {
+        protected void renderHoleBackground() {
             renderBackground();
         }
 
         @Override
-        protected void renderHeader(int x, int y, Tessellator tessellator)
-        {
-            if(!Mouse.isButtonDown(0))
-            {
-                clickedColumn = -1;
+        protected void renderHeader(int x, int y, TessellatorGeneral tessellator) {
+            if (!Mouse.isButtonDown(0)) {
+                this.clickedColumn = -1;
             }
-            if(clickedColumn == 0) {
+            if (this.clickedColumn == 0) {
                 drawGuiIcon((x + COLUMN0_RIGHT) - STATS_ICON_SIZE + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/slot"));
             } else {
                 drawGuiIcon((x + COLUMN0_RIGHT) - STATS_ICON_SIZE, y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/slot_raised"));
             }
-            if(clickedColumn == 1) {
+            if (this.clickedColumn == 1) {
                 drawGuiIcon((x + COLUMN1_RIGHT) - STATS_ICON_SIZE + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/slot"));
             } else {
                 drawGuiIcon((x + COLUMN1_RIGHT) - STATS_ICON_SIZE, y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/slot_raised"));
             }
-            if(clickedColumn == 2) {
+            if (this.clickedColumn == 2) {
                 drawGuiIcon((x + COLUMN2_RIGHT) - STATS_ICON_SIZE + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/slot"));
             } else {
                 drawGuiIcon((x + COLUMN2_RIGHT) - STATS_ICON_SIZE, y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/slot_raised"));
             }
-            if(sortingColumn != -1)
-            {
+            if (this.sortingColumn != -1) {
                 int c = COLUMN0_RIGHT - COLUMN_BUTTON_SIZE;
                 boolean up = false;
-                if(sortingColumn == 1)
-                {
+                if (this.sortingColumn == 1) {
                     c = COLUMN1_RIGHT - COLUMN_BUTTON_SIZE;
-                } else if(sortingColumn == 2)
-                {
+                } else if (this.sortingColumn == 2) {
                     c = COLUMN2_RIGHT - COLUMN_BUTTON_SIZE;
                 }
-                if(sortingMode == 1)
-                {
+                if (this.sortingMode == 1) {
                     up = true;
                 }
                 drawGuiIcon(x + c, y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/arrow_" + (up ? "up" : "down")));
@@ -198,222 +171,190 @@ public class ScreenStats extends Screen {
         }
 
         @Override
-        protected void clickedHeader(int x, int y)
-        {
-            clickedColumn = -1;
-            if(x >= COLUMN0_RIGHT - COLUMN_BUTTON_SIZE && x < COLUMN0_RIGHT)
-            {
-                clickedColumn = 0;
-            } else
-            if(x >= COLUMN1_RIGHT - COLUMN_BUTTON_SIZE && x < COLUMN1_RIGHT)
-            {
-                clickedColumn = 1;
-            } else
-            if(x >= COLUMN2_RIGHT - COLUMN_BUTTON_SIZE && x < COLUMN2_RIGHT)
-            {
-                clickedColumn = 2;
+        protected void clickedHeader(int x, int y) {
+            this.clickedColumn = -1;
+            if (x >= COLUMN0_RIGHT - COLUMN_BUTTON_SIZE && x < COLUMN0_RIGHT) {
+                this.clickedColumn = 0;
+            } else if (x >= COLUMN1_RIGHT - COLUMN_BUTTON_SIZE && x < COLUMN1_RIGHT) {
+                this.clickedColumn = 1;
+            } else if (x >= COLUMN2_RIGHT - COLUMN_BUTTON_SIZE && x < COLUMN2_RIGHT) {
+                this.clickedColumn = 2;
             }
-            if(clickedColumn >= 0)
-            {
-                clickedColumn(clickedColumn);
-                mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
+            if (this.clickedColumn >= 0) {
+                clickedColumn(this.clickedColumn);
+                ScreenStats.this.mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
             }
         }
 
         @Override
-        protected final int getItemCount()
-        {
-            return statsList.size();
+        protected final int getItemCount() {
+            return this.statsList.size();
         }
 
-        protected final StatItem getStat(int index)
-        {
-            return statsList.get(index);
+        protected final StatItem getStat(int index) {
+            return this.statsList.get(index);
         }
 
         protected abstract String getTooltipKey(int column);
 
-        protected void renderStatValue(StatItem statItem, int x, int y, boolean white)
-        {
-            if(statItem != null)
-            {
-                String s = statItem.getFormattedValue(statsCounter.readStat(statItem));
-                drawStringShadow(fontRenderer, s, x - MathHelper.ceil(fontRenderer.stringWidthDouble(s)), y + 5, white ? 0xffffff : 0x909090);
-            } else
-            {
+        protected void renderStatValue(StatItem statItem, int x, int y, boolean white) {
+            if (statItem != null) {
+                String s = statItem.getFormattedValue(ScreenStats.this.statsCounter.readStat(statItem));
+                drawStringShadow(ScreenStats.this.fontRenderer, s, x - MathHelper.ceil(ScreenStats.this.fontRenderer.stringWidthDouble(s)), y + 5, white ? 0xffffff : 0x909090);
+            } else {
                 String s1 = "-";
-                drawStringShadow(fontRenderer, s1, x - MathHelper.ceil(fontRenderer.stringWidthDouble(s1)), y + 5, white ? 0xffffff : 0x909090);
+                drawStringShadow(ScreenStats.this.fontRenderer, s1, x - MathHelper.ceil(ScreenStats.this.fontRenderer.stringWidthDouble(s1)), y + 5, white ? 0xffffff : 0x909090);
             }
         }
 
         @Override
-        protected void renderDecorations(int x, int y)
-        {
-            GL11.glEnable(GL11.GL_TEXTURE_2D);
-            GL11.glShadeModel(GL11.GL_FLAT);
-            GL11.glEnable(GL11.GL_ALPHA_TEST);
-            if(y < y0 || y > y1)
-            {
-                return;
-            }
-            int row = getItemAtPosition(x, y);
-            int statsListLeft = width / 2 - 92 - 16;
-            if(row >= 0) { // If in darkened middle section (stats list)
-                if(x < statsListLeft + 40 || x > statsListLeft + 40 + 20) { // Return if not hovering over item icon column
+        protected void renderDecorations(int x, int y) {
+//            GL11.glEnable(GL11.GL_TEXTURE_2D);
+//            GL11.glShadeModel(GL11.GL_FLAT);
+//            GL11.glEnable(GL11.GL_ALPHA_TEST);
+            try {
+                GLRenderer.pushFrame();
+                GLRenderer.setShader(Shaders.INTERFACE);
+                if (y < this.y0 || y > this.y1) {
                     return;
                 }
-                StatItem statItem = getStat(row);
-                renderStatItemTooltip(statItem, x, y);
-            } else
-            {
-                String s;
-                if(x >= (statsListLeft + COLUMN0_RIGHT) - STATS_ICON_SIZE && x <= statsListLeft + COLUMN0_RIGHT) {
-                    s = getTooltipKey(0);
-                } else if(x >= (statsListLeft + COLUMN1_RIGHT) - STATS_ICON_SIZE && x <= statsListLeft + COLUMN1_RIGHT) {
-                    s = getTooltipKey(1);
-                } else if(x >= (statsListLeft + COLUMN2_RIGHT) - STATS_ICON_SIZE && x <= statsListLeft + COLUMN2_RIGHT) {
-                    s = getTooltipKey(2);
+                int row = getItemAtPosition(x, y);
+                int statsListLeft = ScreenStats.this.width / 2 - 92 - 16;
+                if (row >= 0) { // If in darkened middle section (stats list)
+                    if (x < statsListLeft + 40 || x > statsListLeft + 40 + 20) { // Return if not hovering over item icon column
+                        return;
+                    }
+                    StatItem statItem = getStat(row);
+                    renderStatItemTooltip(statItem, x, y);
                 } else {
-                    return;
+                    String s;
+                    if (x >= (statsListLeft + COLUMN0_RIGHT) - STATS_ICON_SIZE && x <= statsListLeft + COLUMN0_RIGHT) {
+                        s = getTooltipKey(0);
+                    } else if (x >= (statsListLeft + COLUMN1_RIGHT) - STATS_ICON_SIZE && x <= statsListLeft + COLUMN1_RIGHT) {
+                        s = getTooltipKey(1);
+                    } else if (x >= (statsListLeft + COLUMN2_RIGHT) - STATS_ICON_SIZE && x <= statsListLeft + COLUMN2_RIGHT) {
+                        s = getTooltipKey(2);
+                    } else {
+                        return;
+                    }
+                    s = I18n.getInstance().translateKey(s).trim();
+                    ScreenStats.this.tooltip.render(s, x, y, 8, -8);
                 }
-                s = I18n.getInstance().translateKey(s).trim();
-                tooltip.render(s, x, y, 8, -8);
+            } finally {
+                GLRenderer.popFrame();
             }
         }
 
-        protected void renderStatItemTooltip(StatItem statItem, int x, int y)
-        {
-            if(statItem == null) {
+        protected void renderStatItemTooltip(StatItem statItem, int x, int y) {
+            if (statItem == null) {
                 return;
             }
             Item item = statItem.getItem();
             String s = I18n.getInstance().translateKey(item.getKey() + ".name").trim();
-            tooltip.render(s, x, y, 8, -8);
+            ScreenStats.this.tooltip.render(s, x, y, 8, -8);
         }
 
-        protected void clickedColumn(int column)
-        {
-            if(column != sortingColumn)
-            {
-                sortingColumn = column;
-                sortingMode = -1;
-            } else if(sortingMode == -1)
-            {
-                sortingMode = 1;
+        protected void clickedColumn(int column) {
+            if (column != this.sortingColumn) {
+                this.sortingColumn = column;
+                this.sortingMode = -1;
+            } else if (this.sortingMode == -1) {
+                this.sortingMode = 1;
             } else {
-                sortingColumn = -1;
-                sortingMode = 0;
+                this.sortingColumn = -1;
+                this.sortingMode = 0;
             }
-            statsList.sort(statsSorter);
+            this.statsList.sort(this.statsSorter);
         }
     }
 
-    class GeneralStatisticsList extends ScrolledSelectionList
-    {
+    class GeneralStatisticsList extends ScrolledSelectionList {
 
-        public GeneralStatisticsList()
-        {
-            super(mc, width, height, 32, height - 64, 10);
+        public GeneralStatisticsList() {
+            super(ScreenStats.this.mc, ScreenStats.this.width, ScreenStats.this.height, 32, ScreenStats.this.height - 64, 10);
             setRenderSelection(false);
         }
 
         @Override
-        protected int getItemCount()
-        {
+        protected int getItemCount() {
             return StatList.basicStats.size();
         }
 
         @Override
-        protected void selectItem(int itemIndex, boolean doubleClicked)
-        {
+        protected void selectItem(int itemIndex, boolean doubleClicked) {
         }
 
         @Override
-        protected boolean isSelectedItem(int itemIndex)
-        {
+        protected boolean isSelectedItem(int itemIndex) {
             return false;
         }
 
         @Override
-        protected int getMaxPosition()
-        {
+        protected int getMaxPosition() {
             return getItemCount() * 10;
         }
 
         @Override
-        protected void renderHoleBackground()
-        {
+        protected void renderHoleBackground() {
             renderBackground();
         }
 
         @Override
-        protected void renderItem(int index, int x, int y, int height, Tessellator tessellator)
-        {
+        protected void renderItem(int index, int x, int y, int height, TessellatorGeneral tessellator) {
             Stat stat = StatList.basicStats.get(index);
-            drawStringShadow(fontRenderer, stat.getStatName(), x + 2, y + 1, index % 2 != 0 ? 0x909090 : 0xffffff);
-            String s = stat.getFormattedValue(statsCounter.readStat(stat));
-            drawStringShadow(fontRenderer, s, (x + 2 + 213) - MathHelper.ceil(fontRenderer.stringWidthDouble(s)), y + 1, index % 2 != 0 ? 0x909090 : 0xffffff);
+            drawStringShadow(ScreenStats.this.fontRenderer, stat.getStatName(), x + 2, y + 1, index % 2 != 0 ? 0x909090 : 0xffffff);
+            String s = stat.getFormattedValue(ScreenStats.this.statsCounter.readStat(stat));
+            drawStringShadow(ScreenStats.this.fontRenderer, s, (x + 2 + 213) - MathHelper.ceil(ScreenStats.this.fontRenderer.stringWidthDouble(s)), y + 1, index % 2 != 0 ? 0x909090 : 0xffffff);
         }
     }
 
-    public class ItemStatisticsList extends StatsSelectionList
-    {
+    public class ItemStatisticsList extends StatsSelectionList {
 
-        public ItemStatisticsList()
-        {
-            statsList = new ArrayList<>();
+        public ItemStatisticsList() {
+            this.statsList = new ArrayList<>();
             for (Stat stat : StatList.usedItemStats) {
                 StatItem statItem = (StatItem) stat;
                 boolean flag = false;
                 int i = statItem.getItemID();
                 Stat broken = statItem.getItem().getStat(StatList.STAT_DEPLETED);
                 Stat crafted = statItem.getItem().getStat(StatList.STAT_CRAFTED);
-                if (statsCounter.readStat(statItem) > 0) {
+                if (ScreenStats.this.statsCounter.readStat(statItem) > 0) {
                     flag = true;
-                } else if (broken != null && statsCounter.readStat(broken) > 0) {
+                } else if (broken != null && ScreenStats.this.statsCounter.readStat(broken) > 0) {
                     flag = true;
-                } else if (crafted != null && statsCounter.readStat(crafted) > 0) {
+                } else if (crafted != null && ScreenStats.this.statsCounter.readStat(crafted) > 0) {
                     flag = true;
                 }
                 if (flag) {
-                    statsList.add(statItem);
+                    this.statsList.add(statItem);
                 }
             }
-            statsSorter = (stat1, stat2) -> {
+            this.statsSorter = (stat1, stat2) -> {
                 int id1 = stat1.getItemID();
                 int id2 = stat2.getItemID();
                 Stat statbase1 = null;
                 Stat statbase2 = null;
-                if(sortingColumn == 0)
-                {
+                if (this.sortingColumn == 0) {
                     statbase1 = stat1.getItem().getStat(StatList.STAT_DEPLETED);
                     statbase2 = stat2.getItem().getStat(StatList.STAT_DEPLETED);
-                } else
-                if(sortingColumn == 1)
-                {
+                } else if (this.sortingColumn == 1) {
                     statbase1 = stat1.getItem().getStat(StatList.STAT_CRAFTED);
                     statbase2 = stat2.getItem().getStat(StatList.STAT_CRAFTED);
-                } else
-                if(sortingColumn == 2)
-                {
+                } else if (this.sortingColumn == 2) {
                     statbase1 = stat1.getItem().getStat(StatList.STAT_USED);
                     statbase2 = stat2.getItem().getStat(StatList.STAT_USED);
                 }
-                if(statbase1 != null || statbase2 != null)
-                {
-                    if(statbase1 == null)
-                    {
+                if (statbase1 != null || statbase2 != null) {
+                    if (statbase1 == null) {
                         return 1;
                     }
-                    if(statbase2 == null)
-                    {
+                    if (statbase2 == null) {
                         return -1;
                     }
-                    int k = statsCounter.readStat(statbase1);
-                    int l = statsCounter.readStat(statbase2);
-                    if(k != l)
-                    {
-                        return (k - l) * sortingMode;
+                    int k = ScreenStats.this.statsCounter.readStat(statbase1);
+                    int l = ScreenStats.this.statsCounter.readStat(statbase2);
+                    if (k != l) {
+                        return (k - l) * this.sortingMode;
                     }
                 }
                 return id1 - id2;
@@ -421,66 +362,52 @@ public class ScreenStats extends Screen {
         }
 
         @Override
-        protected void renderHeader(int x, int y, Tessellator tessellator)
-        {
+        protected void renderHeader(int x, int y, TessellatorGeneral tessellator) {
             super.renderHeader(x, y, tessellator);
-            if(clickedColumn == 0)
-            {
+            if (this.clickedColumn == 0) {
                 drawGuiIcon((x + COLUMN0_RIGHT) - STATS_ICON_SIZE + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/depleted"));
-            } else
-            {
+            } else {
                 drawGuiIcon((x + COLUMN0_RIGHT) - STATS_ICON_SIZE, y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/depleted"));
             }
-            if(clickedColumn == 1)
-            {
+            if (this.clickedColumn == 1) {
                 drawGuiIcon((x + COLUMN1_RIGHT) - STATS_ICON_SIZE + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/crafted"));
-            } else
-            {
+            } else {
                 drawGuiIcon((x + COLUMN1_RIGHT) - STATS_ICON_SIZE, y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/crafted"));
             }
-            if(clickedColumn == 2)
-            {
+            if (this.clickedColumn == 2) {
                 drawGuiIcon((x + COLUMN2_RIGHT) - STATS_ICON_SIZE + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/used"));
-            } else
-            {
+            } else {
                 drawGuiIcon((x + COLUMN2_RIGHT) - STATS_ICON_SIZE, y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/used"));
             }
         }
 
         @Override
-        protected void renderItem(int index, int x, int y, int height, Tessellator tessellator)
-        {
+        protected void renderItem(int index, int x, int y, int height, TessellatorGeneral tessellator) {
             StatItem statItem = getStat(index);
             int i1 = statItem.getItemID();
             renderItemAsIcon(x + 40, y, i1);
-            renderStatValue((StatItem)statItem.getItem().getStat(StatList.STAT_DEPLETED), x + COLUMN0_RIGHT, y, index % 2 == 0);
-            renderStatValue((StatItem)statItem.getItem().getStat(StatList.STAT_CRAFTED), x + COLUMN1_RIGHT, y, index % 2 == 0);
+            renderStatValue((StatItem) statItem.getItem().getStat(StatList.STAT_DEPLETED), x + COLUMN0_RIGHT, y, index % 2 == 0);
+            renderStatValue((StatItem) statItem.getItem().getStat(StatList.STAT_CRAFTED), x + COLUMN1_RIGHT, y, index % 2 == 0);
             renderStatValue(statItem, x + COLUMN2_RIGHT, y, index % 2 == 0);
         }
 
         @Override
-        protected String getTooltipKey(int column)
-        {
-            if(column == 1)
-            {
+        protected String getTooltipKey(int column) {
+            if (column == 1) {
                 return "stat.crafted";
             }
-            if(column == 2)
-            {
+            if (column == 2) {
                 return "stat.used";
-            } else
-            {
+            } else {
                 return "stat.depleted";
             }
         }
     }
 
-    public class BlockStatisticsList extends StatsSelectionList
-    {
+    public class BlockStatisticsList extends StatsSelectionList {
 
-        public BlockStatisticsList()
-        {
-            statsList = new ArrayList<>();
+        public BlockStatisticsList() {
+            this.statsList = new ArrayList<>();
             for (Stat stat : Objects.requireNonNull(Item.getStats(StatList.STAT_MINED))) {
                 StatItem statItem = (StatItem) stat;
                 boolean flag = false;
@@ -488,48 +415,43 @@ public class ScreenStats extends Screen {
                 Stat used = statItem.getItem().getStat(StatList.STAT_USED);
                 Stat crafted = statItem.getItem().getStat(StatList.STAT_CRAFTED);
 
-                if (statsCounter.readStat(statItem) > 0) {
+                if (ScreenStats.this.statsCounter.readStat(statItem) > 0) {
                     flag = true;
-                } else if (used != null && statsCounter.readStat(used) > 0) {
+                } else if (used != null && ScreenStats.this.statsCounter.readStat(used) > 0) {
                     flag = true;
-                } else if (crafted != null && statsCounter.readStat(crafted) > 0) {
+                } else if (crafted != null && ScreenStats.this.statsCounter.readStat(crafted) > 0) {
                     flag = true;
                 }
                 if (flag) {
-                    statsList.add(statItem);
+                    this.statsList.add(statItem);
                 }
             }
-            statsSorter = (stat1, stat2) -> {
+            this.statsSorter = (stat1, stat2) -> {
                 int id1 = stat1.getItemID();
                 int id2 = stat2.getItemID();
                 Stat statbase1 = null;
                 Stat statbase2 = null;
-                if(sortingColumn == 2)
-                {
+                if (this.sortingColumn == 2) {
                     statbase1 = stat1.getItem().getStat(StatList.STAT_MINED);
                     statbase2 = stat2.getItem().getStat(StatList.STAT_MINED);
-                } else if(sortingColumn == 0) {
+                } else if (this.sortingColumn == 0) {
                     statbase1 = stat1.getItem().getStat(StatList.STAT_CRAFTED);
                     statbase2 = stat2.getItem().getStat(StatList.STAT_CRAFTED);
-                } else if(sortingColumn == 1) {
+                } else if (this.sortingColumn == 1) {
                     statbase1 = stat1.getItem().getStat(StatList.STAT_USED);
                     statbase2 = stat2.getItem().getStat(StatList.STAT_USED);
                 }
-                if(statbase1 != null || statbase2 != null)
-                {
-                    if(statbase1 == null)
-                    {
+                if (statbase1 != null || statbase2 != null) {
+                    if (statbase1 == null) {
                         return 1;
                     }
-                    if(statbase2 == null)
-                    {
+                    if (statbase2 == null) {
                         return -1;
                     }
-                    int k = statsCounter.readStat(statbase1);
-                    int l = statsCounter.readStat(statbase2);
-                    if(k != l)
-                    {
-                        return (k - l) * sortingMode;
+                    int k = ScreenStats.this.statsCounter.readStat(statbase1);
+                    int l = ScreenStats.this.statsCounter.readStat(statbase2);
+                    if (k != l) {
+                        return (k - l) * this.sortingMode;
                     }
                 }
                 return id1 - id2;
@@ -538,35 +460,27 @@ public class ScreenStats extends Screen {
         }
 
         @Override
-        protected void renderHeader(int x, int y, Tessellator tessellator)
-        {
+        protected void renderHeader(int x, int y, TessellatorGeneral tessellator) {
             super.renderHeader(x, y, tessellator);
-            if(clickedColumn == 0)
-            {
+            if (this.clickedColumn == 0) {
                 drawGuiIcon((x + COLUMN0_RIGHT) - STATS_ICON_SIZE + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/crafted"));
-            } else
-            {
+            } else {
                 drawGuiIcon((x + COLUMN0_RIGHT) - STATS_ICON_SIZE, y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/crafted"));
             }
-            if(clickedColumn == 1)
-            {
+            if (this.clickedColumn == 1) {
                 drawGuiIcon(((x + COLUMN1_RIGHT) - STATS_ICON_SIZE) + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/used"));
-            } else
-            {
+            } else {
                 drawGuiIcon(((x + COLUMN1_RIGHT) - STATS_ICON_SIZE), y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/used"));
             }
-            if(clickedColumn == 2)
-            {
+            if (this.clickedColumn == 2) {
                 drawGuiIcon(((x + COLUMN2_RIGHT) - STATS_ICON_SIZE) + 1, y + 2, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/mined"));
-            } else
-            {
+            } else {
                 drawGuiIcon(((x + COLUMN2_RIGHT) - STATS_ICON_SIZE), y + 1, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/stats/mined"));
             }
         }
 
         @Override
-        protected void renderItem(int index, int x, int y, int height, Tessellator tessellator)
-        {
+        protected void renderItem(int index, int x, int y, int height, TessellatorGeneral tessellator) {
             StatItem statItem = getStat(index);
             int id = statItem.getItem().id;
             renderItemAsIcon(x + 40, y, id);
@@ -576,17 +490,13 @@ public class ScreenStats extends Screen {
         }
 
         @Override
-        protected String getTooltipKey(int column)
-        {
-            if(column == 0)
-            {
+        protected String getTooltipKey(int column) {
+            if (column == 0) {
                 return "stat.crafted";
             }
-            if(column == 1)
-            {
+            if (column == 1) {
                 return "stat.used";
-            } else
-            {
+            } else {
                 return "stat.mined";
             }
         }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScreenTextureViewer.java b/game/client/src/main/java/net/minecraft/client/gui/ScreenTextureViewer.java
index 3d30cc8d5..0aed5225e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScreenTextureViewer.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScreenTextureViewer.java
@@ -4,25 +4,21 @@ import it.unimi.dsi.fastutil.ints.IntList;
 import net.minecraft.client.GLAllocation;
 import net.minecraft.client.gui.modelviewer.elements.ListenerButtonElement;
 import net.minecraft.client.gui.modelviewer.elements.IListenerElement;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.client.util.helper.FileOpener;
 import net.minecraft.client.util.helper.Textures;
 import net.minecraft.core.lang.I18n;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
+import org.lwjgl.opengl.GL41;
 
 import java.io.File;
 import java.util.ArrayList;
 import java.util.List;
 
-import static org.lwjgl.opengl.GL11.GL_BLEND;
-import static org.lwjgl.opengl.GL11.GL_TEXTURE_2D;
-import static org.lwjgl.opengl.GL11.GL_TEXTURE_HEIGHT;
-import static org.lwjgl.opengl.GL11.GL_TEXTURE_WIDTH;
-import static org.lwjgl.opengl.GL11.glGetTexLevelParameteri;
-
 public class ScreenTextureViewer extends Screen {
     private static final int TOP_SPACING = 24;
     private static final int BUTTON_SPACING = 4;
@@ -43,134 +39,132 @@ public class ScreenTextureViewer extends Screen {
     }
 
     @Override
-    public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
-    {
+    public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
         if (eventKey == Keyboard.KEY_LEFT) {
             cycleTexture(-1);
         } else if (eventKey == Keyboard.KEY_RIGHT) {
             cycleTexture(1);
         } else if (eventKey == Keyboard.KEY_ESCAPE) {
-            mc.displayScreen(parentScreen);
+            this.mc.displayScreen(this.parentScreen);
         }
-        List<ButtonElement> _buttons = new ArrayList<>(buttons);
-        for (ButtonElement button : _buttons){
-            if (button instanceof IListenerElement && button.isHovered(mx, my)){
+        List<ButtonElement> _buttons = new ArrayList<>(this.buttons);
+        for (ButtonElement button : _buttons) {
+            if (button instanceof IListenerElement && button.isHovered(mx, my)) {
                 ((IListenerElement<?>) button).onKeyTyped(eventCharacter, eventKey);
             }
         }
     }
+
     @Override
-    public void tick(){
-        List<ButtonElement> _buttons = new ArrayList<>(buttons);
-        for (ButtonElement button : _buttons){
-            if (button instanceof ListenerButtonElement){
+    public void tick() {
+        List<ButtonElement> _buttons = new ArrayList<>(this.buttons);
+        for (ButtonElement button : _buttons) {
+            if (button instanceof ListenerButtonElement) {
                 ((ListenerButtonElement) button).tick();
             }
         }
     }
-    public void init()
-    {
 
-        top = TOP_SPACING;
-        bottom = height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
-        add(new ListenerButtonElement(0, width/2 - 100, height - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.options.button.done")).setActionListener(() -> {
+    public void init() {
+
+        this.top = TOP_SPACING;
+        this.bottom = this.height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
+        add(new ListenerButtonElement(0, this.width / 2 - 100, this.height - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.options.button.done")).setActionListener(() -> {
             removed();
-            mc.displayScreen(null);
+            this.mc.displayScreen(null);
         }));
 
-        leftTexCycle = add(new ListenerButtonElement(1, width - (20 + BUTTON_SPACING) * 2, bottom - (BUTTON_SPACING + 20), 20, 20, "<")
+        this.leftTexCycle = add(new ListenerButtonElement(1, this.width - (20 + BUTTON_SPACING) * 2, this.bottom - (BUTTON_SPACING + 20), 20, 20, "<")
             .setActionListener(() -> cycleTexture(-1)));
-        add(new ListenerButtonElement(2, width - (20 + BUTTON_SPACING) * 1, bottom - (BUTTON_SPACING + 20), 20, 20, ">")
+        add(new ListenerButtonElement(2, this.width - (20 + BUTTON_SPACING), this.bottom - (BUTTON_SPACING + 20), 20, 20, ">")
             .setActionListener(() -> cycleTexture(1)));
 
-        add(new ListenerButtonElement(11, BUTTON_SPACING, bottom - BUTTON_SPACING - 20, 20, 20, "V")
-            .setActionListener(() -> drawCheckers = !drawCheckers)
+        add(new ListenerButtonElement(11, BUTTON_SPACING, this.bottom - BUTTON_SPACING - 20, 20, 20, "V")
+            .setActionListener(() -> this.drawCheckers = !this.drawCheckers)
         );
-        add(new ListenerButtonElement(11, 20 + BUTTON_SPACING * 2, bottom - BUTTON_SPACING - 20, 20, 20, "F")
-            .setActionListener(() -> flip = !flip)
+        add(new ListenerButtonElement(11, 20 + BUTTON_SPACING * 2, this.bottom - BUTTON_SPACING - 20, 20, 20, "F")
+            .setActionListener(() -> this.flip = !this.flip)
         );
-        add(new ListenerButtonElement(12, 40 + BUTTON_SPACING * 3, bottom - BUTTON_SPACING - 20, 20, 20, "D")
+        add(new ListenerButtonElement(12, 40 + BUTTON_SPACING * 3, this.bottom - BUTTON_SPACING - 20, 20, 20, "D")
             .setActionListener(() -> {
                 Textures.dumpTextures();
                 FileOpener.open(new File("dumpTextures"));
             })
         );
-        add(new ListenerButtonElement(13, 60 + BUTTON_SPACING * 4, bottom - BUTTON_SPACING - 20, 20, 20, "T")
-            .setActionListener(() -> drawText = !drawText)
+        add(new ListenerButtonElement(13, 60 + BUTTON_SPACING * 4, this.bottom - BUTTON_SPACING - 20, 20, 20, "T")
+            .setActionListener(() -> this.drawText = !this.drawText)
         );
     }
 
-    protected void buttonClicked(@NotNull ButtonElement button)
-    {
+    protected void buttonClicked(@NotNull ButtonElement button) {
     }
 
-    protected void buttonReleased(@NotNull ButtonElement button)
-    {
+    protected void buttonReleased(@NotNull ButtonElement button) {
     }
 
     protected void cycleTexture(int offset) {
         IntList textureList = GLAllocation.textureNames;
-        texIndex += offset;
-        if (texIndex < 0) {
-            texIndex += textureList.size();
+        this.texIndex += offset;
+        if (this.texIndex < 0) {
+            this.texIndex += textureList.size();
         }
-        texIndex = texIndex % textureList.size();
+        this.texIndex = this.texIndex % textureList.size();
     }
 
     public void render(int mx, int my, float partialTick) {
         renderBackground();
 
-        drawStringCenteredNoShadow(fontRenderer, I18n.getInstance().translateKey("gui.texture_viewer.label.title"), width/2, 5, 0xFFFFFF);
+        drawStringCenteredNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.texture_viewer.label.title"), this.width / 2, 5, 0xFFFFFF);
 
         IntList textureList = GLAllocation.textureNames;
-        int id = texIndex % textureList.size();
-        GL11.glBindTexture(GL_TEXTURE_2D, textureList.getInt(id));
-
-        Texture t = mc.textureManager.idToTextureMap.get(textureList.getInt(id));
+        int id = this.texIndex % textureList.size();
+        GL41.glBindTexture(GL41.GL_TEXTURE_2D, textureList.getInt(id));
 
+        Texture t = this.mc.textureManager.idToTextureMap.get(textureList.getInt(id));
 
-        GL11.glEnable(GL_BLEND);
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.enableState(State.DEPTH_TEST);
 
-        int texWidth = glGetTexLevelParameteri(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH);
-        int texHeight = glGetTexLevelParameteri(GL_TEXTURE_2D, 0, GL_TEXTURE_HEIGHT);
+        int texWidth = GL41.glGetTexLevelParameteri(GL41.GL_TEXTURE_2D, 0, GL41.GL_TEXTURE_WIDTH);
+        int texHeight = GL41.glGetTexLevelParameteri(GL41.GL_TEXTURE_2D, 0, GL41.GL_TEXTURE_HEIGHT);
         double ratio = (double) texWidth / texHeight;
 
-        double imgHeight = (bottom - top - 40d);
+        double imgHeight = (this.bottom - this.top - 40d);
         double imgWidth = imgHeight * ratio;
 
-        if (imgWidth > width * 0.75) {
-            imgWidth = width * 0.75f;
-            imgHeight = imgWidth/ratio;
+        if (imgWidth > this.width * 0.75) {
+            imgWidth = this.width * 0.75f;
+            imgHeight = imgWidth / ratio;
         }
 
-        double x = (width - imgWidth)/2;
-        double y = (height - imgHeight)/2;
+        double x = (this.width - imgWidth) / 2;
+        double y = (this.height - imgHeight) / 2;
 
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
 
-        if (drawCheckers) {
-            mc.textureManager.bindTexture(mc.textureManager.loadTexture("/assets/minecraft/textures/gui/designer_bg.png"));
+        if (this.drawCheckers) {
+            this.mc.textureManager.bindTexture(this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/designer_bg.png"));
             tessellator.startDrawingQuads();
-            tessellator.addVertexWithUV(x + 0,         y + imgHeight,   zLevel, 0,          imgHeight/2);
-            tessellator.addVertexWithUV(x + imgWidth,  y + imgHeight,   zLevel, imgWidth/2, imgHeight/2);
-            tessellator.addVertexWithUV(x + imgWidth,  y + 0,           zLevel, imgWidth/2, 0);
-            tessellator.addVertexWithUV(x + 0,         y + 0,           zLevel, 0,          0);
+            tessellator.addVertexWithUV(x + 0, y + imgHeight, this.zLevel, 0, imgHeight / 2);
+            tessellator.addVertexWithUV(x + imgWidth, y + imgHeight, this.zLevel, imgWidth / 2, imgHeight / 2);
+            tessellator.addVertexWithUV(x + imgWidth, y + 0, this.zLevel, imgWidth / 2, 0);
+            tessellator.addVertexWithUV(x + 0, y + 0, this.zLevel, 0, 0);
             tessellator.draw();
         }
 
-        GL11.glBindTexture(GL_TEXTURE_2D, textureList.getInt(id));
+        GL41.glBindTexture(GL41.GL_TEXTURE_2D, textureList.getInt(id));
         tessellator.startDrawingQuads();
-        if (flip) {
-            tessellator.addVertexWithUV(x + 0,          y + imgHeight,  zLevel, 0, 0);
-            tessellator.addVertexWithUV(x + imgWidth,   y + imgHeight,  zLevel, 1, 0);
-            tessellator.addVertexWithUV(x + imgWidth,   y + 0,          zLevel, 1, 1);
-            tessellator.addVertexWithUV(x + 0,          y + 0,          zLevel, 0, 1);
+        if (this.flip) {
+            tessellator.addVertexWithUV(x + 0, y + imgHeight, this.zLevel, 0, 0);
+            tessellator.addVertexWithUV(x + imgWidth, y + imgHeight, this.zLevel, 1, 0);
+            tessellator.addVertexWithUV(x + imgWidth, y + 0, this.zLevel, 1, 1);
+            tessellator.addVertexWithUV(x + 0, y + 0, this.zLevel, 0, 1);
         } else {
-            tessellator.addVertexWithUV(x + 0,          y + imgHeight,  zLevel, 0, 1);
-            tessellator.addVertexWithUV(x + imgWidth,   y + imgHeight,  zLevel, 1, 1);
-            tessellator.addVertexWithUV(x + imgWidth,   y + 0,          zLevel, 1, 0);
-            tessellator.addVertexWithUV(x + 0,          y + 0,          zLevel, 0, 0);
+            tessellator.addVertexWithUV(x + 0, y + imgHeight, this.zLevel, 0, 1);
+            tessellator.addVertexWithUV(x + imgWidth, y + imgHeight, this.zLevel, 1, 1);
+            tessellator.addVertexWithUV(x + imgWidth, y + 0, this.zLevel, 1, 0);
+            tessellator.addVertexWithUV(x + 0, y + 0, this.zLevel, 0, 0);
         }
 
         tessellator.draw();
@@ -185,12 +179,12 @@ public class ScreenTextureViewer extends Screen {
 
         super.render(mx, my, partialTick);
 
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
+        GLRenderer.disableState(State.DEPTH_TEST);
 
-        if (drawText) {
-            drawStringShadow(this.fontRenderer, "Tex ID: " + id , 1, top + 1, 0xFFFFFF);
-            drawStringShadow(this.fontRenderer, "Tex Width: " + texWidth, 1, top + 11, 0xFFFFFF);
-            drawStringShadow(this.fontRenderer, "Tex Height: " + texHeight, 1, top + 21, 0xFFFFFF);
+        if (this.drawText) {
+            drawStringShadow(this.fontRenderer, "Tex ID: " + id, 1, this.top + 1, 0xFFFFFF);
+            drawStringShadow(this.fontRenderer, "Tex Width: " + texWidth, 1, this.top + 11, 0xFFFFFF);
+            drawStringShadow(this.fontRenderer, "Tex Height: " + texHeight, 1, this.top + 21, 0xFFFFFF);
 
             String s;
             if (t == null) {
@@ -199,37 +193,36 @@ public class ScreenTextureViewer extends Screen {
                 s = t.toString();
             }
             String[] lines = s.split("\n");
-            int yOff = top + 31;
+            int yOff = this.top + 31;
             for (String line : lines) {
-                drawStringShadow(fontRenderer, line, 1, yOff, 0xFFFFFF);
+                drawStringShadow(this.fontRenderer, line, 1, yOff, 0xFFFFFF);
                 yOff += 10;
             }
         }
+        GLRenderer.popFrame();
     }
+
     @Override
     public void renderBackground() {
         super.renderBackground();
 
-        if (mc.currentWorld == null)
-        {
-            Tessellator tessellator = Tessellator.instance;
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        if (this.mc.currentWorld == null) {
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
             float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x202020);
+            tessellator.setColorOpaque1i(0x202020);
 
-            tessellator.addVertexWithUV(0,      bottom, 0.0D,   0,              bottom / scale);
-            tessellator.addVertexWithUV(width,  bottom, 0.0D,   width / scale,  bottom / scale);
-            tessellator.addVertexWithUV(width,  top,    0.0D,   width / scale,  top / scale);
-            tessellator.addVertexWithUV(0,      top,    0.0D,   0,              top / scale);
+            tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0, this.bottom / scale);
+            tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, this.width / scale, this.bottom / scale);
+            tessellator.addVertexWithUV(this.width, this.top, 0.0D, this.width / scale, this.top / scale);
+            tessellator.addVertexWithUV(0, this.top, 0.0D, 0, this.top / scale);
 
             tessellator.draw();
-        }
-        else
-        {
-            drawRect(0, 0, width, top, 0x5F000000);
-            drawRect(0, bottom, width, height, 0x5F000000);
+        } else {
+            drawRect(0, 0, this.width, this.top, 0x5F000000);
+            drawRect(0, this.bottom, this.width, this.height, 0x5F000000);
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/ScrolledSelectionList.java b/game/client/src/main/java/net/minecraft/client/gui/ScrolledSelectionList.java
index 18840ac6d..88681190c 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/ScrolledSelectionList.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/ScrolledSelectionList.java
@@ -1,10 +1,13 @@
 package net.minecraft.client.gui;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 public abstract class ScrolledSelectionList {
     private final Minecraft minecraft;
@@ -25,17 +28,17 @@ public abstract class ScrolledSelectionList {
     private int headerHeight;
 
     public ScrolledSelectionList(Minecraft minecraft, int width, int height, int y0, int y1, int itemHeight) {
-        yDrag = -2F;
-        selectedElement = -1;
-        lastClicked = 0L;
-        renderSelection = true;
+        this.yDrag = -2F;
+        this.selectedElement = -1;
+        this.lastClicked = 0L;
+        this.renderSelection = true;
         this.minecraft = minecraft;
         this.width = width;
         this.height = height;
         this.y0 = y0;
         this.y1 = y1;
         this.itemHeight = itemHeight;
-        x1 = width;
+        this.x1 = width;
     }
 
     public void setRenderSelection(boolean renderSelection) {
@@ -57,14 +60,14 @@ public abstract class ScrolledSelectionList {
     protected abstract boolean isSelectedItem(int itemIndex);
 
     protected int getMaxPosition() {
-        return getItemCount() * itemHeight + headerHeight;
+        return getItemCount() * this.itemHeight + this.headerHeight;
     }
 
     protected abstract void renderHoleBackground();
 
-    protected abstract void renderItem(int index, int x, int y, int height, Tessellator tessellator);
+    protected abstract void renderItem(int index, int x, int y, int height, TessellatorGeneral tessellator);
 
-    protected void renderHeader(int x, int y, Tessellator tessellator) {
+    protected void renderHeader(int x, int y, TessellatorGeneral tessellator) {
     }
 
     protected void clickedHeader(int x, int y) {
@@ -74,10 +77,10 @@ public abstract class ScrolledSelectionList {
     }
 
     public int getItemAtPosition(int x, int y) {
-        int xMin = width / 2 - 110;
-        int xMax = width / 2 + 110;
-        int yMin = ((y - y0 - headerHeight) + (int) amountScrolled) - 4;
-        int yMax = yMin / itemHeight;
+        int xMin = this.width / 2 - 110;
+        int xMax = this.width / 2 + 110;
+        int yMin = ((y - this.y0 - this.headerHeight) + (int) this.amountScrolled) - 4;
+        int yMax = yMin / this.itemHeight;
         if (x >= xMin && x <= xMax && yMax >= 0 && yMin >= 0 && yMax < getItemCount()) {
             return yMax;
         } else {
@@ -86,204 +89,204 @@ public abstract class ScrolledSelectionList {
     }
 
     private void capYPosition() {
-        int maxAmountScrolled = getMaxPosition() - (y1 - y0 - 4);
+        int maxAmountScrolled = getMaxPosition() - (this.y1 - this.y0 - 4);
         if (maxAmountScrolled < 0) {
             maxAmountScrolled /= 2;
         }
-        if (amountScrolled < 0.0F) {
-            amountScrolled = 0.0F;
+        if (this.amountScrolled < 0.0F) {
+            this.amountScrolled = 0.0F;
         }
-        if (amountScrolled > (float) maxAmountScrolled) {
-            amountScrolled = maxAmountScrolled;
+        if (this.amountScrolled > (float) maxAmountScrolled) {
+            this.amountScrolled = maxAmountScrolled;
         }
     }
 
     public void render(int x, int y, float partialTicks) {
         renderHoleBackground();
         int numItems = getItemCount();
-        int scrollbarLeft = width / 2 + 124;
+        int scrollbarLeft = this.width / 2 + 124;
         int scrollbarRight = scrollbarLeft + 6;
-        if (minecraft.controllerInput != null) {
-            if (Math.abs(minecraft.controllerInput.joyRight.getY()) > 0.1f) {
-                amountScrolled += minecraft.controllerInput.joyRight.getY();
+        if (this.minecraft.controllerInput != null) {
+            if (Math.abs(this.minecraft.controllerInput.joyRight.getY()) > 0.1f) {
+                this.amountScrolled += this.minecraft.controllerInput.joyRight.getY();
             }
         }
-        if (Mouse.isButtonDown(0) || (minecraft.controllerInput != null && minecraft.controllerInput.buttonA.isPressed())) {
-            if (yDrag == -1F) {
+        if (Mouse.isButtonDown(0) || (this.minecraft.controllerInput != null && this.minecraft.controllerInput.buttonA.isPressed())) {
+            if (this.yDrag == -1F) {
                 boolean flag = true;
-                if (y >= y0 && y <= y1) {
-                    int left = width / 2 - 110;
-                    int right = width / 2 + 110;
-                    int i2 = ((y - y0 - headerHeight) + (int) amountScrolled) - 4;
-                    int k2 = i2 / itemHeight;
+                if (y >= this.y0 && y <= this.y1) {
+                    int left = this.width / 2 - 110;
+                    int right = this.width / 2 + 110;
+                    int i2 = ((y - this.y0 - this.headerHeight) + (int) this.amountScrolled) - 4;
+                    int k2 = i2 / this.itemHeight;
                     if (x >= left && x <= right && k2 >= 0 && i2 >= 0 && k2 < numItems) {
-                        boolean flag1 = k2 == selectedElement && System.currentTimeMillis() - lastClicked < 250L;
+                        boolean flag1 = k2 == this.selectedElement && System.currentTimeMillis() - this.lastClicked < 250L;
                         selectItem(k2, flag1);
-                        selectedElement = k2;
-                        lastClicked = System.currentTimeMillis();
+                        this.selectedElement = k2;
+                        this.lastClicked = System.currentTimeMillis();
                     } else if (x >= left && x <= right && i2 < 0) {
-                        clickedHeader(x - left, ((y - y0) + (int) amountScrolled) - 4);
+                        clickedHeader(x - left, ((y - this.y0) + (int) this.amountScrolled) - 4);
                         flag = false;
                     }
                     if (x >= scrollbarLeft && x <= scrollbarRight && getMaxPosition() != 0) {
-                        scrollMultiplier = -1F;
-                        int i3 = getMaxPosition() - (y1 - y0 - 4);
+                        this.scrollMultiplier = -1F;
+                        int i3 = getMaxPosition() - (this.y1 - this.y0 - 4);
                         if (i3 < 1) {
                             i3 = 1;
                         }
-                        int l3 = (int) ((float) ((y1 - y0) * (y1 - y0)) / (float) getMaxPosition());
+                        int l3 = (int) ((float) ((this.y1 - this.y0) * (this.y1 - this.y0)) / (float) getMaxPosition());
                         if (l3 < 32) {
                             l3 = 32;
                         }
-                        if (l3 > y1 - y0 - 8) {
-                            l3 = y1 - y0 - 8;
+                        if (l3 > this.y1 - this.y0 - 8) {
+                            l3 = this.y1 - this.y0 - 8;
                         }
-                        scrollMultiplier /= (float) (y1 - y0 - l3) / (float) i3;
+                        this.scrollMultiplier /= (float) (this.y1 - this.y0 - l3) / (float) i3;
                     } else {
-                        scrollMultiplier = 1.0F;
+                        this.scrollMultiplier = 1.0F;
                     }
                     if (flag) {
-                        yDrag = y;
+                        this.yDrag = y;
                     } else {
-                        yDrag = -2F;
+                        this.yDrag = -2F;
                     }
                 } else {
-                    yDrag = -2F;
+                    this.yDrag = -2F;
                 }
-            } else if (yDrag >= 0.0F) {
-                amountScrolled -= ((float) y - yDrag) * scrollMultiplier;
-                yDrag = y;
+            } else if (this.yDrag >= 0.0F) {
+                this.amountScrolled -= ((float) y - this.yDrag) * this.scrollMultiplier;
+                this.yDrag = y;
             }
         } else {
-            yDrag = -1F;
+            this.yDrag = -1F;
         }
-        amountScrolled -= Mouse.getDWheel() * 20f;
+        this.amountScrolled -= Mouse.getDWheel() * 20f;
 
         capYPosition();
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_FOG);
-        Tessellator tessellator = Tessellator.instance;
-        minecraft.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.globalSetLightEnabled(false);
+//        GL11.glDisable(GL11.GL_FOG);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        this.minecraft.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         float f1 = 32F;
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0x202020);
-        tessellator.addVertexWithUV(x0, y1, 0.0D, (float) x0 / f1, (float) (y1 + (int) amountScrolled) / f1);
-        tessellator.addVertexWithUV(x1, y1, 0.0D, (float) x1 / f1, (float) (y1 + (int) amountScrolled) / f1);
-        tessellator.addVertexWithUV(x1, y0, 0.0D, (float) x1 / f1, (float) (y0 + (int) amountScrolled) / f1);
-        tessellator.addVertexWithUV(x0, y0, 0.0D, (float) x0 / f1, (float) (y0 + (int) amountScrolled) / f1);
+        tessellator.setColorOpaque1i(0x202020);
+        tessellator.addVertexWithUV(this.x0, this.y1, 0.0D, (float) this.x0 / f1, (float) (this.y1 + (int) this.amountScrolled) / f1);
+        tessellator.addVertexWithUV(this.x1, this.y1, 0.0D, (float) this.x1 / f1, (float) (this.y1 + (int) this.amountScrolled) / f1);
+        tessellator.addVertexWithUV(this.x1, this.y0, 0.0D, (float) this.x1 / f1, (float) (this.y0 + (int) this.amountScrolled) / f1);
+        tessellator.addVertexWithUV(this.x0, this.y0, 0.0D, (float) this.x0 / f1, (float) (this.y0 + (int) this.amountScrolled) / f1);
         tessellator.draw();
-        int ix = width / 2 - 92 - 16;
-        int j2 = (y0 + 4) - (int) amountScrolled;
-        if (renderHeader) {
+        int ix = this.width / 2 - 92 - 16;
+        int j2 = (this.y0 + 4) - (int) this.amountScrolled;
+        if (this.renderHeader) {
             renderHeader(ix, j2, tessellator);
         }
         for (int itemIndex = 0; itemIndex < numItems; itemIndex++) {
-            int iy = j2 + itemIndex * itemHeight + headerHeight;
-            int height = itemHeight - 4;
-            if (iy > y1 || iy + height < y0) {
+            int iy = j2 + itemIndex * this.itemHeight + this.headerHeight;
+            int height = this.itemHeight - 4;
+            if (iy > this.y1 || iy + height < this.y0) {
                 continue;
             }
-            if (renderSelection && isSelectedItem(itemIndex)) {
-                int minX = width / 2 - 110;
-                int maxX = width / 2 + 110;
-                GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-                GL11.glDisable(GL11.GL_TEXTURE_2D);
+            if (this.renderSelection && isSelectedItem(itemIndex)) {
+                int minX = this.width / 2 - 110;
+                int maxX = this.width / 2 + 110;
+                GLRenderer.pushFrame();
+                GLRenderer.setShader(Shaders.COLOR);
+                GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
                 tessellator.startDrawingQuads();
-                tessellator.setColorOpaque_I(0x808080);
+                tessellator.setColorOpaque1i(0x808080);
                 tessellator.addVertexWithUV(minX, iy + height + 2, 0.0D, 0.0D, 1.0D);
                 tessellator.addVertexWithUV(maxX, iy + height + 2, 0.0D, 1.0D, 1.0D);
                 tessellator.addVertexWithUV(maxX, iy - 2, 0.0D, 1.0D, 0.0D);
                 tessellator.addVertexWithUV(minX, iy - 2, 0.0D, 0.0D, 0.0D);
-                tessellator.setColorOpaque_I(0);
+                tessellator.setColorOpaque1i(0);
                 tessellator.addVertexWithUV(minX + 1, iy + height + 1, 0.0D, 0.0D, 1.0D);
                 tessellator.addVertexWithUV(maxX - 1, iy + height + 1, 0.0D, 1.0D, 1.0D);
                 tessellator.addVertexWithUV(maxX - 1, iy - 1, 0.0D, 1.0D, 0.0D);
                 tessellator.addVertexWithUV(minX + 1, iy - 1, 0.0D, 0.0D, 0.0D);
                 tessellator.draw();
-                GL11.glEnable(GL11.GL_TEXTURE_2D);
+                GLRenderer.popFrame();
             }
             renderItem(itemIndex, ix, iy, height, tessellator);
         }
 
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
+        GLRenderer.disableState(State.DEPTH_TEST);
         byte byte0 = 4;
-        renderHoleBackground(0, y0, 255, 255);
-        renderHoleBackground(y1, height, 255, 255);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glDisable(GL11.GL_ALPHA_TEST);
-        GL11.glShadeModel(GL11.GL_SMOOTH);
-        GL11.glDisable(GL11.GL_TEXTURE_2D);
+        renderHoleBackground(0, this.y0, 255, 255);
+        renderHoleBackground(this.y1, this.height, 255, 255);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+//        GL11.glDisable(GL11.GL_ALPHA_TEST);
+//        GL11.glShadeModel(GL11.GL_SMOOTH);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_I(0, 0);
-        tessellator.addVertexWithUV(x0, y0 + byte0, 0.0D, 0.0D, 1.0D);
-        tessellator.addVertexWithUV(x1, y0 + byte0, 0.0D, 1.0D, 1.0D);
-        tessellator.setColorRGBA_I(0, 255);
-        tessellator.addVertexWithUV(x1, y0, 0.0D, 1.0D, 0.0D);
-        tessellator.addVertexWithUV(x0, y0, 0.0D, 0.0D, 0.0D);
+        tessellator.setColor2i(0, 0);
+        tessellator.addVertexWithUV(this.x0, this.y0 + byte0, 0.0D, 0.0D, 1.0D);
+        tessellator.addVertexWithUV(this.x1, this.y0 + byte0, 0.0D, 1.0D, 1.0D);
+        tessellator.setColor2i(0, 255);
+        tessellator.addVertexWithUV(this.x1, this.y0, 0.0D, 1.0D, 0.0D);
+        tessellator.addVertexWithUV(this.x0, this.y0, 0.0D, 0.0D, 0.0D);
         tessellator.draw();
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_I(0, 255);
-        tessellator.addVertexWithUV(x0, y1, 0.0D, 0.0D, 1.0D);
-        tessellator.addVertexWithUV(x1, y1, 0.0D, 1.0D, 1.0D);
-        tessellator.setColorRGBA_I(0, 0);
-        tessellator.addVertexWithUV(x1, y1 - byte0, 0.0D, 1.0D, 0.0D);
-        tessellator.addVertexWithUV(x0, y1 - byte0, 0.0D, 0.0D, 0.0D);
+        tessellator.setColor2i(0, 255);
+        tessellator.addVertexWithUV(this.x0, this.y1, 0.0D, 0.0D, 1.0D);
+        tessellator.addVertexWithUV(this.x1, this.y1, 0.0D, 1.0D, 1.0D);
+        tessellator.setColor2i(0, 0);
+        tessellator.addVertexWithUV(this.x1, this.y1 - byte0, 0.0D, 1.0D, 0.0D);
+        tessellator.addVertexWithUV(this.x0, this.y1 - byte0, 0.0D, 0.0D, 0.0D);
         tessellator.draw();
-        int k3 = getMaxPosition() - (y1 - y0 - 4);
+        int k3 = getMaxPosition() - (this.y1 - this.y0 - 4);
         if (k3 > 0 && getMaxPosition() != 0) {
-            int j4 = ((y1 - y0) * (y1 - y0)) / getMaxPosition();
+            int j4 = ((this.y1 - this.y0) * (this.y1 - this.y0)) / getMaxPosition();
             if (j4 < 32) {
                 j4 = 32;
             }
-            if (j4 > y1 - y0 - 8) {
-                j4 = y1 - y0 - 8;
+            if (j4 > this.y1 - this.y0 - 8) {
+                j4 = this.y1 - this.y0 - 8;
             }
-            int l4 = ((int) amountScrolled * (y1 - y0 - j4)) / k3 + y0;
-            if (l4 < y0) {
-                l4 = y0;
+            int l4 = ((int) this.amountScrolled * (this.y1 - this.y0 - j4)) / k3 + this.y0;
+            if (l4 < this.y0) {
+                l4 = this.y0;
             }
             tessellator.startDrawingQuads();
-            tessellator.setColorRGBA_I(0, 255);
-            tessellator.addVertexWithUV(scrollbarLeft, y1, 0.0D, 0.0D, 1.0D);
-            tessellator.addVertexWithUV(scrollbarRight, y1, 0.0D, 1.0D, 1.0D);
-            tessellator.addVertexWithUV(scrollbarRight, y0, 0.0D, 1.0D, 0.0D);
-            tessellator.addVertexWithUV(scrollbarLeft, y0, 0.0D, 0.0D, 0.0D);
-            tessellator.draw();
-            tessellator.startDrawingQuads();
-            tessellator.setColorRGBA_I(0x808080, 255);
+            tessellator.setColor2i(0, 255);
+            tessellator.addVertexWithUV(scrollbarLeft, this.y1, 0.0D, 0.0D, 1.0D);
+            tessellator.addVertexWithUV(scrollbarRight, this.y1, 0.0D, 1.0D, 1.0D);
+            tessellator.addVertexWithUV(scrollbarRight, this.y0, 0.0D, 1.0D, 0.0D);
+            tessellator.addVertexWithUV(scrollbarLeft, this.y0, 0.0D, 0.0D, 0.0D);
+
+            tessellator.setColor2i(0x808080, 255);
             tessellator.addVertexWithUV(scrollbarLeft, l4 + j4, 0.0D, 0.0D, 1.0D);
             tessellator.addVertexWithUV(scrollbarRight, l4 + j4, 0.0D, 1.0D, 1.0D);
             tessellator.addVertexWithUV(scrollbarRight, l4, 0.0D, 1.0D, 0.0D);
             tessellator.addVertexWithUV(scrollbarLeft, l4, 0.0D, 0.0D, 0.0D);
-            tessellator.draw();
-            tessellator.startDrawingQuads();
-            tessellator.setColorRGBA_I(0xc0c0c0, 255);
-            tessellator.addVertexWithUV(scrollbarLeft, (l4 + j4) - 1, 0.0D, 0.0D, 1.0D);
-            tessellator.addVertexWithUV(scrollbarRight - 1, (l4 + j4) - 1, 0.0D, 1.0D, 1.0D);
-            tessellator.addVertexWithUV(scrollbarRight - 1, l4, 0.0D, 1.0D, 0.0D);
-            tessellator.addVertexWithUV(scrollbarLeft, l4, 0.0D, 0.0D, 0.0D);
+
+            tessellator.setColor2i(0xc0c0c0, 255);
+            tessellator.addVertexWithUV(scrollbarLeft + 1, (l4 + j4) - 1, 0.0D, 0.0D, 1.0D);
+            tessellator.addVertexWithUV(scrollbarRight, (l4 + j4) - 1, 0.0D, 1.0D, 1.0D);
+            tessellator.addVertexWithUV(scrollbarRight, l4, 0.0D, 1.0D, 0.0D);
+            tessellator.addVertexWithUV(scrollbarLeft + 1, l4, 0.0D, 0.0D, 0.0D);
             tessellator.draw();
         }
         renderDecorations(x, y);
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
-        GL11.glShadeModel(GL11.GL_FLAT);
-        GL11.glEnable(GL11.GL_ALPHA_TEST);
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.popFrame();
+//        GL11.glShadeModel(GL11.GL_FLAT);
+//        GL11.glEnable(GL11.GL_ALPHA_TEST);
+        GLRenderer.disableState(State.BLEND);
     }
 
     private void renderHoleBackground(int y0, int y1, int a0, int a1) {
-        Tessellator tessellator = Tessellator.instance;
-        minecraft.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        this.minecraft.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         float f = 32F;
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_I(0x404040, a1);
+        tessellator.setColor2i(0x404040, a1);
         tessellator.addVertexWithUV(0.0D, y1, 0.0D, 0.0D, (float) y1 / f);
-        tessellator.addVertexWithUV(width, y1, 0.0D, (float) width / f, (float) y1 / f);
-        tessellator.setColorRGBA_I(0x404040, a0);
-        tessellator.addVertexWithUV(width, y0, 0.0D, (float) width / f, (float) y0 / f);
+        tessellator.addVertexWithUV(this.width, y1, 0.0D, (float) this.width / f, (float) y1 / f);
+        tessellator.setColor2i(0x404040, a0);
+        tessellator.addVertexWithUV(this.width, y0, 0.0D, (float) this.width / f, (float) y0 / f);
         tessellator.addVertexWithUV(0.0D, y0, 0.0D, 0.0D, (float) y0 / f);
         tessellator.draw();
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/SliderElement.java b/game/client/src/main/java/net/minecraft/client/gui/SliderElement.java
index dc40c1223..d2745a462 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/SliderElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/SliderElement.java
@@ -1,126 +1,111 @@
 package net.minecraft.client.gui;
 
 import net.minecraft.client.input.InputType;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.MathHelper;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.option.OptionFloat;
 
 public class SliderElement extends ButtonElement {
 
-	public double sliderValue;
-	public boolean dragging;
-	private final OptionFloat option;
-	public IconCoordinate backgroundTexture;
-
-	public SliderElement(int id, int xPosition, int yPosition, OptionFloat optionFloat) {
-		this(id, xPosition, yPosition, 150, 20, optionFloat);
-	}
-
-	public SliderElement(int id, int xPosition, int yPosition, int width, int height, OptionFloat optionFloat) {
-		super(id, xPosition, yPosition, width, height, optionFloat.getDisplayStringValue());
-		this.dragging = false;
-		this.option = optionFloat;
-		this.sliderValue = optionFloat.value;
-	}
-
-	public SliderElement(int id, int xPosition, int yPosition, int width, int height, String text, float defaultValue) {
-		super(id, xPosition, yPosition, width, height, text);
-		dragging = false;
-		option = null;
-		sliderValue = defaultValue;
-	}
-
-	@Override
-	protected void setDefaultTextures() {
-		backgroundTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_background");
-		defaultTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider");
-		hoveredTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_highlighted");
-		disabledTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_disabled");
-	}
-
-	@Override
-	public void mouseDragged(Minecraft mc, int mouseX, int mouseY) {
-		if(!visible) {
-			return;
-		}
-		if(dragging) {
-			final double realMouseX = mc.inputType == InputType.CONTROLLER ? mc.controllerInput.cursorX : (double) (Mouse.getX() * mc.resolution.getScaledWidthScreenCoords()) / mc.resolution.getWidthScreenCoords();
-			sliderValue = MathHelper.clamp((realMouseX - (xPosition + 4)) / (float) (width - 8), 0, 1);
-			if(option != null) {
-				option.set((float) sliderValue);
-				displayString = option.getDisplayString();
-			}
-		}
-	}
-
-	public void drawButton(Minecraft mc, int mouseX, int mouseY)
-	{
-		if (!visible) return;
-
-				boolean mouseOver = mouseX >= xPosition && mouseY >= yPosition && mouseX < xPosition + width && mouseY < yPosition + height;
-		int state = getButtonState(mouseOver);
-
-		GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-
-		IconCoordinate tex;
-		switch (state) {
-			case STATE_DISABLED:
-				tex = disabledTexture;
-				break;
-			case STATE_HOVERED:
-				tex = hoveredTexture;
-				break;
-			case STATE_DEFAULT:
-			default:
-				tex = defaultTexture;
-		}
-
-		// Draw background
-		drawGuiIcon(xPosition, yPosition, width, height, backgroundTexture);
-
-		// Draw foreground
-		drawGuiIcon(xPosition + (int) (sliderValue * (float) (width - 8)), yPosition, 8, height, tex);
-
-		mouseDragged(mc, mouseX, mouseY);
-
-		int textColor;
-		switch (state) {
-			case 0:
-				textColor = 0xA0A0A0;
-				break;
-			case 1:
-				textColor = 0xE0E0E0;
-				break;
-			default:
-				textColor = 0xFFFFA0;
-				break;
-		}
-		drawStringCenteredShadow(mc.font, displayString, xPosition + width / 2, yPosition + (height - 8) / 2, textColor);
-	}
-
-	@Override
-	public boolean mouseClicked(Minecraft mc, int mouseX, int mouseY) {
-		if(super.mouseClicked(mc, mouseX, mouseY)) {
-			final double realMouseX = mc.inputType == InputType.CONTROLLER ? mc.controllerInput.cursorX : (double) (Mouse.getX() * mc.resolution.getScaledWidthScreenCoords()) / mc.resolution.getWidthScreenCoords();
-			sliderValue = MathHelper.clamp((realMouseX - (xPosition + 4)) / (float) (width - 8), 0, 1);
-			if(option != null) {
-				option.set((float) sliderValue);
-				displayString = option.getDisplayString();
-			}
-			dragging = true;
-			return true;
-		} else {
-			return false;
-		}
-	}
-
-	@Override
-	public void mouseReleased(int mouseX, int mouseY) {
-		dragging = false;
-	}
+    public double sliderValue;
+    public boolean dragging;
+    private final OptionFloat option;
+    public IconCoordinate backgroundTexture;
+
+    public SliderElement(int id, int xPosition, int yPosition, OptionFloat optionFloat) {
+        this(id, xPosition, yPosition, 150, 20, optionFloat);
+    }
+
+    public SliderElement(int id, int xPosition, int yPosition, int width, int height, OptionFloat optionFloat) {
+        super(id, xPosition, yPosition, width, height, optionFloat.getDisplayStringValue());
+        this.dragging = false;
+        this.option = optionFloat;
+        this.sliderValue = optionFloat.value;
+    }
+
+    public SliderElement(int id, int xPosition, int yPosition, int width, int height, String text, float defaultValue) {
+        super(id, xPosition, yPosition, width, height, text);
+        this.dragging = false;
+        this.option = null;
+        this.sliderValue = defaultValue;
+    }
+
+    @Override
+    protected void setDefaultTextures() {
+        this.backgroundTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_background");
+        this.defaultTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider");
+        this.hoveredTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_highlighted");
+        this.disabledTexture = TextureRegistry.getTexture("minecraft:gui/widgets/slider/slider_disabled");
+    }
+
+    @Override
+    public void mouseDragged(Minecraft mc, int mouseX, int mouseY) {
+        if (!this.visible) {
+            return;
+        }
+        if (this.dragging) {
+            final double realMouseX = mc.inputType == InputType.CONTROLLER ? mc.controllerInput.cursorX : (double) (Mouse.getX() * mc.resolution.getScaledWidthScreenCoords()) / mc.resolution.getWidthScreenCoords();
+            this.sliderValue = MathHelper.clamp((realMouseX - (this.xPosition + 4)) / (float) (this.width - 8), 0, 1);
+            if (this.option != null) {
+                this.option.set((float) this.sliderValue);
+                this.displayString = this.option.getDisplayString();
+            }
+        }
+    }
+
+    public void drawButton(Minecraft mc, int mouseX, int mouseY) {
+        if (!this.visible) return;
+
+        boolean mouseOver = mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height;
+        int state = getButtonState(mouseOver);
+
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+
+        IconCoordinate tex = switch (state) {
+            case STATE_DISABLED -> this.disabledTexture;
+            case STATE_HOVERED -> this.hoveredTexture;
+            default -> this.defaultTexture;
+        };
+
+        // Draw background
+        drawGuiIcon(this.xPosition, this.yPosition, this.width, this.height, this.backgroundTexture);
+
+        // Draw foreground
+        drawGuiIcon(this.xPosition + (int) (this.sliderValue * (float) (this.width - 8)), this.yPosition, 8, this.height, tex);
+
+        mouseDragged(mc, mouseX, mouseY);
+
+        int textColor = switch (state) {
+            case 0 -> 0xA0A0A0;
+            case 1 -> 0xE0E0E0;
+            default -> 0xFFFFA0;
+        };
+        drawStringCenteredShadow(mc.font, this.displayString, this.xPosition + this.width / 2, this.yPosition + (this.height - 8) / 2, textColor);
+    }
+
+    @Override
+    public boolean mouseClicked(Minecraft mc, int mouseX, int mouseY) {
+        if (super.mouseClicked(mc, mouseX, mouseY)) {
+            final double realMouseX = mc.inputType == InputType.CONTROLLER ? mc.controllerInput.cursorX : (double) (Mouse.getX() * mc.resolution.getScaledWidthScreenCoords()) / mc.resolution.getWidthScreenCoords();
+            this.sliderValue = MathHelper.clamp((realMouseX - (this.xPosition + 4)) / (float) (this.width - 8), 0, 1);
+            if (this.option != null) {
+                this.option.set((float) this.sliderValue);
+                this.displayString = this.option.getDisplayString();
+            }
+            this.dragging = true;
+            return true;
+        } else {
+            return false;
+        }
+    }
+
+    @Override
+    public void mouseReleased(int mouseX, int mouseY) {
+        this.dragging = false;
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/SwitchElement.java b/game/client/src/main/java/net/minecraft/client/gui/SwitchElement.java
index 0c110995f..c61fb740e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/SwitchElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/SwitchElement.java
@@ -1,9 +1,9 @@
 package net.minecraft.client.gui;
 
 import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import org.lwjgl.opengl.GL11;
 
 public class SwitchElement
     extends ButtonElement {
@@ -33,10 +33,10 @@ public class SwitchElement
     }
     @Override
     protected void setDefaultTextures() {
-        backgroundTexture = TextureRegistry.getTexture("minecraft:gui/widgets/switch/switch_background");
-        defaultTexture = TextureRegistry.getTexture("minecraft:gui/widgets/switch/switch");
-        hoveredTexture = TextureRegistry.getTexture("minecraft:gui/widgets/switch/switch_highlighted");
-        disabledTexture = TextureRegistry.getTexture("minecraft:gui/widgets/switch/switch_disabled");
+        this.backgroundTexture = TextureRegistry.getTexture("minecraft:gui/widgets/switch/switch_background");
+        this.defaultTexture = TextureRegistry.getTexture("minecraft:gui/widgets/switch/switch");
+        this.hoveredTexture = TextureRegistry.getTexture("minecraft:gui/widgets/switch/switch_highlighted");
+        this.disabledTexture = TextureRegistry.getTexture("minecraft:gui/widgets/switch/switch_disabled");
     }
 
     private void updateText() {
@@ -58,47 +58,33 @@ public class SwitchElement
 
     @Override
     public void drawButton(Minecraft mc, int mouseX, int mouseY) {
-        if (!visible) return;
+        if (!this.visible) return;
 
-        boolean mouseOver = mouseX >= xPosition && mouseY >= yPosition && mouseX < xPosition + width && mouseY < yPosition + height;
+        boolean mouseOver = mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height;
         int state = getButtonState(mouseOver);
-        int xBar = on ? (width / 3) + 1 : 0;
-
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-
-        IconCoordinate tex;
-        switch (state) {
-            case STATE_DISABLED:
-                tex = disabledTexture;
-                break;
-            case STATE_HOVERED:
-                tex = hoveredTexture;
-                break;
-            case STATE_DEFAULT:
-            default:
-                tex = defaultTexture;
-        }
+        int xBar = this.on ? (this.width / 3) + 1 : 0;
+
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+
+        IconCoordinate tex = switch (state) {
+            case STATE_DISABLED -> this.disabledTexture;
+            case STATE_HOVERED -> this.hoveredTexture;
+            default -> this.defaultTexture;
+        };
 
         // Draw background
-        drawGuiIcon(xPosition, yPosition, width, height, backgroundTexture);
+        drawGuiIcon(this.xPosition, this.yPosition, this.width, this.height, this.backgroundTexture);
 
         // Draw foreground
-        drawGuiIcon(xPosition + xBar, yPosition, (width * 2)/3, height, tex);
+        drawGuiIcon(this.xPosition + xBar, this.yPosition, (this.width * 2)/3, this.height, tex);
 
         mouseDragged(mc, mouseX, mouseY);
 
-        int textColor;
-        switch (state) {
-            case 0:
-                textColor = 0xA0A0A0;
-                break;
-            case 1:
-                textColor = 0xE0E0E0;
-                break;
-            default:
-                textColor = 0xFFFFA0;
-                break;
-        }
-        drawStringCenteredShadow(mc.font, displayString, xPosition + xBar + width / 3, yPosition + (height - 8) / 2, textColor);
+        int textColor = switch (state) {
+            case 0 -> 0xA0A0A0;
+            case 1 -> 0xE0E0E0;
+            default -> 0xFFFFA0;
+        };
+        drawStringCenteredShadow(mc.font, this.displayString, this.xPosition + xBar + this.width / 3, this.yPosition + (this.height - 8) / 2, textColor);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/TexturedButtonElement.java b/game/client/src/main/java/net/minecraft/client/gui/TexturedButtonElement.java
index e8627cecb..f8f270919 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/TexturedButtonElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/TexturedButtonElement.java
@@ -1,15 +1,15 @@
 package net.minecraft.client.gui;
 
 import net.minecraft.client.Minecraft;
-import org.lwjgl.opengl.GL11;
+import net.minecraft.client.render.renderer.GLRenderer;
 
 public class TexturedButtonElement extends ButtonElement {
     private final String texturePath;
-    private int u;
-    private int v;
+    private final int u;
+    private final int v;
 
     public TexturedButtonElement(int id, String texturePath, int xPosition, int yPosition, int u, int v, int width, int height) {
-        super(id, xPosition, yPosition,width, height, "");
+        super(id, xPosition, yPosition, width, height, "");
         this.texturePath = texturePath;
         this.u = u;
         this.v = v;
@@ -17,23 +17,18 @@ public class TexturedButtonElement extends ButtonElement {
 
     @Override
     public void drawButton(Minecraft mc, int mouseX, int mouseY) {
-        if (!visible) {
+        if (!this.visible) {
             return;
         }
-        mc.textureManager.loadTexture(texturePath).bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        boolean isHovered = mouseX >= xPosition && mouseY >= yPosition && mouseX < xPosition + width && mouseY < yPosition + height;
-        if (!enabled)
-        {
-            drawTexturedModalRect(xPosition, yPosition, u, v, width, height);
-        }
-        else if (!isHovered)
-        {
-            drawTexturedModalRect(xPosition, yPosition, u, v + height, width, height);
-        }
-        else
-        {
-            drawTexturedModalRect(xPosition, yPosition, u, v + height * 2, width, height);
+        mc.textureManager.loadTexture(this.texturePath).bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        boolean isHovered = mouseX >= this.xPosition && mouseY >= this.yPosition && mouseX < this.xPosition + this.width && mouseY < this.yPosition + this.height;
+        if (!this.enabled) {
+            drawTexturedModalRect(this.xPosition, this.yPosition, this.u, this.v, this.width, this.height);
+        } else if (!isHovered) {
+            drawTexturedModalRect(this.xPosition, this.yPosition, this.u, this.v + this.height, this.width, this.height);
+        } else {
+            drawTexturedModalRect(this.xPosition, this.yPosition, this.u, this.v + this.height * 2, this.width, this.height);
         }
         mouseDragged(mc, mouseX, mouseY);
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/TooltipElement.java b/game/client/src/main/java/net/minecraft/client/gui/TooltipElement.java
index 25fb3a196..9345d8e73 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/TooltipElement.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/TooltipElement.java
@@ -8,7 +8,10 @@ import com.google.gson.stream.JsonReader;
 import com.mojang.logging.LogUtils;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.CompareFunc;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.render.texturepack.TexturePack;
@@ -26,9 +29,7 @@ import net.minecraft.client.gui.guidebook.SlotGuidebook;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 
-import com.mojang.nbt.tags.CompoundTag;
 import org.slf4j.Logger;
 
 import java.io.IOException;
@@ -40,8 +41,7 @@ import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
 
-public class TooltipElement extends Gui
-{
+public class TooltipElement extends Gui {
     protected final static Logger LOGGER = LogUtils.getLogger();
     public final static Map<String, Style> styleMap = new HashMap<>();
     public final static List<String> stylesIdList = new ArrayList<>();
@@ -50,35 +50,35 @@ public class TooltipElement extends Gui
     Minecraft mc;
     FontRenderer fontRenderer;
 
-    public TooltipElement(Minecraft mc)
-    {
+    public TooltipElement(Minecraft mc) {
         this.mc = mc;
         this.fontRenderer = mc.font;
     }
+
     public static final int BASE_PADDING = 3;
     public static final int LINE_SPACING = 3;
 
     public void render(final CharSequence string, final int x, final int y, final int offsetX, final int offsetY) {
         render(string, x, y, offsetX, offsetY, -1, -1, true);
     }
-    public void render(final CharSequence chars, int x, int y, int offsetX, int offsetY, int maxWidth, int maxHeight, boolean canOffset)
-    {
+
+    public void render(final CharSequence chars, int x, int y, int offsetX, int offsetY, int maxWidth, int maxHeight, boolean canOffset) {
+        GLRenderer.pushFrame();
+        GLRenderer.setDepthFunc(CompareFunc.ALWAYS);
         maxWidth = maxWidth == -1 ? Integer.MAX_VALUE : maxWidth;
         maxHeight = maxHeight == -1 ? Integer.MAX_VALUE : maxHeight;
 
         final List<String> lines = new ArrayList<>();
         this.fontRenderer.splitCharsIntoLines(chars, maxWidth, lines);
         int width = 0;
-        for (final String line : lines)
-        {
+        for (final String line : lines) {
             width = Math.max(width, this.fontRenderer.stringWidth(line) - 1);
         }
 
         final int height = MathHelper.ceil(this.fontRenderer.heightOfLines(lines, maxWidth) - 1);
 
         // Flip tooltip X if it goes offscreen to the right
-        if(canOffset && x + offsetX + width > this.mc.resolution.getScaledWidthScreenCoords())
-        {
+        if (canOffset && x + offsetX + width > this.mc.resolution.getScaledWidthScreenCoords()) {
             offsetX = -offsetX - width;
         }
 
@@ -96,23 +96,25 @@ public class TooltipElement extends Gui
         drawBackground(x, y, x + width, y + height);
 //        drawRect(x, y, x + width, y + height, 0xFFFFFFFF);
 
-        this.fontRenderer.renderWidthConstrained(Tessellator.instance, chars, x + padding, y + padding, maxWidth).call();
+        this.fontRenderer.renderWidthConstrained(chars, x + padding, y + padding, maxWidth).call();
+        GLRenderer.popFrame();
     }
-    public int getPadding(){
+
+    public int getPadding() {
         return 0;
     }
-    public int[] drawBackground(int x, int y, int offsetX, int offsetY, int width, int height){
+
+    public int[] drawBackground(int x, int y, int offsetX, int offsetY, int width, int height) {
 //        int targetOffset = 0;
         // Flip tooltip X if it goes offscreen to the right
-        if(x + offsetX + width > mc.resolution.getScaledWidthScreenCoords())
-        {
+        if (x + offsetX + width > this.mc.resolution.getScaledWidthScreenCoords()) {
 //            int _offsetX = offsetX;
             offsetX = -offsetX - width;
 //            targetOffset = offsetX - _offsetX;
         }
 
         // Move tooltip up when it goes offscreen to the bottom
-        offsetY -= Math.max(0, y + height + offsetY - mc.resolution.getScaledHeightScreenCoords());
+        offsetY -= Math.max(0, y + height + offsetY - this.mc.resolution.getScaledHeightScreenCoords());
 
         x += offsetX;
         y += offsetY;
@@ -120,12 +122,13 @@ public class TooltipElement extends Gui
         return drawBackground(x, y, x + width, y + height);
     }
 
-    private int[] drawBackground(final int minX, final int minY, final int maxX, final int maxY)
-    {
+    private int[] drawBackground(final int minX, final int minY, final int maxX, final int maxY) {
         final Style style = styleMap.getOrDefault(this.mc.gameSettings.tooltipStyle.value, defaultStyle);
         if (style != null) {
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+            GLRenderer.pushFrame();
+            GLRenderer.setDepthFunc(CompareFunc.ALWAYS);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
 
             drawGuiIcon(
                 minX - 2,
@@ -140,50 +143,52 @@ public class TooltipElement extends Gui
                 maxY - minY + 4 + style.paddingTop + style.paddingBottom,
                 style.getBorderIcon());
 
-            GL11.glDisable(GL11.GL_BLEND);
+            GLRenderer.disableState(State.BLEND);
+            GLRenderer.popFrame();
         }
         return new int[]{minX, minY};
     }
 
-	public String getTooltipText(ItemStack itemStack, boolean showDescription, Slot slot) {
-		I18n trans = I18n.getInstance();
-		StringBuilder text = new StringBuilder();
-		boolean discovered = true;
-		boolean ctrlPressed = false;
-		boolean shiftPressed = false;
-		boolean debug = mc.gameSettings.showItemDebugInfo.value;
-
-		if(slot != null) {
-			discovered = slot.getIsDiscovered(mc.thePlayer);
-
-			if(slot instanceof SlotResult) {
-				ctrlPressed = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
-				shiftPressed = Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT);
-
-				showDescription = false;
-				if(mc.gameSettings.swapCraftingButtons.value) {
-					boolean temp = shiftPressed;
-					shiftPressed = ctrlPressed;
-					ctrlPressed = temp;
-				}
-			}
-		}
-
-		if(discovered) {
-			text.append(TextFormatting.get(itemStack.getDisplayColor()));
-			text.append(itemStack.getDisplayName());
-            if (itemStack.getData().containsKey("tileEntityData")) text.append(" ").append(TextFormatting.MAGENTA).append(TextFormatting.ITALIC).append("+NBT").append(TextFormatting.RESET).append(TextFormatting.get(itemStack.getDisplayColor()));
-
-
-            if(debug) {
+    public String getTooltipText(ItemStack itemStack, boolean showDescription, Slot slot) {
+        I18n trans = I18n.getInstance();
+        StringBuilder text = new StringBuilder();
+        boolean discovered = true;
+        boolean ctrlPressed = false;
+        boolean shiftPressed = false;
+        boolean debug = this.mc.gameSettings.showItemDebugInfo.value;
+
+        if (slot != null) {
+            discovered = slot.getIsDiscovered(this.mc.thePlayer);
+
+            if (slot instanceof SlotResult) {
+                ctrlPressed = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
+                shiftPressed = Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT);
+
+                showDescription = false;
+                if (this.mc.gameSettings.swapCraftingButtons.value) {
+                    boolean temp = shiftPressed;
+                    shiftPressed = ctrlPressed;
+                    ctrlPressed = temp;
+                }
+            }
+        }
+
+        if (discovered) {
+            text.append(TextFormatting.get(itemStack.getDisplayColor()));
+            text.append(itemStack.getDisplayName());
+            if (itemStack.getData().containsKey("tileEntityData"))
+                text.append(" ").append(TextFormatting.MAGENTA).append(TextFormatting.ITALIC).append("+NBT").append(TextFormatting.RESET).append(TextFormatting.get(itemStack.getDisplayColor()));
+
+
+            if (debug) {
                 text.append(" #").append(itemStack.itemID).append(":").append(itemStack.getMetadata());
             }
 
-            if(slot instanceof SlotGuidebook){
-                if(((SlotGuidebook) slot).recipe != null) {
+            if (slot instanceof SlotGuidebook) {
+                if (((SlotGuidebook) slot).recipe != null) {
                     if (((SlotGuidebook) slot).recipe instanceof RecipeEntryTrommel) {
                         RecipeSymbol input = (RecipeSymbol) ((SlotGuidebook) slot).recipe.getInput();
-                        if(!input.matches(slot.getItemStack())){
+                        if (!input.matches(slot.getItemStack())) {
                             WeightedRandomBag<?> bag = (WeightedRandomBag<?>) ((SlotGuidebook) slot).recipe.getOutput();
                             double percent = bag.getAsPercentage(slot.getItemStack());
                             text.append('\n').append(TextFormatting.LIGHT_GRAY).append(String.format("%.2f", percent)).append("%");
@@ -192,71 +197,67 @@ public class TooltipElement extends Gui
                 }
             }
 
-			if(debug) {
+            if (debug) {
                 text.append('\n').append(TextFormatting.LIGHT_GRAY).append(itemStack.getItem().namespaceID);
                 text.append('\n').append(TextFormatting.LIGHT_GRAY).append(itemStack.getItemKey());
-				CompoundTag data = itemStack.getData();
-				if(data != null) {
-					text.append('\n').append(TextFormatting.LIGHT_GRAY).append("NBT: ").append(data.getValue().size()).append(" Tags");
-				}
-
-                if(slot instanceof SlotGuidebook){
-                    if(((SlotGuidebook) slot).recipe != null){
-                        text.append('\n').append(TextFormatting.GRAY).append(((SlotGuidebook) slot).recipe.toString());
+                text.append('\n').append(TextFormatting.LIGHT_GRAY).append("NBT: ").append(itemStack.getData().getValue().size()).append(" Tags");
+
+                if (slot instanceof SlotGuidebook slotGuidebook) {
+                    if (slotGuidebook.recipe != null) {
+                        text.append('\n').append(TextFormatting.GRAY).append(slotGuidebook.recipe);
                     }
-                    if(((SlotGuidebook) slot).symbol != null){
-                        if(((SlotGuidebook) slot).symbol.getItemGroup() != null){
-                            text.append('\n').append(TextFormatting.GRAY).append("Accepts any: ").append(((SlotGuidebook) slot).symbol.getItemGroup());
+                    if (slotGuidebook.symbol != null) {
+                        if (slotGuidebook.symbol.getItemGroup() != null) {
+                            text.append('\n').append(TextFormatting.GRAY).append("Accepts any: ").append(slotGuidebook.symbol.getItemGroup());
                         }
                     }
                 }
-			}
+            }
 
-			if(itemStack.isItemStackDamageable() && !showDescription && mc.gameSettings.showItemDebugInfo.value) {
-				int durability = itemStack.getMaxDamage();
-				int remainingUses = durability - itemStack.getMetadata();
+            if (itemStack.isItemStackDamageable() && !showDescription && this.mc.gameSettings.showItemDebugInfo.value) {
+                int durability = itemStack.getMaxDamage();
+                int remainingUses = durability - itemStack.getMetadata();
 
-				text.append('\n').append(TextFormatting.LIGHT_GRAY).append(remainingUses + 1).append(" / ").append(durability + 1);
-			}
+                text.append('\n').append(TextFormatting.LIGHT_GRAY).append(remainingUses + 1).append(" / ").append(durability + 1);
+            }
 
-			if(showDescription) {
-				text.append('\n').append(formatDescription(itemStack.getItemDescription(), 16));
-			} else if (!(slot instanceof SlotResult) && mc.gameSettings.itemDescriptions.value != DescriptionPromptEnum.NEVER_PROMPT) {
-                text.append('\n').append(formatDescription(trans.translateKeyAndFormat("gui.tooltip.prompt.description", mc.gameSettings.keyDescription.getKeyName()), 16));
+            if (showDescription) {
+                text.append('\n').append(formatDescription(itemStack.getItemDescription(), 16));
+            } else if (!(slot instanceof SlotResult) && this.mc.gameSettings.itemDescriptions.value != DescriptionPromptEnum.NEVER_PROMPT) {
+                text.append('\n').append(formatDescription(trans.translateKeyAndFormat("gui.tooltip.prompt.description", this.mc.gameSettings.keyDescription.getKeyName()), 16));
             }
 
-			if(slot instanceof SlotResult) {
-				if(shiftPressed && !ctrlPressed) {
-					text.append('\n').append(TextFormatting.LIGHT_GRAY).append("Craft Stack");
-				}
-				if(ctrlPressed && !shiftPressed) {
-					text.append('\n').append(TextFormatting.LIGHT_GRAY).append("Craft Once");
-				}
-				if(ctrlPressed && shiftPressed) {
-					text.append('\n').append(TextFormatting.LIGHT_GRAY).append("Craft All");
-				}
-			}
-		} else {
-			String translatedName = itemStack.getDisplayName();
-			for(char c : translatedName.toCharArray()) {
-				if(Character.isLetterOrDigit(c))
-					text.append("?");
-				else
-					text.append(c);
-			}
-			// text.append("???" /*
-			// TextFormatting.formatted(trans.translateKey(itemStack.getItemName() +
-			// ".name"), TextFormatting.OBFUSCATED) */);
-			if(showDescription) {
-				text.append('\n').append(trans.translateKey("item.unknown.desc"));
-			}
-		}
-
-		return text.toString();
-	}
-
-    public String getTooltipText(ItemStack itemStack, boolean showDescription)
-    {
+            if (slot instanceof SlotResult) {
+                if (shiftPressed && !ctrlPressed) {
+                    text.append('\n').append(TextFormatting.LIGHT_GRAY).append("Craft Stack");
+                }
+                if (ctrlPressed && !shiftPressed) {
+                    text.append('\n').append(TextFormatting.LIGHT_GRAY).append("Craft Once");
+                }
+                if (ctrlPressed && shiftPressed) {
+                    text.append('\n').append(TextFormatting.LIGHT_GRAY).append("Craft All");
+                }
+            }
+        } else {
+            String translatedName = itemStack.getDisplayName();
+            for (char c : translatedName.toCharArray()) {
+                if (Character.isLetterOrDigit(c))
+                    text.append("?");
+                else
+                    text.append(c);
+            }
+            // text.append("???" /*
+            // TextFormatting.formatted(trans.translateKey(itemStack.getItemName() +
+            // ".name"), TextFormatting.OBFUSCATED) */);
+            if (showDescription) {
+                text.append('\n').append(trans.translateKey("item.unknown.desc"));
+            }
+        }
+
+        return text.toString();
+    }
+
+    public String getTooltipText(ItemStack itemStack, boolean showDescription) {
         return getTooltipText(itemStack, showDescription, null);
     }
 
@@ -266,17 +267,17 @@ public class TooltipElement extends Gui
         string.append(TextFormatting.LIGHT_GRAY);
 
         int lineLength = 0;
-        for(int i=0; i < description.length(); i++) {
+        for (int i = 0; i < description.length(); i++) {
             char c = description.charAt(i);
 
-            if(c == ' ') {
-                if(lineLength > preferredLineLength) {
+            if (c == ' ') {
+                if (lineLength > preferredLineLength) {
                     lineLength = 0;
                     string.append("\n").append(TextFormatting.LIGHT_GRAY);
-                }else {
+                } else {
                     string.append(c);
                 }
-            }else {
+            } else {
                 lineLength++;
                 string.append(c);
             }
@@ -300,7 +301,7 @@ public class TooltipElement extends Gui
             try (final InputStream stylesStream = pack.getResourceAsStream("/assets/minecraft/textures/gui/sprites/tooltip/styles.json")) {
                 if (stylesStream != null) {
                     final JsonObject stylesListObject = JsonParser.parseReader(new InputStreamReader(stylesStream)).getAsJsonObject();
-                    final boolean replace = stylesListObject.has("replace") ? stylesListObject.get("replace").getAsBoolean() : false;
+                    final boolean replace = stylesListObject.has("replace") && stylesListObject.get("replace").getAsBoolean();
                     if (replace) styleIds.clear();
                     final JsonArray styles = stylesListObject.getAsJsonArray("styles");
                     for (final JsonElement element : styles) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/achievements/ScreenAchievements.java b/game/client/src/main/java/net/minecraft/client/gui/achievements/ScreenAchievements.java
index d9df13fac..6bc6a97b5 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/achievements/ScreenAchievements.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/achievements/ScreenAchievements.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.gui.achievements;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ButtonElement;
 import net.minecraft.client.gui.ItemElement;
 import net.minecraft.client.gui.Screen;
@@ -10,11 +9,19 @@ import net.minecraft.client.gui.achievements.data.AchievementPageRegistry;
 import net.minecraft.client.gui.achievements.data.AchievementPages;
 import net.minecraft.client.gui.options.OptionsButtonElement;
 import net.minecraft.client.render.Lighting;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.Scissor;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.CompareFunc;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.RenderBuffer;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.achievement.Achievement;
 import net.minecraft.core.achievement.stat.StatsCounter;
 import net.minecraft.core.item.Item;
@@ -27,20 +34,13 @@ import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.lwjgl.opengl.GL41;
 
 import java.util.Objects;
 import java.util.Random;
 
-import static org.lwjgl.opengl.GL11.GL_TEXTURE_2D;
-import static org.lwjgl.opengl.GL11.glDisable;
-import static org.lwjgl.opengl.GL11.glEnable;
-
 public class ScreenAchievements extends Screen
 {
-
-
     private static final int TOP_SPACING = 24;
     private static final int BUTTON_SPACING = 4;
     private static final int SEPARATOR_WIDTH = 8;
@@ -106,53 +106,53 @@ public class ScreenAchievements extends Screen
 
     public ScreenAchievements(Screen parent, StatsCounter statsCounter)
     {
-        mouseXOld = 0;
-        mouseYOld = 0;
-        draggingViewport = false;
+        this.mouseXOld = 0;
+        this.mouseYOld = 0;
+        this.draggingViewport = false;
         this.statsCounter = statsCounter;
 
         this.parent = parent;
-        this.tooltip = new TooltipElement(mc);
-        this.renderItem = new ItemElement(mc);
+        this.tooltip = new TooltipElement(this.mc);
+        this.renderItem = new ItemElement(this.mc);
 
-        layers = new BGLayer[currentPage.backgroundLayers()];
-        for (int i = 0; i < layers.length; i++) {
-            layers[i] = new BGLayer(i);
+        this.layers = new BGLayer[this.currentPage.backgroundLayers()];
+        for (int i = 0; i < this.layers.length; i++) {
+            this.layers[i] = new BGLayer(i);
         }
     }
 
     @Override
 	public void init()
     {
-        buttons.clear();
-        buttons.add(new OptionsButtonElement(1, width / 2 - 100, height - 20 - BUTTON_SPACING, 200, 20, I18n.getInstance().translateKey("gui.achievements.button.done")));
+        this.buttons.clear();
+        this.buttons.add(new OptionsButtonElement(1, this.width / 2 - 100, this.height - 20 - BUTTON_SPACING, 200, 20, I18n.getInstance().translateKey("gui.achievements.button.done")));
 
-        lastTileX = Integer.MIN_VALUE;
-        lastTileY = Integer.MIN_VALUE;
+        this.lastTileX = Integer.MIN_VALUE;
+        this.lastTileY = Integer.MIN_VALUE;
 
-        top = TOP_SPACING;
-        bottom = height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
+        this.top = TOP_SPACING;
+        this.bottom = this.height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
 
-        pagesListScrollRegionHeight = bottom - top;
-        pageListLeft = 0;
-        pageListRight = width/4;
+        this.pagesListScrollRegionHeight = this.bottom - this.top;
+        this.pageListLeft = 0;
+        this.pageListRight = this.width /4;
 
-        viewportZoom = 1;
+        this.viewportZoom = 1;
 
-        viewportLeft = drawSidebar() ? pageListRight + SEPARATOR_WIDTH : 0;
-        viewportTop = top;
-        viewportBottom = bottom;
-        viewportRight = width;
+        this.viewportLeft = drawSidebar() ? this.pageListRight + SEPARATOR_WIDTH : 0;
+        this.viewportTop = this.top;
+        this.viewportBottom = this.bottom;
+        this.viewportRight = this.width;
 
-        viewportWidth = viewportRight - viewportLeft;
-        viewportHeight = viewportBottom - viewportTop;
+        this.viewportWidth = this.viewportRight - this.viewportLeft;
+        this.viewportHeight = this.viewportBottom - this.viewportTop;
 
         int achMinX = Integer.MAX_VALUE;
         int achMinY = Integer.MAX_VALUE;
         int achMaxX = Integer.MIN_VALUE;
         int achMaxY = Integer.MIN_VALUE;
 
-        for (AchievementPage.AchievementEntry ach : currentPage.getAchievementEntries()){
+        for (AchievementPage.AchievementEntry ach : this.currentPage.getAchievementEntries()){
             if (ach.x < achMinX){
                 achMinX = ach.x;
             }
@@ -167,26 +167,38 @@ public class ScreenAchievements extends Screen
             }
         }
 
-        shiftMinX = achMinX * ACHIEVEMENT_CELL_WIDTH ;
-        shiftMinY = achMinY * ACHIEVEMENT_CELL_HEIGHT;
-        shiftMaxX = achMaxX * ACHIEVEMENT_CELL_WIDTH  + ACHIEVEMENT_CELL_WIDTH;
-        shiftMaxY = achMaxY * ACHIEVEMENT_CELL_HEIGHT + ACHIEVEMENT_CELL_HEIGHT;
+        this.shiftMinX = achMinX * ACHIEVEMENT_CELL_WIDTH ;
+        this.shiftMinY = achMinY * ACHIEVEMENT_CELL_HEIGHT;
+        this.shiftMaxX = achMaxX * ACHIEVEMENT_CELL_WIDTH  + ACHIEVEMENT_CELL_WIDTH;
+        this.shiftMaxY = achMaxY * ACHIEVEMENT_CELL_HEIGHT + ACHIEVEMENT_CELL_HEIGHT;
 
-        shiftMinX -= (int) (viewportWidth /4d);
-        shiftMinY -= (int) (viewportHeight/4d);
-        shiftMaxX += (int) (viewportWidth /4d);
-        shiftMaxY += (int) (viewportHeight/4d);
+        this.shiftMinX -= (int) (this.viewportWidth /4d);
+        this.shiftMinY -= (int) (this.viewportHeight /4d);
+        this.shiftMaxX += (int) (this.viewportWidth /4d);
+        this.shiftMaxY += (int) (this.viewportHeight /4d);
 
         // Centers the screen on the Open ContainerInventory achievement
-        AchievementPage.AchievementEntry ach = currentPage.onOpenAchievement();
-        oldShiftX = targetShiftX = currentShiftX = ach.x * ACHIEVEMENT_CELL_WIDTH + ACHIEVEMENT_CELL_WIDTH/2d;
-        oldShiftY = targetShiftY = currentShiftY = ach.y * ACHIEVEMENT_CELL_HEIGHT + ACHIEVEMENT_CELL_HEIGHT/2d;
+        AchievementPage.AchievementEntry ach = this.currentPage.onOpenAchievement();
+        this.oldShiftX = this.targetShiftX = this.currentShiftX = ach.x * ACHIEVEMENT_CELL_WIDTH + ACHIEVEMENT_CELL_WIDTH/2d;
+        this.oldShiftY = this.targetShiftY = this.currentShiftY = ach.y * ACHIEVEMENT_CELL_HEIGHT + ACHIEVEMENT_CELL_HEIGHT/2d;
+    }
+
+    @Override
+    public void removed() {
+        if (this.lastBackgroundShadowBuf != null) {
+            this.lastBackgroundShadowBuf.delete();
+            this.lastBackgroundShadowBuf = null;
+        }
+        if (this.lastBackgroundTileBuf != null) {
+            this.lastBackgroundTileBuf.delete();
+            this.lastBackgroundTileBuf = null;
+        }
     }
 
     @Override
 	protected void buttonClicked(@NotNull ButtonElement button) {
         if(button.id == 1) {
-            mc.displayScreen(parent);
+            this.mc.displayScreen(this.parent);
             //mc.setIngameFocus();
         }
         super.buttonClicked(button);
@@ -196,27 +208,37 @@ public class ScreenAchievements extends Screen
 	public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
     {
         if (eventKey == Keyboard.KEY_ESCAPE) {
-            mc.displayScreen(parent);
+            this.mc.displayScreen(this.parent);
         } else {
             super.keyPressed(eventCharacter, eventKey, mx, my);
         }
     }
     @Override
     public void mouseClicked(int mx, int my, int buttonNum) {
-        if (drawSidebar() && mx >= pageListLeft && mx <= (pageListRight - 6) && my >= top && my <= bottom) {
+        if (drawSidebar() && mx >= this.pageListLeft && mx <= (this.pageListRight - 6) && my >= this.top && my <= this.bottom) {
             int pagesListHeight = getTotalPagesListHeight();
-            int pagesListY = top - (int) pageListScrollAmount;
-            if (pagesListHeight < bottom - top) {
-                pagesListY = top + (bottom - top - pagesListHeight) / 2;
+            int pagesListY = this.top - (int) this.pageListScrollAmount;
+            if (pagesListHeight < this.bottom - this.top) {
+                pagesListY = this.top + (this.bottom - this.top - pagesListHeight) / 2;
             }
             for(AchievementPage page : AchievementPageRegistry.getInstance().getPages()) {
-                if (mx >= pageListLeft && mx <= (pageListRight - 6) && my >= pagesListY && my <= pagesListY + PAGE_BUTTON_HEIGHT) {
-                    currentPage = page;
-                    mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
+                if (mx >= this.pageListLeft && mx <= (this.pageListRight - 6) && my >= pagesListY && my <= pagesListY + PAGE_BUTTON_HEIGHT) {
+                    this.currentPage = page;
+
+                    if (this.lastBackgroundShadowBuf != null) {
+                        this.lastBackgroundShadowBuf.delete();
+                        this.lastBackgroundShadowBuf = null;
+                    }
+                    if (this.lastBackgroundTileBuf != null) {
+                        this.lastBackgroundTileBuf.delete();
+                        this.lastBackgroundTileBuf = null;
+                    }
+
+                    this.mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
 
-                    layers = new BGLayer[currentPage.backgroundLayers()];
-                    for (int i = 0; i < layers.length; i++) {
-                        layers[i] = new BGLayer(i);
+                    this.layers = new BGLayer[this.currentPage.backgroundLayers()];
+                    for (int i = 0; i < this.layers.length; i++) {
+                        this.layers[i] = new BGLayer(i);
                     }
 
                     init();
@@ -227,66 +249,66 @@ public class ScreenAchievements extends Screen
         }
         super.mouseClicked(mx, my, buttonNum);
 
-        clickX = mx;
-        clickY = my;
+        this.clickX = mx;
+        this.clickY = my;
     }
 
     @Override
 	public void render(int mx, int my, float partialTick)
     {
         if(Mouse.isButtonDown(0)) {
-            if(mx >= viewportLeft && mx < viewportRight && my >= viewportTop && my < viewportBottom) {
-                if(!draggingViewport) {
-                    draggingViewport = true;
+            if(mx >= this.viewportLeft && mx < this.viewportRight && my >= this.viewportTop && my < this.viewportBottom) {
+                if(!this.draggingViewport) {
+                    this.draggingViewport = true;
                 } else {
-                    targetShiftX -= (mx - mouseXOld) / viewportZoom;
-                    targetShiftY -= (my - mouseYOld) / viewportZoom;
-                    currentShiftX = oldShiftX = targetShiftX;
-                    currentShiftY = oldShiftY = targetShiftY;
+                    this.targetShiftX -= (mx - this.mouseXOld) / this.viewportZoom;
+                    this.targetShiftY -= (my - this.mouseYOld) / this.viewportZoom;
+                    this.currentShiftX = this.oldShiftX = this.targetShiftX;
+                    this.currentShiftY = this.oldShiftY = this.targetShiftY;
                 }
-                mouseXOld = mx;
-                mouseYOld = my;
-            }
-            currentShiftX =  MathHelper.clamp(currentShiftX, shiftMinX, shiftMaxX);
-            currentShiftY =  MathHelper.clamp(currentShiftY, shiftMinY, shiftMaxY);
-        } else if (mc.controllerInput != null) {
-            targetShiftX += mc.controllerInput.joyRight.getX() / viewportZoom * 4;
-            targetShiftY += mc.controllerInput.joyRight.getY() / viewportZoom * 4;
-            currentShiftX = oldShiftX = targetShiftX;
-            currentShiftY = oldShiftY = targetShiftY;
-            currentShiftX =  MathHelper.clamp(currentShiftX, shiftMinX, shiftMaxX);
-            currentShiftY =  MathHelper.clamp(currentShiftY, shiftMinY, shiftMaxY);
-
-            if (mc.controllerInput.buttonLeftTrigger.isPressed()) {
-                viewportZoom -= 0.01d;
-            } else if (mc.controllerInput.buttonRightTrigger.isPressed()) {
-                viewportZoom += 0.01f;
-            }
-            viewportZoom = MathHelper.clamp(viewportZoom, 0.5d, 2d);
+                this.mouseXOld = mx;
+                this.mouseYOld = my;
+            }
+            this.currentShiftX =  MathHelper.clamp(this.currentShiftX, this.shiftMinX, this.shiftMaxX);
+            this.currentShiftY =  MathHelper.clamp(this.currentShiftY, this.shiftMinY, this.shiftMaxY);
+        } else if (this.mc.controllerInput != null) {
+            this.targetShiftX += this.mc.controllerInput.joyRight.getX() / this.viewportZoom * 4;
+            this.targetShiftY += this.mc.controllerInput.joyRight.getY() / this.viewportZoom * 4;
+            this.currentShiftX = this.oldShiftX = this.targetShiftX;
+            this.currentShiftY = this.oldShiftY = this.targetShiftY;
+            this.currentShiftX =  MathHelper.clamp(this.currentShiftX, this.shiftMinX, this.shiftMaxX);
+            this.currentShiftY =  MathHelper.clamp(this.currentShiftY, this.shiftMinY, this.shiftMaxY);
+
+            if (this.mc.controllerInput.buttonLeftTrigger.isPressed()) {
+                this.viewportZoom -= 0.01d;
+            } else if (this.mc.controllerInput.buttonRightTrigger.isPressed()) {
+                this.viewportZoom += 0.01f;
+            }
+            this.viewportZoom = MathHelper.clamp(this.viewportZoom, 0.5d, 2d);
 
         } else {
-            clickX = clickY = null;
-            oldPagesListScrollAmount = null;
-            draggingViewport = false;
+            this.clickX = this.clickY = null;
+            this.oldPagesListScrollAmount = null;
+            this.draggingViewport = false;
         }
 
-        if (drawSidebar() && mx >= pageListLeft && mx <= pageListRight) {
+        if (drawSidebar() && mx >= this.pageListLeft && mx <= this.pageListRight) {
             if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL)) {
                 scrollPagesList(Mouse.getDWheel() / -0.01f);
             } else {
                 scrollPagesList(Mouse.getDWheel() / -0.05f);
             }
             onScrollPagesList();
-        } else if (mx >= viewportLeft && mx <= viewportRight && my >= viewportTop && my <= viewportBottom){
+        } else if (mx >= this.viewportLeft && mx <= this.viewportRight && my >= this.viewportTop && my <= this.viewportBottom){
             final double change = (Mouse.getDWheel()/10d);
-            viewportZoom = MathHelper.clamp(viewportZoom + change, 0.5d, 2);
+            this.viewportZoom = MathHelper.clamp(this.viewportZoom + change, 0.5d, 2);
 
             // Make zoom notch onto integer multiples
             if (change != 0) {
                 final double[] notches = new double[]{0.25, 0.5, 1, 2, 4};
                 for (double notch : notches){
-                    if (Math.abs(viewportZoom - notch) < 0.05){
-                        viewportZoom = notch;
+                    if (Math.abs(this.viewportZoom - notch) < 0.05){
+                        this.viewportZoom = notch;
                         break;
                     }
                 }
@@ -297,201 +319,200 @@ public class ScreenAchievements extends Screen
         renderBackground();
 
         if (drawSidebar()){
-            overlayBackground(0, pageListRight, top, bottom, 0x202020);
+            overlayBackground(0, this.pageListRight, this.top, this.bottom, 0x202020);
         }
 
         renderAchievementsPanel(mx, my, partialTick);
 
-        overlayBackground(0, width, 0, top, 0x404040);
-        overlayBackground(0, width, bottom, height, 0x404040);
-        overlayBackground(pageListRight, viewportLeft, top, bottom, 0x404040);
+        overlayBackground(0, this.width, 0, this.top, 0x404040);
+        overlayBackground(0, this.width, this.bottom, this.height, 0x404040);
+        overlayBackground(this.pageListRight, this.viewportLeft, this.top, this.bottom, 0x404040);
 
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glDisable(GL11.GL_ALPHA_TEST);
-        GL11.glShadeModel(GL11.GL_SMOOTH);
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+//        GL11.glDisable(GL11.GL_ALPHA_TEST);
+//        GL11.glShadeModel(GL11.GL_SMOOTH);
+//        GL11.glEnable(GL11.GL_TEXTURE_2D);
 
         super.render(mx, my, partialTick); // Draw Buttons
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glEnable(GL11.GL_LIGHTING);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.globalSetLightEnabled(true);
         Lighting.disable();
 
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
-        GL11.glShadeModel(GL11.GL_FLAT);
-        GL11.glEnable(GL11.GL_ALPHA_TEST);
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.disableState(State.DEPTH_TEST);
+//        GL11.glEnable(GL11.GL_TEXTURE_2D);
+//        GL11.glShadeModel(GL11.GL_FLAT);
+//        GL11.glEnable(GL11.GL_ALPHA_TEST);
 
         if (drawSidebar()){
-            Scissor.enable(pageListLeft, top, pageListRight - pageListLeft, bottom - top);
+            Scissor.enable(this.pageListLeft, this.top, this.pageListRight - this.pageListLeft, this.bottom - this.top);
             int pagesListHeight = getTotalPagesListHeight();
-            int pagesListY = top - (int) pageListScrollAmount;
-            if (pagesListHeight < bottom - top) {
-                pagesListY = top + (bottom - top - pagesListHeight) / 2;
+            int pagesListY = this.top - (int) this.pageListScrollAmount;
+            if (pagesListHeight < this.bottom - this.top) {
+                pagesListY = this.top + (this.bottom - this.top - pagesListHeight) / 2;
             }
-            if (my >= top && my <= bottom) {
-                hoveredPage = drawPagesListItems(pageListLeft + PADDING - 4, pagesListY, pageListRight - PADDING, mx, my);
+            if (my >= this.top && my <= this.bottom) {
+                this.hoveredPage = drawPagesListItems(this.pageListLeft + PADDING - 4, pagesListY, this.pageListRight - PADDING, mx, my);
             } else {
-                hoveredPage = drawPagesListItems(pageListLeft + PADDING - 4, pagesListY, pageListRight - PADDING, -1, -1);
+                this.hoveredPage = drawPagesListItems(this.pageListLeft + PADDING - 4, pagesListY, this.pageListRight - PADDING, -1, -1);
             }
             Scissor.disable();
         }
 
         {
-            GL11.glDisable(GL11.GL_TEXTURE_2D);
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-            GL11.glDisable(GL11.GL_ALPHA_TEST);
-            GL11.glShadeModel(GL11.GL_SMOOTH);
+            GLRenderer.pushFrame();
+            GLRenderer.setShader(Shaders.COLOR);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+//            GL11.glDisable(GL11.GL_ALPHA_TEST);
+//            GL11.glShadeModel(GL11.GL_SMOOTH);
 
             byte fadeDist = 4;
-            Tessellator tessellator = Tessellator.instance;
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
             if (drawSidebar()) {
                 tessellator.startDrawingQuads();
-                tessellator.setColorRGBA_I(0, 0);
-                tessellator.addVertexWithUV(pageListLeft, top + fadeDist, 0.0D, 0.0D, 1.0D);
-                tessellator.addVertexWithUV(pageListRight, top + fadeDist, 0.0D, 1.0D, 1.0D);
-                tessellator.setColorRGBA_I(0, 255);
-                tessellator.addVertexWithUV(pageListRight, top, 0.0D, 1.0D, 0.0D);
-                tessellator.addVertexWithUV(pageListLeft, top, 0.0D, 0.0D, 0.0D);
+                tessellator.setColor2i(0, 0);
+                tessellator.addVertexWithUV(this.pageListLeft, this.top + fadeDist, 0.0D, 0.0D, 1.0D);
+                tessellator.addVertexWithUV(this.pageListRight, this.top + fadeDist, 0.0D, 1.0D, 1.0D);
+                tessellator.setColor2i(0, 255);
+                tessellator.addVertexWithUV(this.pageListRight, this.top, 0.0D, 1.0D, 0.0D);
+                tessellator.addVertexWithUV(this.pageListLeft, this.top, 0.0D, 0.0D, 0.0D);
                 tessellator.draw();
 
                 tessellator.startDrawingQuads();
-                tessellator.setColorRGBA_I(0, 255);
-                tessellator.addVertexWithUV(pageListLeft, bottom, 0.0D, 0.0D, 1.0D);
-                tessellator.addVertexWithUV(pageListRight, bottom, 0.0D, 1.0D, 1.0D);
-                tessellator.setColorRGBA_I(0, 0);
-                tessellator.addVertexWithUV(pageListRight, bottom - fadeDist, 0.0D, 1.0D, 0.0D);
-                tessellator.addVertexWithUV(pageListLeft, bottom - fadeDist, 0.0D, 0.0D, 0.0D);
+                tessellator.setColor2i(0, 255);
+                tessellator.addVertexWithUV(this.pageListLeft, this.bottom, 0.0D, 0.0D, 1.0D);
+                tessellator.addVertexWithUV(this.pageListRight, this.bottom, 0.0D, 1.0D, 1.0D);
+                tessellator.setColor2i(0, 0);
+                tessellator.addVertexWithUV(this.pageListRight, this.bottom - fadeDist, 0.0D, 1.0D, 0.0D);
+                tessellator.addVertexWithUV(this.pageListLeft, this.bottom - fadeDist, 0.0D, 0.0D, 0.0D);
                 tessellator.draw();
 
                 tessellator.startDrawingQuads();
-                tessellator.setColorRGBA_I(0, 0);
-                tessellator.addVertexWithUV(viewportLeft, top + fadeDist, 0.0D, 0.0D, 1.0D);
-                tessellator.addVertexWithUV(viewportRight, top + fadeDist, 0.0D, 1.0D, 1.0D);
-                tessellator.setColorRGBA_I(0, 255);
-                tessellator.addVertexWithUV(viewportRight, top, 0.0D, 1.0D, 0.0D);
-                tessellator.addVertexWithUV(viewportLeft, top, 0.0D, 0.0D, 0.0D);
+                tessellator.setColor2i(0, 0);
+                tessellator.addVertexWithUV(this.viewportLeft, this.top + fadeDist, 0.0D, 0.0D, 1.0D);
+                tessellator.addVertexWithUV(this.viewportRight, this.top + fadeDist, 0.0D, 1.0D, 1.0D);
+                tessellator.setColor2i(0, 255);
+                tessellator.addVertexWithUV(this.viewportRight, this.top, 0.0D, 1.0D, 0.0D);
+                tessellator.addVertexWithUV(this.viewportLeft, this.top, 0.0D, 0.0D, 0.0D);
                 tessellator.draw();
 
                 tessellator.startDrawingQuads();
-                tessellator.setColorRGBA_I(0, 255);
-                tessellator.addVertexWithUV(viewportLeft, bottom, 0.0D, 0.0D, 1.0D);
-                tessellator.addVertexWithUV(viewportRight, bottom, 0.0D, 1.0D, 1.0D);
-                tessellator.setColorRGBA_I(0, 0);
-                tessellator.addVertexWithUV(viewportRight, bottom - fadeDist, 0.0D, 1.0D, 0.0D);
-                tessellator.addVertexWithUV(viewportLeft, bottom - fadeDist, 0.0D, 0.0D, 0.0D);
+                tessellator.setColor2i(0, 255);
+                tessellator.addVertexWithUV(this.viewportLeft, this.bottom, 0.0D, 0.0D, 1.0D);
+                tessellator.addVertexWithUV(this.viewportRight, this.bottom, 0.0D, 1.0D, 1.0D);
+                tessellator.setColor2i(0, 0);
+                tessellator.addVertexWithUV(this.viewportRight, this.bottom - fadeDist, 0.0D, 1.0D, 0.0D);
+                tessellator.addVertexWithUV(this.viewportLeft, this.bottom - fadeDist, 0.0D, 0.0D, 0.0D);
                 tessellator.draw();
             } else {
                 tessellator.startDrawingQuads();
-                tessellator.setColorRGBA_I(0, 0);
-                tessellator.addVertexWithUV(0, top + fadeDist, 0.0D, 0.0D, 1.0D);
-                tessellator.addVertexWithUV(width, top + fadeDist, 0.0D, 1.0D, 1.0D);
-                tessellator.setColorRGBA_I(0, 255);
-                tessellator.addVertexWithUV(width, top, 0.0D, 1.0D, 0.0D);
-                tessellator.addVertexWithUV(0, top, 0.0D, 0.0D, 0.0D);
+                tessellator.setColor2i(0, 0);
+                tessellator.addVertexWithUV(0, this.top + fadeDist, 0.0D, 0.0D, 1.0D);
+                tessellator.addVertexWithUV(this.width, this.top + fadeDist, 0.0D, 1.0D, 1.0D);
+                tessellator.setColor2i(0, 255);
+                tessellator.addVertexWithUV(this.width, this.top, 0.0D, 1.0D, 0.0D);
+                tessellator.addVertexWithUV(0, this.top, 0.0D, 0.0D, 0.0D);
                 tessellator.draw();
 
                 tessellator.startDrawingQuads();
-                tessellator.setColorRGBA_I(0, 255);
-                tessellator.addVertexWithUV(0, bottom, 0.0D, 0.0D, 1.0D);
-                tessellator.addVertexWithUV(width, bottom, 0.0D, 1.0D, 1.0D);
-                tessellator.setColorRGBA_I(0, 0);
-                tessellator.addVertexWithUV(width, bottom - fadeDist, 0.0D, 1.0D, 0.0D);
-                tessellator.addVertexWithUV(0, bottom - fadeDist, 0.0D, 0.0D, 0.0D);
+                tessellator.setColor2i(0, 255);
+                tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0.0D, 1.0D);
+                tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, 1.0D, 1.0D);
+                tessellator.setColor2i(0, 0);
+                tessellator.addVertexWithUV(this.width, this.bottom - fadeDist, 0.0D, 1.0D, 0.0D);
+                tessellator.addVertexWithUV(0, this.bottom - fadeDist, 0.0D, 0.0D, 0.0D);
                 tessellator.draw();
             }
-            GL11.glEnable(GL_TEXTURE_2D);
-            GL11.glEnable(GL11.GL_ALPHA_TEST);
+            GLRenderer.popFrame();
         }
 
-        if (hoveredAchievement != null){
-            drawAchievementToolTip(hoveredAchievement, mx, my);
+        if (this.hoveredAchievement != null){
+            drawAchievementToolTip(this.hoveredAchievement, mx, my);
         }
 
         if (drawSidebar()) {
             drawPagesListScrollBar(mx, my);
 
-            if (hoveredPage != null){
-                final String msg = this.hoveredPage.getDescription() + "\n" + TextFormatting.LIGHT_GRAY + I18n.getInstance().translateKeyAndFormat("gui.achievements.label.completion",  Math.round(hoveredPage.getCompletionFraction(statsCounter) * 100) + "%");
+            if (this.hoveredPage != null){
+                final String msg = this.hoveredPage.getDescription() + "\n" + TextFormatting.LIGHT_GRAY + I18n.getInstance().translateKeyAndFormat("gui.achievements.label.completion",  Math.round(this.hoveredPage.getCompletionFraction(this.statsCounter) * 100) + "%");
                 this.tooltip.render(msg, mx, my, TOOLTIP_OFF_X, TOOLTIP_OFF_Y, TOOLTIP_BOX_WIDTH_MIN, -1, true);
             }
         }
 
         renderLabels();
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
+        GLRenderer.enableState(State.DEPTH_TEST);
 
-        hoveredAchievement = null;
-        hoveredPage = null;
+        this.hoveredAchievement = null;
+        this.hoveredPage = null;
     }
 
     @Override
 	public void tick() {
-        oldShiftX = targetShiftX;
-        oldShiftY = targetShiftY;
-        double xDiff = currentShiftX - targetShiftX;
-        double yDiff = currentShiftY - targetShiftY;
+        this.oldShiftX = this.targetShiftX;
+        this.oldShiftY = this.targetShiftY;
+        double xDiff = this.currentShiftX - this.targetShiftX;
+        double yDiff = this.currentShiftY - this.targetShiftY;
         if(xDiff * xDiff + yDiff * yDiff < 4D) {
-            targetShiftX += xDiff;
-            targetShiftY += yDiff;
+            this.targetShiftX += xDiff;
+            this.targetShiftY += yDiff;
         } else {
-            targetShiftX += xDiff * 0.85D;
-            targetShiftY += yDiff * 0.85D;
+            this.targetShiftX += xDiff * 0.85D;
+            this.targetShiftY += yDiff * 0.85D;
         }
     }
 
     protected void renderLabels() {
-        drawStringCenteredNoShadow(fontRenderer, I18n.getInstance().translateKey("gui.achievements.label.title")/* + " " + viewportZoom + " X:" + currentShiftX + ", Y:" + currentShiftY*/, width/2, 5 , 0xFFFFFF);
+        drawStringCenteredNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.achievements.label.title")/* + " " + viewportZoom + " X:" + currentShiftX + ", Y:" + currentShiftY*/, this.width /2, 5 , 0xFFFFFF);
     }
 
 
     protected void renderAchievementsPanel(int mouseX, int mouseY, float partialTick){
-        double shiftX = MathHelper.lerp(oldShiftX, targetShiftX, partialTick);
-        double shiftY = MathHelper.lerp(oldShiftY, targetShiftY, partialTick);
-        shiftX =  MathHelper.clamp(shiftX, shiftMinX, shiftMaxX);
-        shiftY =  MathHelper.clamp(shiftY, shiftMinY, shiftMaxY);
-
-        zLevel = 0.0F;
-
-        GL11.glDepthFunc(GL11.GL_GEQUAL);
-        GL11.glPushMatrix();
-        GL11.glTranslatef(0, 0, -200F);
-        Scissor.enable(viewportLeft, viewportTop, viewportWidth, viewportHeight);
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
-        drawRectDouble(viewportLeft, viewportTop, viewportRight, viewportBottom, 0xFF000000 | currentPage.backgroundColor()); // Ensures that the viewport always has a background of some kind
-
-        GL11.glPushMatrix();
+        double shiftX = MathHelper.lerp(this.oldShiftX, this.targetShiftX, partialTick);
+        double shiftY = MathHelper.lerp(this.oldShiftY, this.targetShiftY, partialTick);
+        shiftX =  MathHelper.clamp(shiftX, this.shiftMinX, this.shiftMaxX);
+        shiftY =  MathHelper.clamp(shiftY, this.shiftMinY, this.shiftMaxY);
+
+        this.zLevel = 0.0F;
+
+        GLRenderer.setDepthFunc(CompareFunc.GREATER_EQUAL);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate(0, 0, -200F);
+        Scissor.enable(this.viewportLeft, this.viewportTop, this.viewportWidth, this.viewportHeight);
+//        GL11.glEnable(GL11.GL_TEXTURE_2D);
+        GLRenderer.globalSetLightEnabled(false);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
+        drawRectDouble(this.viewportLeft, this.viewportTop, this.viewportRight, this.viewportBottom, 0xFF000000 | this.currentPage.backgroundColor()); // Ensures that the viewport always has a background of some kind
+
+        GLRenderer.pushFrame();
         drawBackgroundTiles(shiftX, shiftY);
 
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glDepthFunc(GL11.GL_LEQUAL); // Responsible for culling the overdraw later on
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.setDepthFunc(CompareFunc.LESS_EQUAL); // Responsible for culling the overdraw later on
         drawConnectingLines(mouseX, mouseY,shiftX, shiftY);
 
         Lighting.enableInventoryLight();
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
-        hoveredAchievement = drawAchievementIcons(mouseX, mouseY, shiftX, shiftY);
+        GLRenderer.globalSetLightEnabled(false);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
+        this.hoveredAchievement = drawAchievementIcons(mouseX, mouseY, shiftX, shiftY);
 
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
 
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         Scissor.disable();
 
 //        drawRectDouble(viewportLeft + viewportWidth/2d - 2.5, viewportTop + viewportHeight/2d - 2.5, viewportLeft + viewportWidth/2d + 2.5, viewportTop + viewportHeight/2d + 2.5, 0xFFA0A0A0); // Debug cross-hair
 
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
 
-        zLevel = 0.0F;
-        GL11.glDepthFunc(GL11.GL_LEQUAL);
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
+        this.zLevel = 0.0F;
+        GLRenderer.setDepthFunc(CompareFunc.LESS_EQUAL);
+        GLRenderer.disableState(State.DEPTH_TEST);
     }
 
     private static final int TILE_WIDTH = 16;
@@ -501,10 +522,12 @@ public class ScreenAchievements extends Screen
     public int lastTileY = Integer.MIN_VALUE;
     public int lastTilesWide = Integer.MIN_VALUE;
     public int lastTilesTall = Integer.MIN_VALUE;
+    public @Nullable RenderBuffer lastBackgroundTileBuf;
+    public @Nullable RenderBuffer lastBackgroundShadowBuf;
     private void drawBackgroundTiles(double shiftX, double shiftY){
-        double zoom = viewportZoom/* * 0.85*/;
+        double zoom = this.viewportZoom/* * 0.85*/;
 
-        TextureRegistry.blockAtlas.bind();
+        TextureRegistry.worldAtlas.bind();
         final int offset = 18 * TILE_WIDTH;
         int viewTileX = (MathHelper.floor(shiftX) + offset) / TILE_WIDTH;
         int viewTileY = (MathHelper.floor(shiftY) + offset) / TILE_HEIGHT;
@@ -512,8 +535,8 @@ public class ScreenAchievements extends Screen
         double remainderY = (shiftY + offset) % TILE_HEIGHT;
         Random random = new Random();
 
-        int tilesWide = (int) (viewportWidth/(TILE_WIDTH * zoom) + 2);
-        int tilesTall = (int) (viewportHeight/(TILE_HEIGHT * zoom) + 2);
+        int tilesWide = (int) (this.viewportWidth /(TILE_WIDTH * zoom) + 2);
+        int tilesTall = (int) (this.viewportHeight /(TILE_HEIGHT * zoom) + 2);
 
         int orgX = -tilesWide/2 - 1;
         int orgY = -tilesTall/2 - 1;
@@ -524,17 +547,19 @@ public class ScreenAchievements extends Screen
         tilesTall = endY - orgY;
 
         // Cache background, saves some render time which is nice
-        if (viewTileX != lastTileX || viewTileY != lastTileY || tilesWide != lastTilesWide || tilesTall != lastTilesTall) {
-            lastTileX = viewTileX;
-            lastTileY = viewTileY;
-            lastTilesWide = tilesWide;
-            lastTilesTall = tilesTall;
-
-            for (BGLayer layer : layers){
+        boolean dirty = false;
+        if (viewTileX != this.lastTileX || viewTileY != this.lastTileY || tilesWide != this.lastTilesWide || tilesTall != this.lastTilesTall) {
+            this.lastTileX = viewTileX;
+            this.lastTileY = viewTileY;
+            this.lastTilesWide = tilesWide;
+            this.lastTilesTall = tilesTall;
+            dirty = true;
+
+            for (BGLayer layer : this.layers){
                 layer.resize(tilesWide, tilesTall);
             }
 
-            long worldSeed = mc.currentWorld == null ? 0 : mc.currentWorld.getRandomSeed();
+            long worldSeed = this.mc.currentWorld == null ? 0 : this.mc.currentWorld.getRandomSeed();
             for (int _y = 0; _y < tilesTall; _y++){
                 for (int _x = 0; _x < tilesWide; _x++) {
                     int tileX = orgX + _x + viewTileX;
@@ -549,9 +574,9 @@ public class ScreenAchievements extends Screen
 
                     long seed = Objects.hash(l1, l2, ~l3);
 
-                    for (BGLayer layer : layers) {
+                    for (BGLayer layer : this.layers) {
                         random.setSeed(seed);
-                        IconCoordinate fore = currentPage.getBackgroundTile(this, layer.id, random, tileX, tileY);
+                        IconCoordinate fore = this.currentPage.getBackgroundTile(this, layer.id, random, tileX, tileY);
                         layer.put(fore, _x, _y);
                     }
                 }
@@ -567,186 +592,234 @@ public class ScreenAchievements extends Screen
 //            long seed = Objects.hash(l1, l2, ~l3);
 //            random.setSeed(seed);
 
-            for (BGLayer layer : layers) {
+            for (BGLayer layer : this.layers) {
                 random.setSeed(worldSeed);
-                currentPage.postProcessBackground(this, random, layer, orgX + viewTileX, orgY + viewTileY);
+                this.currentPage.postProcessBackground(this, random, layer, orgX + viewTileX, orgY + viewTileY);
             }
         }
 
 
-
-        for(int _y = 0; _y < tilesTall; _y++) {
-            int tileY = orgY + _y + viewTileY;
-            float brightness = 0.6F - ((float)(tileY) / 25F) * 0.3F;
-            for(int _x = 0; _x < tilesWide; _x++) {
-                int tileX = orgX + _x + viewTileX;
-
-                for (int i = layers.length - 1; i >= 0; i--) {
-                    BGLayer topLayer = getLayer(i);
-                    IconCoordinate fore = topLayer.get(_x, _y);
-
-                    IconCoordinate next = null;
-                    if (i - 1 >= 0) {
-                        BGLayer nextLayer = getLayer(i - 1);
-                        next = nextLayer.get(_x, _y);
-                    }
-
-
-                    boolean bottom = false;
-                    boolean top = false;
-                    boolean left = false;
-                    boolean right = false;
-                    boolean topLeft = false;
-                    boolean topRight = false;
-                    boolean bottomLeft = false;
-                    boolean bottomRight = false;
-
-
-                    if (fore != null && next == null && i - 1 >= 0) {
-                        BGLayer nextLayer = getLayer(i - 1);
-                        top = nextLayer.get(_x, _y - 1) != null;
-                        left = nextLayer.get(_x - 1, _y) != null;
-                        right = nextLayer.get(_x + 1, _y) != null;
-                        bottom = nextLayer.get(_x, _y + 1) != null;
-                        topLeft = nextLayer.get(_x - 1, _y - 1) != null;
-                        topRight = nextLayer.get(_x + 1, _y - 1) != null;
-                        bottomLeft = nextLayer.get(_x - 1, _y + 1) != null;
-                        bottomRight = nextLayer.get(_x + 1, _y + 1) != null;
-                    }
-
-                    double iconLeft = (viewportLeft + viewportWidth / 2d) + zoom * (((orgX + _x) * TILE_WIDTH) - remainderX);
-                    double iconTop = (viewportTop + viewportHeight / 2d) + zoom * (((orgY + _y) * TILE_HEIGHT) - remainderY);
-                    double iconWidth = TILE_WIDTH * zoom;
-                    double iconHeight = TILE_HEIGHT * zoom;
-
-                    if (fore != null) {
-                        float shadowScale = (float) Math.pow(0.65f, i);
-                        if (next != null) {
-                            shadowScale *= 0.5f;
+        if (dirty) {
+            for (int renderpass = 0; renderpass < 2; renderpass++) {
+                TessellatorGeneral t = GLRenderer.getTessellator();
+                if (renderpass == 0) {
+                    t.startDrawingQuads();
+                } else {
+                    t.startDrawing(DrawMode.TRIANGLES);
+                }
+                for(int _y = 0; _y < tilesTall; _y++) {
+                    int tileY = orgY + _y + viewTileY;
+                    float brightness = 0.6F - ((float)(tileY) / 25F) * 0.3F;
+                    for(int _x = 0; _x < tilesWide; _x++) {
+                        int tileX = orgX + _x + viewTileX;
+
+                        for (int i = this.layers.length - 1; i >= 0; i--) {
+                            BGLayer topLayer = getLayer(i);
+                            IconCoordinate fore = topLayer.get(_x, _y);
+
+                            IconCoordinate next = null;
+                            if (i - 1 >= 0) {
+                                BGLayer nextLayer = getLayer(i - 1);
+                                next = nextLayer.get(_x, _y);
+                            }
+
+
+                            boolean bottom = false;
+                            boolean top = false;
+                            boolean left = false;
+                            boolean right = false;
+                            boolean topLeft = false;
+                            boolean topRight = false;
+                            boolean bottomLeft = false;
+                            boolean bottomRight = false;
+
+
+                            if (fore != null && next == null && i - 1 >= 0) {
+                                BGLayer nextLayer = getLayer(i - 1);
+                                top = nextLayer.get(_x, _y - 1) != null;
+                                left = nextLayer.get(_x - 1, _y) != null;
+                                right = nextLayer.get(_x + 1, _y) != null;
+                                bottom = nextLayer.get(_x, _y + 1) != null;
+                                topLeft = nextLayer.get(_x - 1, _y - 1) != null;
+                                topRight = nextLayer.get(_x + 1, _y - 1) != null;
+                                bottomLeft = nextLayer.get(_x - 1, _y + 1) != null;
+                                bottomRight = nextLayer.get(_x + 1, _y + 1) != null;
+                            }
+
+                            double iconLeft = _x * TILE_WIDTH;
+                            double iconTop = _y * TILE_WIDTH;
+                            double iconWidth = TILE_WIDTH;
+                            double iconHeight = TILE_HEIGHT;
+
+
+                            if (renderpass == 0) { // Background block tile quads pass
+                                if (fore != null) {
+                                    float shadowScale = (float) Math.pow(0.65f, i);
+                                    if (next != null) {
+                                        shadowScale *= 0.5f;
+                                    }
+                                    t.setColor4f(brightness * shadowScale, brightness * shadowScale, brightness * shadowScale, 1.0F);
+                                    addGuiIconDouble(t, iconLeft, iconTop, iconWidth, iconHeight, fore);
+                                }
+                            } else { // Background shadow tri pass
+                                final double off = 0;
+                                double fadeDist = 6 * zoom;
+                                short shadowDarkness = 128;
+
+                                if (top) {
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft - off, iconTop + fadeDist + off, 0.0D);
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + iconWidth + off, iconTop + fadeDist + off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft - off, iconTop - off, 0.0D);
+
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft - off, iconTop - off, 0.0D);
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + iconWidth + off, iconTop + fadeDist + off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft + iconWidth + off, iconTop - off, 0.0D);
+                                }
+                                if (left) {
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + fadeDist + off, iconTop + iconHeight + off, 0.0D);
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + fadeDist + off, iconTop - off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft - off, iconTop + iconHeight + off, 0.0D);
+
+
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft - off, iconTop + iconHeight + off, 0.0D);
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + fadeDist + off, iconTop - off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft - off, iconTop - off, 0.0D);
+                                }
+                                if (bottom) {
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + iconWidth + off, iconTop + iconHeight - fadeDist + off, 0.0D);
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft - off, iconTop + iconHeight - fadeDist + off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft + iconWidth + off, iconTop + iconHeight - off, 0.0D);
+
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft + iconWidth + off, iconTop + iconHeight - off, 0.0D);
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft - off, iconTop + iconHeight - fadeDist + off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft - off, iconTop + iconHeight - off, 0.0D);
+                                }
+                                if (right) {
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + iconWidth - fadeDist + off, iconTop - off, 0.0D);
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + iconWidth - fadeDist + off, iconTop + iconHeight + off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft + iconWidth - off, iconTop - off, 0.0D);
+
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft + iconWidth - off, iconTop - off, 0.0D);
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + iconWidth - fadeDist + off, iconTop + iconHeight + off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft + iconWidth - off, iconTop + iconHeight + off, 0.0D);
+                                }
+                                if (topLeft && !(left || top)) {
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft - off, iconTop + fadeDist + off, 0.0D);
+                                    t.addVertex(iconLeft + fadeDist + off, iconTop - off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft - off, iconTop - off, 0.0D);
+                                }
+                                if (topRight && !(right || top)) {
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + iconWidth - fadeDist + off, iconTop - off, 0.0D);
+                                    t.addVertex(iconLeft + iconWidth - off, iconTop + fadeDist + off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft + iconWidth - off, iconTop - off, 0.0D);
+                                }
+                                if (bottomLeft && !(left || bottom)) {
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + fadeDist + off, iconTop + iconHeight - off, 0.0D);
+                                    t.addVertex(iconLeft - off, iconTop + iconHeight - fadeDist + off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft - off, iconTop + iconHeight - off, 0.0D);
+                                }
+                                if (bottomRight && !(right || bottom)) {
+                                    t.setColor2i(0, 0);
+                                    t.addVertex(iconLeft + iconWidth - off, iconTop + iconHeight - fadeDist + off, 0.0D);
+                                    t.addVertex(iconLeft + iconWidth - fadeDist + off, iconTop + iconHeight - off, 0.0D);
+                                    t.setColor2i(0, shadowDarkness);
+                                    t.addVertex(iconLeft + iconWidth - off, iconTop + iconHeight - off, 0.0D);
+                                }
+                            }
                         }
-                        GL11.glColor4f(brightness * shadowScale, brightness * shadowScale, brightness * shadowScale, 1.0F);
-                        final double epsilon = 0.05;
-                        drawGuiIconDouble(iconLeft - epsilon, iconTop - epsilon, iconWidth + epsilon * 2, iconHeight + epsilon * 2, fore);
-                    }
-
-                    GL11.glDisable(GL11.GL_TEXTURE_2D);
-                    GL11.glEnable(GL11.GL_BLEND);
-                    GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-                    GL11.glDisable(GL11.GL_ALPHA_TEST);
-                    GL11.glShadeModel(GL11.GL_SMOOTH);
-                    Tessellator t = Tessellator.instance;
-                    final double off = 0.05d;
-                    double fadeDist = 6 * zoom;
-                    short shadowDarkness = 128;
-                    if (top) {
-                        t.startDrawingQuads();
-                        t.setColorRGBA_I(0, 0);
-                        t.addVertexWithUV(iconLeft - off, iconTop + fadeDist + off, 0.0D, 0.0D, 1.0D);
-                        t.addVertexWithUV(iconLeft + iconWidth + off, iconTop + fadeDist + off, 0.0D, 1.0D, 1.0D);
-                        t.setColorRGBA_I(0, shadowDarkness);
-                        t.addVertexWithUV(iconLeft + iconWidth + off, iconTop - off, 0.0D, 1.0D, 0.0D);
-                        t.addVertexWithUV(iconLeft - off, iconTop - off, 0.0D, 0.0D, 0.0D);
-                        t.draw();
-                    }
-                    if (left) {
-                        t.startDrawingQuads();
-                        t.setColorRGBA_I(0, 0);
-                        t.addVertexWithUV(iconLeft + fadeDist + off, iconTop + iconHeight + off, 0.0D, 1.0D, 1.0D);
-                        t.addVertexWithUV(iconLeft + fadeDist + off, iconTop - off, 0.0D, 0.0D, 1.0D);
-                        t.setColorRGBA_I(0, shadowDarkness);
-                        t.addVertexWithUV(iconLeft - off, iconTop - off, 0.0D, 0.0D, 0.0D);
-                        t.addVertexWithUV(iconLeft - off, iconTop + iconHeight + off, 0.0D, 1.0D, 0.0D);
-                        t.draw();
                     }
-                    if (bottom) {
-                        t.startDrawingQuads();
-                        t.setColorRGBA_I(0, 0);
-                        t.addVertexWithUV(iconLeft + iconWidth + off, iconTop + iconHeight - fadeDist + off, 0.0D, 1.0D, 1.0D);
-                        t.addVertexWithUV(iconLeft - off, iconTop + iconHeight - fadeDist + off, 0.0D, 0.0D, 1.0D);
-                        t.setColorRGBA_I(0, shadowDarkness);
-                        t.addVertexWithUV(iconLeft - off, iconTop + iconHeight - off, 0.0D, 0.0D, 0.0D);
-                        t.addVertexWithUV(iconLeft + iconWidth + off, iconTop + iconHeight - off, 0.0D, 1.0D, 0.0D);
-                        t.draw();
-                    }
-                    if (right) {
-                        t.startDrawingQuads();
-                        t.setColorRGBA_I(0, 0);
-                        t.addVertexWithUV(iconLeft + iconWidth - fadeDist + off, iconTop - off, 0.0D, 0.0D, 1.0D);
-                        t.addVertexWithUV(iconLeft + iconWidth - fadeDist + off, iconTop + iconHeight + off, 0.0D, 1.0D, 1.0D);
-                        t.setColorRGBA_I(0, shadowDarkness);
-                        t.addVertexWithUV(iconLeft + iconWidth - off, iconTop + iconHeight + off, 0.0D, 1.0D, 0.0D);
-                        t.addVertexWithUV(iconLeft + iconWidth - off, iconTop - off, 0.0D, 0.0D, 0.0D);
-                        t.draw();
-                    }
-                    if (topLeft && !(left || top)) {
-                        t.startDrawing(GL11.GL_TRIANGLES);
-                        t.setColorRGBA_I(0, 0);
-                        t.addVertexWithUV(iconLeft - off, iconTop + fadeDist + off, 0.0D, 1.0D, 0.0D);
-                        t.addVertexWithUV(iconLeft + fadeDist + off, iconTop - off, 0.0D, 0.0D, 0.0D);
-                        t.setColorRGBA_I(0, shadowDarkness);
-                        t.addVertexWithUV(iconLeft - off, iconTop - off, 0.0D, 0.0D, 1.0D);
-                        t.draw();
-                    }
-                    if (topRight && !(right || top)) {
-                        t.startDrawing(GL11.GL_TRIANGLES);
-                        t.setColorRGBA_I(0, 0);
-                        t.addVertexWithUV(iconLeft + iconWidth - fadeDist + off, iconTop - off, 0.0D, 0.0D, 0.0D);
-                        t.addVertexWithUV(iconLeft + iconWidth - off, iconTop + fadeDist + off, 0.0D, 1.0D, 0.0D);
-                        t.setColorRGBA_I(0, shadowDarkness);
-                        t.addVertexWithUV(iconLeft + iconWidth - off, iconTop - off, 0.0D, 0.0D, 1.0D);
-                        t.draw();
-                    }
-                    if (bottomLeft && !(left || bottom)) {
-                        t.startDrawing(GL11.GL_TRIANGLES);
-                        t.setColorRGBA_I(0, 0);
-                        t.addVertexWithUV(iconLeft + fadeDist + off, iconTop + iconHeight - off, 0.0D, 0.0D, 0.0D);
-                        t.addVertexWithUV(iconLeft - off, iconTop + iconHeight - fadeDist + off, 0.0D, 1.0D, 0.0D);
-                        t.setColorRGBA_I(0, shadowDarkness);
-                        t.addVertexWithUV(iconLeft - off, iconTop + iconHeight - off, 0.0D, 0.0D, 1.0D);
-                        t.draw();
+                }
+                if (renderpass == 0) {
+                    if (this.lastBackgroundTileBuf == null) {
+                        this.lastBackgroundTileBuf = t.record(GL41.glGenVertexArrays(), GL41.glGenBuffers());
+                    } else {
+                        this.lastBackgroundTileBuf = t.record(this.lastBackgroundTileBuf.vao(), this.lastBackgroundTileBuf.vbo());
                     }
-                    if (bottomRight && !(right || bottom)) {
-                        t.startDrawing(GL11.GL_TRIANGLES);
-                        t.setColorRGBA_I(0, 0);
-                        t.addVertexWithUV(iconLeft + iconWidth - off, iconTop + iconHeight - fadeDist + off, 0.0D, 1.0D, 0.0D);
-                        t.addVertexWithUV(iconLeft + iconWidth - fadeDist + off, iconTop + iconHeight - off, 0.0D, 0.0D, 0.0D);
-                        t.setColorRGBA_I(0, shadowDarkness);
-                        t.addVertexWithUV(iconLeft + iconWidth - off, iconTop + iconHeight - off, 0.0D, 0.0D, 1.0D);
-                        t.draw();
+                } else {
+                    if (this.lastBackgroundShadowBuf == null) {
+                        this.lastBackgroundShadowBuf = t.record(GL41.glGenVertexArrays(), GL41.glGenBuffers());
+                    } else {
+                        this.lastBackgroundShadowBuf = t.record(this.lastBackgroundShadowBuf.vao(), this.lastBackgroundShadowBuf.vbo());
                     }
-                    GL11.glEnable(GL_TEXTURE_2D);
-                    GL11.glEnable(GL11.GL_ALPHA_TEST);
                 }
             }
         }
+        double iconLeft = (this.viewportLeft + this.viewportWidth / 2d) + zoom * (orgX * TILE_WIDTH) - zoom * remainderX;
+        double iconTop = (this.viewportTop + this.viewportHeight / 2d) + zoom * ((orgY * TILE_HEIGHT) - remainderY);
+
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) iconLeft, (float) iconTop,0).scale((float) zoom, (float) zoom, 1);
+        if (this.lastBackgroundTileBuf != null) {
+            TextureRegistry.worldAtlas.bind();
+            GLRenderer.render(this.lastBackgroundTileBuf);
+        }
+        if (this.lastBackgroundShadowBuf != null) {
+            GLRenderer.pushFrame();
+            GLRenderer.setShader(Shaders.COLOR);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.render(this.lastBackgroundShadowBuf);
+            GLRenderer.popFrame();
+        }
+        GLRenderer.popFrame();
     }
 
     public BGLayer getLayer(int layer){
-        if (layer < 0 || layer >= layers.length) return null;
-        return layers[layer];
+        if (layer < 0 || layer >= this.layers.length) return null;
+        return this.layers[layer];
     }
 
     private double timeSin(double amplitude, long period){
         return Math.sin(((double)(System.currentTimeMillis() % period) / period) * Math.PI * 2D) * amplitude;
     }
     private void drawConnectingLines(int mouseX, int mouseY, double shiftX, double shiftY){
-        double zoom = viewportZoom;
+        double zoom = this.viewportZoom;
 
-        for(AchievementPage.AchievementEntry entry : currentPage.getAchievementEntries()) {
+        for(AchievementPage.AchievementEntry entry : this.currentPage.getAchievementEntries()) {
             Achievement ach = entry.achievement;
-            AchievementPage.AchievementEntry parentEntry = currentPage.getEntry(ach.parent);
+            AchievementPage.AchievementEntry parentEntry = this.currentPage.getEntry(ach.parent);
             if(parentEntry == null) {
                 continue;
             }
-            if (!currentPage.hasAchievement(ach) || !currentPage.hasAchievement(ach.parent)){
+            if (!this.currentPage.hasAchievement(ach) || !this.currentPage.hasAchievement(ach.parent)){
                 continue;
             }
-            double childX = (viewportLeft + viewportWidth/2d) + ((entry.x * ACHIEVEMENT_CELL_WIDTH - shiftX) + 11) * zoom;
-            double childY = (viewportTop + viewportHeight/2d) + ((entry.y * ACHIEVEMENT_CELL_HEIGHT - shiftY) + 11) * zoom;
-            double parentX = (viewportLeft + viewportWidth/2d) + ((parentEntry.x * ACHIEVEMENT_CELL_WIDTH - shiftX) + 11) * zoom;
-            double parentY = (viewportTop + viewportHeight/2d) + ((parentEntry.y * ACHIEVEMENT_CELL_HEIGHT - shiftY) + 11) * zoom;
-            boolean unlocked = statsCounter.isUnlocked(ach);
-            boolean canUnlock = statsCounter.canUnlock(ach);
+            double childX = (this.viewportLeft + this.viewportWidth /2d) + ((entry.x * ACHIEVEMENT_CELL_WIDTH - shiftX) + 11) * zoom;
+            double childY = (this.viewportTop + this.viewportHeight /2d) + ((entry.y * ACHIEVEMENT_CELL_HEIGHT - shiftY) + 11) * zoom;
+            double parentX = (this.viewportLeft + this.viewportWidth /2d) + ((parentEntry.x * ACHIEVEMENT_CELL_WIDTH - shiftX) + 11) * zoom;
+            double parentY = (this.viewportTop + this.viewportHeight /2d) + ((parentEntry.y * ACHIEVEMENT_CELL_HEIGHT - shiftY) + 11) * zoom;
+            boolean unlocked = this.statsCounter.isUnlocked(ach);
+            boolean canUnlock = this.statsCounter.canUnlock(ach);
 
             final double zoomOff = 11 * zoom;
 //            if (
@@ -759,14 +832,14 @@ public class ScreenAchievements extends Screen
             {
                 double x = parentX - zoomOff;
                 double y = parentY - zoomOff;
-                if ((mouseX >= 0 && mouseY >= viewportTop && mouseX < width && mouseY < viewportBottom) && // In viewport and
+                if ((mouseX >= 0 && mouseY >= this.viewportTop && mouseX < this.width && mouseY < this.viewportBottom) && // In viewport and
                     (mouseX >= x && mouseX <= x + 22 * zoom && mouseY >= y && mouseY <= y + 22 * zoom)) { // Hovering over achievement
                     isHovered = true;
                 }
 
                 x = childX - zoomOff;
                 y = childY - zoomOff;
-                if ((mouseX >= 0 && mouseY >= viewportTop && mouseX < width && mouseY < viewportBottom) && // In viewport and
+                if ((mouseX >= 0 && mouseY >= this.viewportTop && mouseX < this.width && mouseY < this.viewportBottom) && // In viewport and
                     (mouseX >= x && mouseX <= x + 22 * zoom && mouseY >= y && mouseY <= y + 22 * zoom)) { // Hovering over achievement
                     isHovered = true;
                 }
@@ -774,12 +847,12 @@ public class ScreenAchievements extends Screen
 
             int color;
             if(unlocked) {
-                color = 0xff << Color.SHIFT_ALPHA | (currentPage.lineColorUnlocked(isHovered) & 0xffffff);
+                color = 0xff << Color.SHIFT_ALPHA | (this.currentPage.lineColorUnlocked(isHovered) & 0xffffff);
             } else if (canUnlock) {
                 int alpha = timeSin(1, 600) >= 0.6 ? 0x82 : 0xff;
-                color = (alpha << Color.SHIFT_ALPHA) | (currentPage.lineColorCanUnlock(isHovered) & 0xffffff);
+                color = (alpha << Color.SHIFT_ALPHA) | (this.currentPage.lineColorCanUnlock(isHovered) & 0xffffff);
             } else {
-                color = 0xff << Color.SHIFT_ALPHA | (currentPage.lineColorLocked(isHovered) & 0xffffff);
+                color = 0xff << Color.SHIFT_ALPHA | (this.currentPage.lineColorLocked(isHovered) & 0xffffff);
             }
 
             drawLineHorizontalDouble(childX, parentX, childY, color);
@@ -789,53 +862,53 @@ public class ScreenAchievements extends Screen
 
     @Nullable
     private Achievement drawAchievementIcons(int mouseX, int mouseY, double shiftX, double shiftY){
-        double zoom = viewportZoom;
+        double zoom = this.viewportZoom;
 
         Achievement hoveredAchievment = null;
-        for(AchievementPage.AchievementEntry entry : currentPage.getAchievementEntries()) {
+        for(AchievementPage.AchievementEntry entry : this.currentPage.getAchievementEntries()) {
             Achievement ach = entry.achievement;
-            double achViewX = (viewportLeft + viewportWidth/2d) + (entry.x * ACHIEVEMENT_CELL_WIDTH - shiftX ) * zoom;
-            double achViewY = (viewportTop + viewportHeight/2d) + (entry.y * ACHIEVEMENT_CELL_HEIGHT - shiftY) * zoom;
-            if(achViewX < viewportLeft - ACHIEVEMENT_CELL_WIDTH * zoom || achViewY < viewportTop - ACHIEVEMENT_CELL_HEIGHT * zoom || achViewX > viewportRight || achViewY > viewportBottom) { // Continue if outside viewport
+            double achViewX = (this.viewportLeft + this.viewportWidth /2d) + (entry.x * ACHIEVEMENT_CELL_WIDTH - shiftX ) * zoom;
+            double achViewY = (this.viewportTop + this.viewportHeight /2d) + (entry.y * ACHIEVEMENT_CELL_HEIGHT - shiftY) * zoom;
+            if(achViewX < this.viewportLeft - ACHIEVEMENT_CELL_WIDTH * zoom || achViewY < this.viewportTop - ACHIEVEMENT_CELL_HEIGHT * zoom || achViewX > this.viewportRight || achViewY > this.viewportBottom) { // Continue if outside viewport
                 continue;
             }
 
-            if(statsCounter.isUnlocked(ach)) {
+            if(this.statsCounter.isUnlocked(ach)) {
                 float brightness = 1.0F;
-                GL11.glColor4f(brightness, brightness, brightness, 1.0F);
-            } else if(statsCounter.canUnlock(ach)) {
+                GLRenderer.setColor4f(brightness, brightness, brightness, 1.0F);
+            } else if(this.statsCounter.canUnlock(ach)) {
                 // Flicker if can unlock
                 float brightness = timeSin(1, 600) >= 0.6 ? 0.6F : 0.8F;
-                GL11.glColor4f(brightness, brightness, brightness, 1.0F);
+                GLRenderer.setColor4f(brightness, brightness, brightness, 1.0F);
             } else {
                 // Darken if not unlock-able
                 float brightness = 0.3F;
-                GL11.glColor4f(brightness, brightness, brightness, 1.0F);
+                GLRenderer.setColor4f(brightness, brightness, brightness, 1.0F);
             }
 
-            drawGuiIconDouble(achViewX - (ACHIEVEMENT_ICON_WIDTH - ACHIEVEMENT_CELL_WIDTH) * zoom, achViewY - (ACHIEVEMENT_ICON_HEIGHT - ACHIEVEMENT_CELL_HEIGHT) * zoom, ACHIEVEMENT_ICON_WIDTH * zoom, ACHIEVEMENT_ICON_HEIGHT * zoom, currentPage.getAchievementIcon(ach));
+            drawGuiIconDouble(achViewX - (ACHIEVEMENT_ICON_WIDTH - ACHIEVEMENT_CELL_WIDTH) * zoom, achViewY - (ACHIEVEMENT_ICON_HEIGHT - ACHIEVEMENT_CELL_HEIGHT) * zoom, ACHIEVEMENT_ICON_WIDTH * zoom, ACHIEVEMENT_ICON_HEIGHT * zoom, this.currentPage.getAchievementIcon(ach));
 
-            if(!statsCounter.canUnlock(ach)) {
+            if(!this.statsCounter.canUnlock(ach)) {
                 float brightness = 0.1F;
-                GL11.glColor4f(brightness, brightness, brightness, 1.0F);
+                GLRenderer.setColor4f(brightness, brightness, brightness, 1.0F);
             }
 
-            GL11.glPushMatrix();
-            GL11.glEnable(GL11.GL_LIGHTING);
-            GL11.glEnable(GL11.GL_CULL_FACE);
+            GLRenderer.pushFrame();
+            GLRenderer.globalSetLightEnabled(true);
+            GLRenderer.enableState(State.CULL_FACE);
             Item achievementItem = Item.itemsList[ach.iconItemId];
 
-            GL11.glTranslated(achViewX + 3 * zoom, achViewY + 3 * zoom, 0);
-            GL11.glScaled(zoom, zoom, 1);
-//            ItemModelDispatcher.getInstance().getDispatch(achievementItem).renderItemIntoGui(Tessellator.instance, mc.font, mc.textureManager, achievementItem.getDefaultStack(), 0, 0, 1.0f);
-            ItemModelDispatcher.getInstance().getDispatch(achievementItem).renderGui(Tessellator.instance, null, achievementItem.getDefaultStack(), 0, 0, 1f, 1.0f, 1f);
+            GLRenderer.modelM4f().translate((float) (achViewX + 3 * zoom), (float) (achViewY + 3 * zoom), 0);
+            GLRenderer.modelM4f().scale((float) zoom, (float) zoom, 1);
+//            ItemModelDispatcher.getInstance().getDispatch(achievementItem).renderItemIntoGui(GLRenderer.getTessellator(), mc.font, mc.textureManager, achievementItem.getDefaultStack(), 0, 0, 1.0f);
+            ItemModelDispatcher.getInstance().getDispatch(achievementItem).renderGui(GLRenderer.getTessellator(), null, achievementItem.getDefaultStack(), 0, 0, LightmapHelper.getLightmapCoord(15, 15), 1f);
 
-            GL11.glDisable(GL11.GL_LIGHTING);
-            GL11.glPopMatrix();
+            GLRenderer.globalSetLightEnabled(false);
+            GLRenderer.popFrame();
 
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
 
-            if((mouseX >= 0 && mouseY >= viewportTop && mouseX < width && mouseY < viewportBottom) && // In viewport and
+            if((mouseX >= 0 && mouseY >= this.viewportTop && mouseX < this.width && mouseY < this.viewportBottom) && // In viewport and
                 (mouseX >= achViewX && mouseX <= achViewX + 22 * zoom && mouseY >= achViewY && mouseY <= achViewY + 22 * zoom)) { // Hovering over achievement
                 hoveredAchievment = ach;
             }
@@ -845,28 +918,28 @@ public class ScreenAchievements extends Screen
     private void drawAchievementToolTip(Achievement achievement, int mouseX, int mouseY){
         String name = achievement.getStatName();
         String desc = achievement.getDescription();
-        final int padding = tooltip.getPadding();
+        final int padding = this.tooltip.getPadding();
         int[] boxRender;
-        if(statsCounter.canUnlock(achievement)) { // Can unlock/ is unlocked
+        if(this.statsCounter.canUnlock(achievement)) { // Can unlock/ is unlocked
             int boxWidth = Math.max(MathHelper.ceil(this.fontRenderer.stringWidthDouble(name)), TOOLTIP_BOX_WIDTH_MIN);
             int boxHeight = MathHelper.ceil(this.fontRenderer.heightOfConstrainedChars(desc, boxWidth));
-            if(statsCounter.isUnlocked(achievement)) {
+            if(this.statsCounter.isUnlocked(achievement)) {
                 boxHeight += 12;
             }
-            boxRender = tooltip.drawBackground(mouseX, mouseY, TOOLTIP_OFF_X, TOOLTIP_OFF_Y, boxWidth + 3, boxHeight + 3 + 12);
-            this.fontRenderer.renderWidthConstrained(Tessellator.instance, desc, boxRender[0] + padding, boxRender[1] + 12 + padding, boxWidth).setColor(0xffa0a0a0).call();
-            if(statsCounter.isUnlocked(achievement)) { // Add taken string to bottom
-                drawStringShadow(fontRenderer, I18n.getInstance().translateKey("gui.achievements.label.taken"), boxRender[0] + padding, boxRender[1] + boxHeight + 8 + padding, 0xff9090ff);
+            boxRender = this.tooltip.drawBackground(mouseX, mouseY, TOOLTIP_OFF_X, TOOLTIP_OFF_Y, boxWidth + 3, boxHeight + 3 + 12);
+            this.fontRenderer.renderWidthConstrained(desc, boxRender[0] + padding, boxRender[1] + 12 + padding, boxWidth).setColor(0xffa0a0a0).call();
+            if(this.statsCounter.isUnlocked(achievement)) { // Add taken string to bottom
+                drawStringShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.achievements.label.taken"), boxRender[0] + padding, boxRender[1] + boxHeight + 8 + padding, 0xff9090ff);
             }
         } else { // Not unlocked so darken
-            int boxWidth = Math.max(MathHelper.ceil(fontRenderer.stringWidthDouble(name)), TOOLTIP_BOX_WIDTH_MIN);
+            int boxWidth = Math.max(MathHelper.ceil(this.fontRenderer.stringWidthDouble(name)), TOOLTIP_BOX_WIDTH_MIN);
             String msg = I18n.getInstance().translateKeyAndFormat("gui.achievements.label.requires", achievement.parent.getStatName());
-            int boxHeight = MathHelper.ceil(fontRenderer.heightOfConstrainedChars(msg, boxWidth));
-            boxRender = tooltip.drawBackground(mouseX, mouseY, TOOLTIP_OFF_X, TOOLTIP_OFF_Y, boxWidth + 3, boxHeight + 3 + 12);
-            this.fontRenderer.renderWidthConstrained(Tessellator.instance, msg, boxRender[0] + padding, boxRender[1] + 12 + padding, boxWidth).setColor(0xff705050).call();
+            int boxHeight = MathHelper.ceil(this.fontRenderer.heightOfConstrainedChars(msg, boxWidth));
+            boxRender = this.tooltip.drawBackground(mouseX, mouseY, TOOLTIP_OFF_X, TOOLTIP_OFF_Y, boxWidth + 3, boxHeight + 3 + 12);
+            this.fontRenderer.renderWidthConstrained(msg, boxRender[0] + padding, boxRender[1] + 12 + padding, boxWidth).setColor(0xff705050).call();
         }
-        int color = statsCounter.canUnlock(achievement) ? achievement.getType().colorName : achievement.getType().colorNameLocked;
-        drawStringShadow(fontRenderer, name, boxRender[0] + padding, boxRender[1] + padding, color);
+        int color = this.statsCounter.canUnlock(achievement) ? achievement.getType().colorName : achievement.getType().colorNameLocked;
+        drawStringShadow(this.fontRenderer, name, boxRender[0] + padding, boxRender[1] + padding, color);
     }
     public boolean drawSidebar(){
         return AchievementPageRegistry.getInstance().getPages().size() > 1;
@@ -874,14 +947,14 @@ public class ScreenAchievements extends Screen
     private void scrollPagesList(float amount) {
         if(amount == 0.0f) return;
 
-        pageListScrollAmount += amount;
+        this.pageListScrollAmount += amount;
         onScrollPagesList();
     }
 
     private void onScrollPagesList() {
         int totalPagesListHeight = getTotalPagesListHeight();
-        if (pageListScrollAmount < 0 || pagesListScrollRegionHeight > totalPagesListHeight) pageListScrollAmount = 0;
-        else if (pageListScrollAmount > totalPagesListHeight - pagesListScrollRegionHeight) pageListScrollAmount = totalPagesListHeight - pagesListScrollRegionHeight;
+        if (this.pageListScrollAmount < 0 || this.pagesListScrollRegionHeight > totalPagesListHeight) this.pageListScrollAmount = 0;
+        else if (this.pageListScrollAmount > totalPagesListHeight - this.pagesListScrollRegionHeight) this.pageListScrollAmount = totalPagesListHeight - this.pagesListScrollRegionHeight;
     }
     private int getTotalPagesListHeight() {
         return PAGE_BUTTON_HEIGHT * AchievementPageRegistry.getInstance().getPages().size();
@@ -894,16 +967,16 @@ public class ScreenAchievements extends Screen
         for(AchievementPage page : AchievementPageRegistry.getInstance().getPages()) {
             String name = page.getName();
             int textColor = 0xFF7F7F7F;
-            if (page == currentPage) {
+            if (page == this.currentPage) {
                 textColor = 0xFFFFFFFF;
             }
             if (mouseX >= x && mouseX < x + width && mouseY >= y2 && mouseY < y2 + PAGE_BUTTON_HEIGHT) {
                 textColor = 0xFFFFFFA0;
                 pageHovered = page;
             }
-            renderItem.render(page.getIcon(), x, y2 + (PAGE_BUTTON_HEIGHT / 2) - 9);
-            if (page.getCompletionFraction(statsCounter) >= 1) {
-                GL11.glColor4f(1f, 1f, 1f, 1f);
+            this.renderItem.render(page.getIcon(), x, y2 + (PAGE_BUTTON_HEIGHT / 2) - 9);
+            if (page.getCompletionFraction(this.statsCounter) >= 1) {
+                GLRenderer.setColor4f(1f, 1f, 1f, 1f);
                 drawGuiIcon(x + 8, y2 + (PAGE_BUTTON_HEIGHT / 2) - 9 + 8, 11, 11, TextureRegistry.getTexture("minecraft:gui/screen/achievement/star"));
             }
             drawStringShadow(this.fontRenderer, name, x + 19, y2 + (PAGE_BUTTON_HEIGHT / 2) - 4, textColor);
@@ -914,60 +987,61 @@ public class ScreenAchievements extends Screen
     }
     protected void drawPagesListScrollBar(int mouseX, int mouseY) {
         float totalPagesListHeight = getTotalPagesListHeight();
-        float scrollBarHeightPercent = pagesListScrollRegionHeight / totalPagesListHeight;
+        float scrollBarHeightPercent = this.pagesListScrollRegionHeight / totalPagesListHeight;
 
         if(scrollBarHeightPercent > 1.0f) return;
 
-        glDisable(GL_TEXTURE_2D);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
 
-        int scrollBarX = pageListRight - 6;
+        int scrollBarX = this.pageListRight - 6;
 
-        int scrollBarHeightPx = (int) (scrollBarHeightPercent * pagesListScrollRegionHeight);
+        int scrollBarHeightPx = (int) (scrollBarHeightPercent * this.pagesListScrollRegionHeight);
         if(scrollBarHeightPx < 32) {
             scrollBarHeightPx = 32;
         }
 
-        float scrollPercent = pageListScrollAmount / (totalPagesListHeight - pagesListScrollRegionHeight);
+        float scrollPercent = this.pageListScrollAmount / (totalPagesListHeight - this.pagesListScrollRegionHeight);
 
-        int scrollBarY = (int) (top + (pagesListScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
+        int scrollBarY = (int) (this.top + (this.pagesListScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
 
-        Tessellator t = Tessellator.instance;
+        TessellatorGeneral t = GLRenderer.getTessellator();
 
         t.startDrawingQuads();
-        t.setColorOpaque(0, 0, 0);
-        t.drawRectangle(scrollBarX, top, 6, pagesListScrollRegionHeight);
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColorOpaque3i(0, 0, 0);
+        t.drawRectangle(scrollBarX, this.top, 6, this.pagesListScrollRegionHeight);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(scrollBarX, scrollBarY, 6, scrollBarHeightPx);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(scrollBarX + 1, scrollBarY, 5, scrollBarHeightPx - 1);
         t.draw();
 
-        glEnable(GL_TEXTURE_2D);
+        GLRenderer.popFrame();
 
-        if(clickX != null && clickY != null) {
-            if(clickX >= scrollBarX && clickY >= top && clickX <= scrollBarX + 6 && clickY < bottom) {
-                if(oldPagesListScrollAmount == null) {
-                    oldPagesListScrollAmount = pageListScrollAmount;
+        if(this.clickX != null && this.clickY != null) {
+            if(this.clickX >= scrollBarX && this.clickY >= this.top && this.clickX <= scrollBarX + 6 && this.clickY < this.bottom) {
+                if(this.oldPagesListScrollAmount == null) {
+                    this.oldPagesListScrollAmount = this.pageListScrollAmount;
                 }
-                pageListScrollAmount = oldPagesListScrollAmount + (clickY - mouseY) * (1.0f / scrollBarHeightPercent) * -1.0f;
+                this.pageListScrollAmount = this.oldPagesListScrollAmount + (this.clickY - mouseY) * (1.0f / scrollBarHeightPercent) * -1.0f;
                 onScrollPagesList();
             }
         }else {
-            oldPagesListScrollAmount = null;
+            this.oldPagesListScrollAmount = null;
         }
     }
 
     private void overlayBackground(int minX, int maxX, int minY, int maxY, int color)
     {
-        Tessellator tessellator = Tessellator.instance;
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         float scale = 32F;
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(color);
+        tessellator.setColorOpaque1i(color);
         tessellator.addVertexWithUV(minX, maxY, 0.0D, (float) minX / scale, (float) maxY / scale);
         tessellator.addVertexWithUV(maxX, maxY, 0.0D, (float) maxX / scale, (float) maxY / scale);
-        tessellator.setColorOpaque_I(color);
+        tessellator.setColorOpaque1i(color);
         tessellator.addVertexWithUV(maxX, minY, 0.0D, (float) maxX / scale, (float) minY / scale);
         tessellator.addVertexWithUV(minX, minY, 0.0D, (float) minX / scale, (float) minY / scale);
         tessellator.draw();
@@ -980,42 +1054,42 @@ public class ScreenAchievements extends Screen
         public final int id;
         public BGLayer(int id) {
             this.id = id;
-            data = new IconCoordinate[0];
-            width = 0;
-            height = 0;
+            this.data = new IconCoordinate[0];
+            this.width = 0;
+            this.height = 0;
         }
         public int getWidth() {
-            return width;
+            return this.width;
         }
         public int getHeight() {
-            return height;
+            return this.height;
         }
         public IconCoordinate[] getData() {
-            return data;
+            return this.data;
         }
         protected void resize(int width, int height) {
             this.width = width;
             this.height = height;
-            data = new IconCoordinate[width * height];
+            this.data = new IconCoordinate[width * height];
         }
         public void put(IconCoordinate coordinate, int x, int y){
             if (x < 0) return;
             if (y < 0) return;
-            if (x >= width) return;
-            if (y >= height) return;
-            data[makeIndex(x, y)] = coordinate;
+            if (x >= this.width) return;
+            if (y >= this.height) return;
+            this.data[makeIndex(x, y)] = coordinate;
         }
 
         public IconCoordinate get(int x, int y){
             if (x < 0) return null;
             if (y < 0) return null;
-            if (x >= width) return null;
-            if (y >= height) return null;
-            return data[makeIndex(x, y)];
+            if (x >= this.width) return null;
+            if (y >= this.height) return null;
+            return this.data[makeIndex(x, y)];
         }
 
         private int makeIndex(int x, int y){
-            return x % width + y * width;
+            return x % this.width + y * this.width;
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/chat/GuiElementChatSuggestions.java b/game/client/src/main/java/net/minecraft/client/gui/chat/GuiElementChatSuggestions.java
index 5c5b54947..ea3afe4bc 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/chat/GuiElementChatSuggestions.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/chat/GuiElementChatSuggestions.java
@@ -24,7 +24,6 @@ import net.minecraft.client.gui.text.ITextField;
 import net.minecraft.client.gui.text.TextFieldEditor;
 import net.minecraft.client.net.command.ClientCommandSource;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.net.command.*;
 import net.minecraft.core.net.command.util.CommandHelper;
 import net.minecraft.core.net.packet.PacketRequestCommandManager;
@@ -39,7 +38,6 @@ import java.util.ArrayList;
 import java.util.List;
 import java.util.Locale;
 import java.util.Map;
-import java.util.Optional;
 import java.util.OptionalInt;
 import java.util.concurrent.CompletableFuture;
 
@@ -95,7 +93,7 @@ public class GuiElementChatSuggestions extends Gui {
     }
 
     public CommandManager getManager() {
-        return this.mc.currentWorld == null ? new CommandManager(false) : mc.currentWorld.getCommandManager();
+        return this.mc.currentWorld == null ? new CommandManager(false) : this.mc.currentWorld.getCommandManager();
     }
 
     public void drawScreen() {
@@ -170,7 +168,7 @@ public class GuiElementChatSuggestions extends Gui {
 
             int textX = (int) (leftMargin + 1 + (this.anchor.xPosition * (largestSuggestion - fontRenderer.stringWidth(suggestionText))));
 
-            fontRenderer.render(Tessellator.instance, colorCode + suggestionText, textX, minY + suggestionBoxHeight - suggestionHeight + 3).setShadow().setColor(0xE0E0E0).call();
+            fontRenderer.render(colorCode + suggestionText, textX, minY + suggestionBoxHeight - suggestionHeight + 3).setShadow().setColor(0xE0E0E0).call();
         }
 
         if (this.isHoveringOverSuggestions(mouseX, mouseY) && this.suggestions.get(this.getIndexOfSuggestionBeingHoveredOver(mouseX, mouseY).getAsInt()).getTooltip() != null) {
@@ -189,7 +187,7 @@ public class GuiElementChatSuggestions extends Gui {
         minY += (int) CommandHelper.linearInterpolation(this.anchor.yPosition, heightIndex * 12, -12 - heightIndex * 12);
 
         this.drawRect(leftMargin, minY, stringWidth + leftMargin + 1, minY + 12, Integer.MIN_VALUE);
-        fontRenderer.render(Tessellator.instance, text, leftMargin + 1, minY + 2).setShadow().setColor(0xE0E0E0).call();
+        fontRenderer.render(text, leftMargin + 1, minY + 2).setShadow().setColor(0xE0E0E0).call();
     }
 
     private List<String> getCommandUsage(int cursor) {
@@ -378,7 +376,7 @@ public class GuiElementChatSuggestions extends Gui {
     }
 
     public void scroll(int amount) {
-        this.scroll = MathHelper.clamp(scroll + amount, 0, Math.max(this.suggestions.size() - MAX_SUGGESTIONS, 0));
+        this.scroll = MathHelper.clamp(this.scroll + amount, 0, Math.max(this.suggestions.size() - MAX_SUGGESTIONS, 0));
     }
 
     public void cycleThroughSuggestions() {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenActivator.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenActivator.java
index e6e332b24..5016a29bb 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenActivator.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenActivator.java
@@ -1,13 +1,13 @@
 package net.minecraft.client.gui.container;
 
 import net.minecraft.client.gui.ButtonElement;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.InventoryAction;
 import net.minecraft.core.block.entity.TileEntityActivator;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.container.ContainerInventory;
 import net.minecraft.core.player.inventory.menu.MenuActivator;
 import net.minecraft.core.sound.SoundCategory;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -24,27 +24,27 @@ public class ScreenActivator extends ScreenContainerAbstract {
     @Override
     public void init() {
         super.init();
-        int xLeft = (width - xSize) / 2;
-        int yTop = (height - ySize) / 2;
+        int xLeft = (this.width - this.xSize) / 2;
+        int yTop = (this.height - this.ySize) / 2;
         final int startX = xLeft + 7;
         final int startY = yTop + 34;
-        buttons.clear();
-        slotButtons.clear();
-        for (int i = 0; i < tileEntityActivator.getContainerSize(); i++) {
+        this.buttons.clear();
+        this.slotButtons.clear();
+        for (int i = 0; i < this.tileEntityActivator.getContainerSize(); i++) {
             ButtonElement button = new ButtonElement(i, startX + 18 * i, startY, 18, 18, "");
             button.visible = false;
-            slotButtons.add(button);
+            this.slotButtons.add(button);
         }
     }
 
     @Override
     public void clickInventory(int x, int y, int mouseButton) {
-        if (mouseButton == 1 && mc.thePlayer.inventory.getHeldItemStack() == null) {
-            for (ButtonElement button : slotButtons) {
-                if (tileEntityActivator.getItem(button.id) == null && button.mouseClicked(mc, x, y)) {
-                    mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.LOCK, new int[] {button.id, 0}, mc.thePlayer);
+        if (mouseButton == 1 && this.mc.thePlayer.inventory.getHeldItemStack() == null) {
+            for (ButtonElement button : this.slotButtons) {
+                if (this.tileEntityActivator.getItem(button.id) == null && button.mouseClicked(this.mc, x, y)) {
+                    this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.LOCK, new int[]{button.id, 0}, this.mc.thePlayer);
                     if (button.playSound) {
-                        mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
+                        this.mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
                     }
                     break;
                 }
@@ -56,21 +56,21 @@ public class ScreenActivator extends ScreenContainerAbstract {
     @Override
     protected void drawGuiContainerForegroundLayer() {
         drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.activator.label.activator"), 60, 6, 0x404040);
-        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.activator.label.inventory"), 8, (ySize - 96) + 2, 0x404040);
+        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.activator.label.inventory"), 8, (this.ySize - 96) + 2, 0x404040);
     }
 
     @Override
     protected void drawGuiContainerBackgroundLayer(float f) {
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/activator.png").bind();
-        int xLeft = (width - xSize) / 2;
-        int yTop = (height - ySize) / 2;
-        drawTexturedModalRect(xLeft, yTop, 0, 0, xSize, ySize);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/activator.png").bind();
+        int xLeft = (this.width - this.xSize) / 2;
+        int yTop = (this.height - this.ySize) / 2;
+        drawTexturedModalRect(xLeft, yTop, 0, 0, this.xSize, this.ySize);
 
-        if (!tileEntityActivator.locked(tileEntityActivator.stackSelector)) { // Draw selector arrow
+        if (!this.tileEntityActivator.locked(this.tileEntityActivator.stackSelector)) { // Draw selector arrow
             final int startX = xLeft + 7;
             final int startY = yTop + 26;
-            drawTexturedModalRect( startX + 18 * tileEntityActivator.stackSelector, startY, 176, 0, 18, 34);
+            drawTexturedModalRect(startX + 18 * this.tileEntityActivator.stackSelector, startY, 176, 0, 18, 34);
         }
     }
 }
\ No newline at end of file
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenContainer.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenContainer.java
index e925eb97d..1fccc142a 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenContainer.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenContainer.java
@@ -1,55 +1,53 @@
 package net.minecraft.client.gui.container;
 
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.menu.MenuContainer;
 import net.minecraft.core.player.inventory.container.Container;
 import org.lwjgl.opengl.GL11;
 
-public class ScreenContainer extends ScreenContainerAbstract
-{
+public class ScreenContainer extends ScreenContainerAbstract {
 
-    public ScreenContainer(Container containerUpper, Container containerLower)
-    {
+    public ScreenContainer(Container containerUpper, Container containerLower) {
         super(new MenuContainer(containerUpper, containerLower));
-        inventoryRows = 0;
-        upperChestInventory = containerUpper;
-        lowerChestInventory = containerLower;
-        passEvents = false;
+        this.inventoryRows = 0;
+        this.upperChestInventory = containerUpper;
+        this.lowerChestInventory = containerLower;
+        this.passEvents = false;
         int i = 97 /*Bottom section height of gui*/ + 17 /*Top Section height of gui*/ - 1 /*fixes very slight off by 1 issue*/;
-        inventoryRows = containerLower.getContainerSize() / 9;
-        ySize = i + inventoryRows * 18;
+        this.inventoryRows = containerLower.getContainerSize() / 9;
+        this.ySize = i + this.inventoryRows * 18;
     }
 
     @Override
-	protected void drawGuiContainerForegroundLayer()
-    {
-        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey(lowerChestInventory.getNameTranslationKey()), 8, 6, 0x404040);
-        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey(upperChestInventory.getNameTranslationKey()), 8, (ySize - 96) + 2, 0x404040);
+    protected void drawGuiContainerForegroundLayer() {
+        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey(this.lowerChestInventory.getNameTranslationKey()), 8, 6, 0x404040);
+        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey(this.upperChestInventory.getNameTranslationKey()), 8, (this.ySize - 96) + 2, 0x404040);
     }
 
     @Override
-	protected void drawGuiContainerBackgroundLayer(float f)
-    {
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/container.png").bind();
-        int x = (width - xSize) / 2;
-        int y = (height - ySize) / 2;
-        
-        int h1 = Math.min(inventoryRows, 6) * 18 + 17;
-        drawTexturedModalRect(x, y, 0, 0, xSize, h1);
-        
-        int rows = inventoryRows;
-        while(rows > 6) {
-        	int h2 = Math.min(rows, 6) * 18;
-        	drawTexturedModalRect(x, y + h1, 0, 17, xSize, h2);
-        	rows -= 6;
-        	h1 += h2;
+    protected void drawGuiContainerBackgroundLayer(float f) {
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/container.png").bind();
+        int x = (this.width - this.xSize) / 2;
+        int y = (this.height - this.ySize) / 2;
+
+        int h1 = Math.min(this.inventoryRows, 6) * 18 + 17;
+        drawTexturedModalRect(x, y, 0, 0, this.xSize, h1);
+
+        int rows = this.inventoryRows;
+        while (rows > 6) {
+            int h2 = Math.min(rows, 6) * 18;
+            drawTexturedModalRect(x, y + h1, 0, 17, this.xSize, h2);
+            rows -= 6;
+            h1 += h2;
         }
-        drawTexturedModalRect(x, y + inventoryRows * 18 + 17, 0, 126, xSize, 96);
+        drawTexturedModalRect(x, y + this.inventoryRows * 18 + 17, 0, 126, this.xSize, 96);
     }
 
-    private Container upperChestInventory;
-    private Container lowerChestInventory;
+    private final Container upperChestInventory;
+    private final Container lowerChestInventory;
     private int inventoryRows;
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenContainerAbstract.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenContainerAbstract.java
index d2caf6866..a238adc9a 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenContainerAbstract.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenContainerAbstract.java
@@ -8,13 +8,13 @@ import net.minecraft.client.gui.TooltipElement;
 import net.minecraft.client.gui.guidebook.GuidebookPageManager;
 import net.minecraft.client.gui.guidebook.ScreenGuidebook;
 import net.minecraft.client.gui.guidebook.GuidebookSections;
-import net.minecraft.client.gui.guidebook.SearchableGuidebookSection;
 import net.minecraft.client.gui.guidebook.search.GuidebookPageSearch;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.option.enums.DescriptionPromptEnum;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.util.helper.ItemDragHandler;
 import net.minecraft.core.InventoryAction;
-import net.minecraft.core.block.entity.TileEntityFurnaceBlast;
 import net.minecraft.core.crafting.LookupFuelFurnace;
 import net.minecraft.core.crafting.LookupFuelFurnaceBlast;
 import net.minecraft.core.data.registry.Registries;
@@ -32,590 +32,571 @@ import net.minecraft.core.player.inventory.slot.SlotResult;
 import net.minecraft.core.player.inventory.slot.SlotCreative;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
-
-public abstract class ScreenContainerAbstract extends Screen
-{
-	public int xSize;
-	public int ySize;
-	public MenuAbstract inventorySlots;
-	public TooltipElement tooltipElement;
-	public ItemElement itemElement;
-	public ItemDragHandler itemDragHandler;
-
-	public ScreenContainerAbstract(final MenuAbstract container)
-	{
-		Minecraft mc = Minecraft.getMinecraft();
-		xSize = 176;
-		ySize = 166;
-		inventorySlots = container;
-		tooltipElement = new TooltipElement(mc);
-		itemElement = new ItemElement(mc);
-		itemDragHandler = new ItemDragHandler(mc, this, itemElement);
-	}
-
-	@Override
-	public boolean isPauseScreen()
-	{
-		return false;
-	}
-
-	protected abstract void drawGuiContainerBackgroundLayer(float f);
-
-	protected void drawGuiContainerForegroundLayer()
-	{
-	}
-
-	@Override
-	public void render(final int mx, final int my, final float partialTick)
-	{
-		renderBackground();
-		final int centerX = (width - xSize) / 2;
-		final int centerY = (height - ySize) / 2;
-		drawGuiContainerBackgroundLayer(partialTick);
-		GL11.glPushMatrix();
-		GL11.glTranslatef(centerX, centerY, 0.0F);
-		drawGuiContainerForegroundLayer();
-		Slot slot = null;
-		for (int i = 0; i < inventorySlots.slots.size(); i++)
-		{
-			final Slot slot1 = inventorySlots.slots.get(i);
-			boolean mouseOver = getIsMouseOverSlot(slot1, mx, my);
-			if(!itemDragHandler.isSlotDragged(slot1)) {
-				itemElement.render(slot1.getItemStack(), slot1.x, slot1.y, mouseOver, slot1);
-			}
-			if (mouseOver)
-			{
-				slot = slot1;
-			}
-		}
-
-		final ContainerInventory inventoryplayer = mc.thePlayer.inventory;
-		ItemStack grabbedItem = inventoryplayer.getHeldItemStack();
-		if(mc.gameSettings.enableItemDragging.value) {
-			itemDragHandler.drawScreen(mx, my, partialTick);
-
-			ItemStack grabbedItemOverride = itemDragHandler.getHeldItemRenderOverride();
-			if(grabbedItemOverride != null) {
-				grabbedItem = grabbedItemOverride;
-			}
-		}
-		GL11.glPopMatrix();
-
-		super.render(mx, my, partialTick);
-
-		GL11.glPushMatrix();
-		if (grabbedItem != null)
-		{
-			GL11.glTranslatef(centerX, centerY, 100.0F);
-			itemElement.render(grabbedItem, mx - centerX - 8, my - centerY - 8);
-		}
-		GL11.glPopMatrix();
-
-		GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-		if (inventoryplayer.getHeldItemStack() == null && slot != null && slot.hasItem())
-		{
-			boolean showDescription = DescriptionPromptEnum.showDescription(mc);
-			String str = tooltipElement.getTooltipText(slot.getItemStack(), showDescription, slot);
-			if(str.length() > 0)
-			{
-				tooltipElement.render(str, mx, my, 8, -8);
-			}
-		}
-		GL11.glEnable(GL11.GL_DEPTH_TEST);
-	}
-
-	public boolean getIsMouseOverSlot(final Slot slot, int i, int j)
-	{
-		final int k = (width - xSize) / 2;
-		final int l = (height - ySize) / 2;
-		i -= k;
-		j -= l;
-		return i >= slot.x - 1 && i < slot.x + 16 + 1 && j >= slot.y - 1 && j < slot.y + 16 + 1;
-	}
-
-	public Slot getSlotAtPosition(final int i, final int j)
-	{
-		for (int k = 0; k < inventorySlots.slots.size(); k++)
-		{
-			final Slot slot = (Slot) inventorySlots.slots.get(k);
-			if (getIsMouseOverSlot(slot, i, j))
-			{
-				return slot;
-			}
-		}
-
-		return null;
-	}
-
-	@Override
-	public void init()
-	{
-		super.init();
-		mc.thePlayer.craftingInventory = inventorySlots;
-	}
-
-	@Override
-	public void keyPressed(final char eventCharacter, final int eventKey, int mx, int my)
-	{
-		if (eventKey == Keyboard.KEY_ESCAPE || eventKey == Keyboard.KEY_BACK)
-		{
-			mc.thePlayer.closeScreen();
-		}
-		int slotId = getSlotId(mx, my);
-		checkKeybind(slotId, eventKey, -1);
-	}
-
-	public boolean checkKeybind(int slotId, int key, int mouseButton) {
-		boolean cancelClick = false;
-		if (mc.gameSettings.keyInventory.isKeyOrMouse(key, mouseButton))
-		{
-			mc.thePlayer.closeScreen();
-			cancelClick = true;
-		}
-		if(slotId >= 0) {
-			if(mc.gameSettings.keyShowRecipe.isKeyOrMouse(key, mouseButton)){
-				Slot slot = inventorySlots.slots.get(slotId);
-				if(slot.hasItem()){
-					String query = "r:"+slot.getItemStack().getDisplayName()+"!";
+
+public abstract class ScreenContainerAbstract extends Screen {
+    public int xSize;
+    public int ySize;
+    public MenuAbstract inventorySlots;
+    public TooltipElement tooltipElement;
+    public ItemElement itemElement;
+    public ItemDragHandler itemDragHandler;
+
+    public ScreenContainerAbstract(final MenuAbstract container) {
+        Minecraft mc = Minecraft.getMinecraft();
+        this.xSize = 176;
+        this.ySize = 166;
+        this.inventorySlots = container;
+        this.tooltipElement = new TooltipElement(mc);
+        this.itemElement = new ItemElement(mc);
+        this.itemDragHandler = new ItemDragHandler(mc, this, this.itemElement);
+    }
+
+    @Override
+    public boolean isPauseScreen() {
+        return false;
+    }
+
+    protected abstract void drawGuiContainerBackgroundLayer(float f);
+
+    protected void drawGuiContainerForegroundLayer() {
+    }
+
+    @Override
+    public void render(final int mx, final int my, final float partialTick) {
+        renderBackground();
+        final int centerX = (this.width - this.xSize) / 2;
+        final int centerY = (this.height - this.ySize) / 2;
+        drawGuiContainerBackgroundLayer(partialTick);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate(centerX, centerY, 0.0F);
+        drawGuiContainerForegroundLayer();
+        Slot slot = null;
+        for (int i = 0; i < this.inventorySlots.slots.size(); i++) {
+            final Slot slot1 = this.inventorySlots.slots.get(i);
+            boolean mouseOver = getIsMouseOverSlot(slot1, mx, my);
+            if (!this.itemDragHandler.isSlotDragged(slot1)) {
+                this.itemElement.render(slot1.getItemStack(), slot1.x, slot1.y, mouseOver, slot1);
+            }
+            if (mouseOver) {
+                slot = slot1;
+            }
+        }
+
+        final ContainerInventory containerInventory = this.mc.thePlayer.inventory;
+        ItemStack grabbedItem = containerInventory.getHeldItemStack();
+        if (this.mc.gameSettings.enableItemDragging.value) {
+            this.itemDragHandler.drawScreen(mx, my, partialTick);
+
+            ItemStack grabbedItemOverride = this.itemDragHandler.getHeldItemRenderOverride();
+            if (grabbedItemOverride != null) {
+                grabbedItem = grabbedItemOverride;
+            }
+        }
+        GLRenderer.popFrame();
+
+        super.render(mx, my, partialTick);
+
+        GLRenderer.pushFrame();
+        if (grabbedItem != null) {
+            GLRenderer.modelM4f().translate(centerX, centerY, 100.0F);
+            this.itemElement.render(grabbedItem, mx - centerX - 8, my - centerY - 8);
+        }
+        GLRenderer.popFrame();
+
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        if (containerInventory.getHeldItemStack() == null && slot != null && slot.hasItem()) {
+            boolean showDescription = DescriptionPromptEnum.showDescription(this.mc);
+            String str = this.tooltipElement.getTooltipText(slot.getItemStack(), showDescription, slot);
+            if (!str.isEmpty()) {
+                this.tooltipElement.render(str, mx, my, 8, -8);
+            }
+        }
+        GLRenderer.enableState(State.DEPTH_TEST);
+    }
+
+    public boolean getIsMouseOverSlot(final Slot slot, int i, int j) {
+        final int k = (this.width - this.xSize) / 2;
+        final int l = (this.height - this.ySize) / 2;
+        i -= k;
+        j -= l;
+        return i >= slot.x - 1 && i < slot.x + 16 + 1 && j >= slot.y - 1 && j < slot.y + 16 + 1;
+    }
+
+    public Slot getSlotAtPosition(final int i, final int j) {
+        for (int k = 0; k < this.inventorySlots.slots.size(); k++) {
+            final Slot slot = this.inventorySlots.slots.get(k);
+            if (getIsMouseOverSlot(slot, i, j)) {
+                return slot;
+            }
+        }
+
+        return null;
+    }
+
+    @Override
+    public void init() {
+        super.init();
+        this.mc.thePlayer.craftingInventory = this.inventorySlots;
+    }
+
+    @Override
+    public void keyPressed(final char eventCharacter, final int eventKey, int mx, int my) {
+        if (eventKey == Keyboard.KEY_ESCAPE || eventKey == Keyboard.KEY_BACK) {
+            this.mc.thePlayer.closeScreen();
+        }
+        int slotId = getSlotId(mx, my);
+        checkKeybind(slotId, eventKey, -1);
+    }
+
+    public boolean checkKeybind(int slotId, int key, int mouseButton) {
+        boolean cancelClick = false;
+        if (this.mc.gameSettings.keyInventory.isKeyOrMouse(key, mouseButton)) {
+            this.mc.thePlayer.closeScreen();
+            cancelClick = true;
+        }
+        if (slotId >= 0) {
+            if (this.mc.gameSettings.keyShowRecipe.isKeyOrMouse(key, mouseButton)) {
+                Slot slot = this.inventorySlots.slots.get(slotId);
+                if (slot.hasItem()) {
+                    String query = "r:" + slot.getItemStack().getDisplayName() + "!";
 //					removed();
 //					mc.thePlayer.closeScreen();
-					GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
-					GuidebookPageSearch.searchField.setText(query);
-					ScreenGuidebook.getPageManager().updatePages();
-					if (!((SearchableGuidebookSection) GuidebookSections.CRAFTING).searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
-						ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.CRAFTING), true);
-					} else if (!((SearchableGuidebookSection) GuidebookSections.FURNACE).searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
-						ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.FURNACE), true);
-					} else if (!((SearchableGuidebookSection) GuidebookSections.BLAST_FURNACE).searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
-						ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.BLAST_FURNACE), true);
-					} else if (!((SearchableGuidebookSection) GuidebookSections.TROMMEL).searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
-						ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.TROMMEL), true);
-					}
-					mc.thePlayer.displayGuidebookScreen();
-				}
-				cancelClick = true;
-			}
-			if(mc.gameSettings.keyShowUsage.isKeyOrMouse(key, mouseButton)){
-				Slot slot = inventorySlots.slots.get(slotId);
-				if(slot.hasItem()) {
-					String query = "u:" + slot.getItemStack().getDisplayName() + "!";
+                    GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
+                    GuidebookPageSearch.searchField.setText(query);
+                    ScreenGuidebook.getPageManager().updatePages();
+                    if (!GuidebookSections.CRAFTING.searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
+                        ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.CRAFTING), true);
+                    } else if (!GuidebookSections.FURNACE.searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
+                        ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.FURNACE), true);
+                    } else if (!GuidebookSections.BLAST_FURNACE.searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
+                        ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.BLAST_FURNACE), true);
+                    } else if (!GuidebookSections.TROMMEL.searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
+                        ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.TROMMEL), true);
+                    }
+                    this.mc.thePlayer.displayGuidebookScreen();
+                }
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyShowUsage.isKeyOrMouse(key, mouseButton)) {
+                Slot slot = this.inventorySlots.slots.get(slotId);
+                if (slot.hasItem()) {
+                    String query = "u:" + slot.getItemStack().getDisplayName() + "!";
 //					removed();
 //					mc.thePlayer.closeScreen();
-					GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
-					GuidebookPageSearch.searchField.setText(query);
-					ScreenGuidebook.getPageManager().updatePages();
-					if (!((SearchableGuidebookSection) GuidebookSections.CRAFTING).searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
-						ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.CRAFTING), true);
-					} else if (!((SearchableGuidebookSection) GuidebookSections.FURNACE).searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
-						ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.FURNACE), true);
-					} else if (!((SearchableGuidebookSection) GuidebookSections.BLAST_FURNACE).searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
-						ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.BLAST_FURNACE), true);
-					} else if (!((SearchableGuidebookSection) GuidebookSections.TROMMEL).searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
-						ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.TROMMEL), true);
-					}
-					mc.thePlayer.displayGuidebookScreen();
-				}
-				cancelClick = true;
-			}
-			if(mc.gameSettings.keyDrop.isKeyOrMouse(key, mouseButton)) {
-				boolean ctrl = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
-				int amount = 1;
-				if(ctrl) amount = 64;
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.DROP, new int[] {slotId, amount}, mc.thePlayer);
-				cancelClick = true;
-			}
-			// Horrifying
-			if (mc.gameSettings.keyHotBarSlot1.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 1}, mc.thePlayer);
-				cancelClick = true;
-			}
-			if (mc.gameSettings.keyHotBarSlot2.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 2}, mc.thePlayer);
-				cancelClick = true;
-			}
-			if (mc.gameSettings.keyHotBarSlot3.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 3}, mc.thePlayer);
-				cancelClick = true;
-			}
-			if (mc.gameSettings.keyHotBarSlot4.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 4}, mc.thePlayer);
-				cancelClick = true;
-			}
-			if (mc.gameSettings.keyHotBarSlot5.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 5}, mc.thePlayer);
-				cancelClick = true;
-			}
-			if (mc.gameSettings.keyHotBarSlot6.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 6}, mc.thePlayer);
-				cancelClick = true;
-			}
-			if (mc.gameSettings.keyHotBarSlot7.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 7}, mc.thePlayer);
-				cancelClick = true;
-			}
-			if (mc.gameSettings.keyHotBarSlot8.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 8}, mc.thePlayer);
-				cancelClick = true;
-			}
-			if (mc.gameSettings.keyHotBarSlot9.isKeyOrMouse(key, mouseButton)){
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[] {slotId, 9}, mc.thePlayer);
-				cancelClick = true;
-			}
-
-			if(mc.gameSettings.keySortInventory.isKeyOrMouse(key, mouseButton)) {
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.SORT, new int[] {slotId}, mc.thePlayer);
-				cancelClick = true;
-			}
-		}
-		if (mc.currentScreen == this && mc.gameSettings.keyGuidebook.isKeyOrMouse(key, mouseButton)) {
-			mc.thePlayer.displayGuidebookScreen();
-			cancelClick = true;
-		}
-		return cancelClick;
-	}
-
-	@Override
-	public void mouseClicked(final int mx, final int my, int buttonNum)
-	{
-		if(!mc.thePlayer.getGamemode().consumeBlocks()) {
-			// Duplicate items with middle mouse button
-			if(buttonNum == 2) {
-				Slot slot = inventorySlots.getSlot(getSlotId(mx, my));
-				if (slot.getItemStack() == null) {
-					mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.SORT, new int[] {slot.index, 64}, mc.thePlayer);
-				} else {
-					mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[] {slot.index, 64}, mc.thePlayer);
-				}
-				return;
-			}
-		}
-		if (checkKeybind(getSlotId(mx, my), -1, buttonNum)) return;
-		super.mouseClicked(mx, my, buttonNum);
-		if(mc.gameSettings.enableItemDragging.value) {
-			itemDragHandler.mouseEvent(mx, my, buttonNum, true);
-			return;
-		}
-		if (buttonNum == 0 || buttonNum == 1 || buttonNum == 2 || buttonNum == 10) //button == 10 = controller shift click
-		{
-			clickInventory(mx, my, buttonNum);
-		}
-	}
-	
-	@Override
-	public void mouseReleased(int mx, int my, int buttonNum) {
-		if(buttonNum >= 0) {
-			if(mc.gameSettings.enableItemDragging.value) {
-				itemDragHandler.mouseEvent(mx, my, buttonNum, false);
-			}
-		}
-		super.mouseReleased(mx, my, buttonNum);
-	}
-	
-	/**
-	 * This method controls what InventoryAction is sent to the server 
-	 */
-	public void clickInventory(int x, int y, int mouseButton) {
-		int slotId = getSlotId(x, y);
-
-		if(slotId == -1)
-			return;
-
-		if(slotId == -999) {
-			// Drop held item
-			InventoryAction action = InventoryAction.DROP_HELD_STACK;
-			if(mouseButton == 1) action = InventoryAction.DROP_HELD_SINGLE;
-			mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, action, null, mc.thePlayer);
-			return;
-		}
-		
-		if(!mc.thePlayer.getGamemode().consumeBlocks()) {
-			// Duplicate items with middle mouse button
-			if(mouseButton == 2) {
-				Slot slot = inventorySlots.getSlot(slotId);
-				if (slot.getItemStack() == null) {
-					mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.SORT, new int[] {slotId, 64}, mc.thePlayer);
-				} else {
-					mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[] {slotId, 64}, mc.thePlayer);
-				}
-				return;
-			}
-		}
-		
-		InventoryAction action = InventoryAction.CLICK_LEFT;
-		
-		boolean shiftPressed = Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT);
-		boolean ctrlPressed = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
-		boolean altPressed = Keyboard.isKeyDown(Keyboard.KEY_LMENU) || Keyboard.isKeyDown(Keyboard.KEY_RMENU);
-		boolean spacePressed = Keyboard.isKeyDown(Keyboard.KEY_SPACE);
-		
-		if(mouseButton == 10) { // Controller Shift click
-			// TODO replace with a nicer solution
-			shiftPressed = true;
-			mouseButton = 0;
-		}
-
-		if(mc.gameSettings.keySortInventory.isMouseButton(mouseButton)) {
-			action = InventoryAction.SORT;
-		}
-		
-		// Used by MOVE actions to determine where to move the items to.
-		// 0: default,
-		// 1: crafting grid in workbench and inventory
-		// 2: creative inventory in creative inventory
-		int target = 0; 
-
-		Slot slot = inventorySlots.getSlot(slotId);
-		ItemStack stackInSlot = slot != null ? slot.getItemStack() : null;
-		Item itemInSlot = stackInSlot != null ? stackInSlot.getItem() : null;
-		int clickedItemId = stackInSlot != null ? stackInSlot.getItem().id : 0;
-		ItemStack grabbedItem = mc.thePlayer.inventory.getHeldItemStack();
-		
-		if(mouseButton == 1) action = InventoryAction.CLICK_RIGHT;
-		
-		if(slot instanceof SlotResult) {
-			// Crafting behavior
-			if(mc.gameSettings.swapCraftingButtons.value) {
-				if(shiftPressed && ctrlPressed) {
-					action = InventoryAction.MOVE_SIMILAR;
-				}else if(shiftPressed) {
-					action = InventoryAction.MOVE_SINGLE_ITEM;
-				}else if(ctrlPressed){
-					action = InventoryAction.MOVE_STACK;
-				}
-			}else {
-				if(shiftPressed && ctrlPressed) {
-					action = InventoryAction.MOVE_SIMILAR;
-				}else if(shiftPressed) {
-					action = InventoryAction.MOVE_STACK;
-				}else if(ctrlPressed){
-					action = InventoryAction.MOVE_SINGLE_ITEM;
-				}
-			}
-		}else {
-			// Regular Slot behavior
-			if(spacePressed) {
-				action = InventoryAction.MOVE_ALL;
-			}else {
-				if(shiftPressed && ctrlPressed) {
-					action = InventoryAction.MOVE_SIMILAR;
-				}else if(shiftPressed || altPressed) {
-					action = InventoryAction.MOVE_STACK;
-				}else if(ctrlPressed) {
-					action = InventoryAction.MOVE_SINGLE_ITEM;
-				}
-			}
-		}
-		
-		if(slot instanceof SlotCreative) {
-			// Creative slot behavior
-			ItemStack heldItem = mc.thePlayer.inventory.getHeldItemStack();
-			
-			if(heldItem != null) {
-				if(heldItem.canStackWith(stackInSlot)) {
-					if(shiftPressed || ctrlPressed) {
-						mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[] {slot.index, heldItem.getMaxStackSize()}, mc.thePlayer);
-					}else {
-						mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[] {slot.index, heldItem.stackSize + 1}, mc.thePlayer);
-					}
-				}else {
-					mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[] {slot.index, 0}, mc.thePlayer);
-				}
-			}else {
-				if(shiftPressed || ctrlPressed) {
-					int amount = 1;
-					if(shiftPressed && stackInSlot != null) amount = stackInSlot.getMaxStackSize();
-					mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.CREATIVE_MOVE, new int[] {slot.index, amount}, mc.thePlayer);
-				}else {
-					mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[] {slot.index, 1}, mc.thePlayer);
-				}
-			}
-			return;
-		}
-
-		if(inventorySlots instanceof MenuInventory) {
-			if(itemInSlot instanceof IArmorItem) {
-				// Check for instanceof ItemArmor instead of canPutStackInSlot
-				// Pumpkins should not go into the armor slot when pressing shift
-				target = 2; // Into the armor slots
-			}
-		}
-		if(inventorySlots instanceof MenuFurnace) {
-			boolean isFuel, isIngredient = false;
-
-			for (RecipeEntryFurnace recipe : Registries.RECIPES.getAllFurnaceRecipes()) {
-				isIngredient = recipe.matches(stackInSlot);
-				if(isIngredient){
-					break;
-				}
-			}
-			isFuel = LookupFuelFurnace.instance.getFuelYield(clickedItemId) > 0;
-
-			if(isIngredient) {
-				target = 1; // Into the ingredient slot
-			}else if(isFuel) {
-				target = 2; // Into the fuel slot
-			}
-		}
-		if(inventorySlots instanceof MenuFurnaceBlast) {
-			boolean isFuel, isIngredient = false;
-
-			for (RecipeEntryBlastFurnace recipe : Registries.RECIPES.getAllBlastFurnaceRecipes()) {
-				RecipeSymbol[] input = recipe.getInput();
-				isIngredient = input[0].matches(stackInSlot);
-				if (input.length == 2) {
-					isIngredient |= input[1].matches(stackInSlot);
-				}
-				if(isIngredient){
-					break;
-				}
-			}
-			isFuel = LookupFuelFurnaceBlast.instance.getFuelYield(clickedItemId) > 0;
-
-			if(isIngredient) {
-				target = 1; // Into the ingredient slot
-			}else if(isFuel) {
-				target = 2; // Into the fuel slot
-			}
-		}
-		if(inventorySlots instanceof MenuTrommel) {
-			if(LookupFuelFurnace.instance.getFuelYield(clickedItemId) > 0) {
-				target = 2; // Into the fuel slot
-			}else {
-				target = 1; // Into the item slots
-			}
-		}
-		if(inventorySlots instanceof MenuCrafting || inventorySlots instanceof MenuInventory) {
-			// Move items into crafting by holding alt
-			
-			if(altPressed) target = 1; // Into the crafting grid
-		}
-		if(inventorySlots instanceof MenuInventoryCreative) {
-			// Delete items by holding alt in the creative inventory
-			
-			if(altPressed) {
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.CREATIVE_DELETE, new int[] {slot.index}, mc.thePlayer);
-				return;
-			}
-		}
-		
-		// ContainerInventory Interactions (Grabbed Item)
-		if(slot != null && slot.allowItemInteraction() && grabbedItem != null && grabbedItem.getItem().hasInventoryInteraction()) {
-			if(mouseButton == 1) {
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.INTERACT_GRABBED, new int[] {slot.index}, mc.thePlayer);
-				return;
-			}
-		}
-		
-		// ContainerInventory Interactions (Clicked Item)
-		if(slot != null && stackInSlot != null && slot.allowItemInteraction() && stackInSlot.getItem().hasInventoryInteraction()) {
-			if(mouseButton == 1) {
-				mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, InventoryAction.INTERACT_SLOT, new int[] {slot.index}, mc.thePlayer);
-				return;
-			}
-		}
-		
-		int[] args = new int[] { slotId, target };
-		mc.playerController.handleInventoryMouseClick(inventorySlots.containerId, action, args, mc.thePlayer);
-	}
-	public void controllerInput(@NotNull ControllerInput controller){
-		Slot slot = controller.getSlotAtCursor(this);
+                    GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
+                    GuidebookPageSearch.searchField.setText(query);
+                    ScreenGuidebook.getPageManager().updatePages();
+                    if (!GuidebookSections.CRAFTING.searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
+                        ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.CRAFTING), true);
+                    } else if (!GuidebookSections.FURNACE.searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
+                        ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.FURNACE), true);
+                    } else if (!GuidebookSections.BLAST_FURNACE.searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
+                        ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.BLAST_FURNACE), true);
+                    } else if (!GuidebookSections.TROMMEL.searchPages(GuidebookPageManager.searchQuery).isEmpty()) {
+                        ScreenGuidebook.getPageManager().setCurrentPage(ScreenGuidebook.getPageManager().getSectionIndex(GuidebookSections.TROMMEL), true);
+                    }
+                    this.mc.thePlayer.displayGuidebookScreen();
+                }
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyDrop.isKeyOrMouse(key, mouseButton)) {
+                boolean ctrl = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
+                int amount = 1;
+                if (ctrl) amount = 64;
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.DROP, new int[]{slotId, amount}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            // Horrifying
+            if (this.mc.gameSettings.keyHotBarSlot1.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 1}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyHotBarSlot2.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 2}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyHotBarSlot3.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 3}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyHotBarSlot4.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 4}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyHotBarSlot5.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 5}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyHotBarSlot6.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 6}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyHotBarSlot7.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 7}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyHotBarSlot8.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 8}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+            if (this.mc.gameSettings.keyHotBarSlot9.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.HOTBAR_ITEM_SWAP, new int[]{slotId, 9}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+
+            if (this.mc.gameSettings.keySortInventory.isKeyOrMouse(key, mouseButton)) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.SORT, new int[]{slotId}, this.mc.thePlayer);
+                cancelClick = true;
+            }
+        }
+        if (this.mc.currentScreen == this && this.mc.gameSettings.keyGuidebook.isKeyOrMouse(key, mouseButton)) {
+            this.mc.thePlayer.displayGuidebookScreen();
+            cancelClick = true;
+        }
+        return cancelClick;
+    }
+
+    @Override
+    public void mouseClicked(final int mx, final int my, int buttonNum) {
+        if (!this.mc.thePlayer.getGamemode().consumeBlocks()) {
+            // Duplicate items with middle mouse button
+            if (buttonNum == 2) {
+                Slot slot = this.inventorySlots.getSlot(getSlotId(mx, my));
+                if (slot.getItemStack() == null) {
+                    this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.SORT, new int[]{slot.index, 64}, this.mc.thePlayer);
+                } else {
+                    this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[]{slot.index, 64}, this.mc.thePlayer);
+                }
+                return;
+            }
+        }
+        if (checkKeybind(getSlotId(mx, my), -1, buttonNum)) return;
+        super.mouseClicked(mx, my, buttonNum);
+        if (this.mc.gameSettings.enableItemDragging.value) {
+            this.itemDragHandler.mouseEvent(mx, my, buttonNum, true);
+            return;
+        }
+        if (buttonNum == 0 || buttonNum == 1 || buttonNum == 2 || buttonNum == 10) //button == 10 = controller shift click
+        {
+            clickInventory(mx, my, buttonNum);
+        }
+    }
+
+    @Override
+    public void mouseReleased(int mx, int my, int buttonNum) {
+        if (buttonNum >= 0) {
+            if (this.mc.gameSettings.enableItemDragging.value) {
+                this.itemDragHandler.mouseEvent(mx, my, buttonNum, false);
+            }
+        }
+        super.mouseReleased(mx, my, buttonNum);
+    }
+
+    /**
+     * This method controls what InventoryAction is sent to the server
+     */
+    public void clickInventory(int x, int y, int mouseButton) {
+        int slotId = getSlotId(x, y);
+
+        if (slotId == -1)
+            return;
+
+        if (slotId == -999) {
+            // Drop held item
+            InventoryAction action = InventoryAction.DROP_HELD_STACK;
+            if (mouseButton == 1) action = InventoryAction.DROP_HELD_SINGLE;
+            this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, action, null, this.mc.thePlayer);
+            return;
+        }
+
+        if (!this.mc.thePlayer.getGamemode().consumeBlocks()) {
+            // Duplicate items with middle mouse button
+            if (mouseButton == 2) {
+                Slot slot = this.inventorySlots.getSlot(slotId);
+                if (slot.getItemStack() == null) {
+                    this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.SORT, new int[]{slotId, 64}, this.mc.thePlayer);
+                } else {
+                    this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[]{slotId, 64}, this.mc.thePlayer);
+                }
+                return;
+            }
+        }
+
+        InventoryAction action = InventoryAction.CLICK_LEFT;
+
+        boolean shiftPressed = Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT);
+        boolean ctrlPressed = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
+        boolean altPressed = Keyboard.isKeyDown(Keyboard.KEY_LMENU) || Keyboard.isKeyDown(Keyboard.KEY_RMENU);
+        boolean spacePressed = Keyboard.isKeyDown(Keyboard.KEY_SPACE);
+
+        if (mouseButton == 10) { // Controller Shift click
+            // TODO replace with a nicer solution
+            shiftPressed = true;
+            mouseButton = 0;
+        }
+
+        if (this.mc.gameSettings.keySortInventory.isMouseButton(mouseButton)) {
+            action = InventoryAction.SORT;
+        }
+
+        // Used by MOVE actions to determine where to move the items to.
+        // 0: default,
+        // 1: crafting grid in workbench and inventory
+        // 2: creative inventory in creative inventory
+        int target = 0;
+
+        Slot slot = this.inventorySlots.getSlot(slotId);
+        ItemStack stackInSlot = slot != null ? slot.getItemStack() : null;
+        Item itemInSlot = stackInSlot != null ? stackInSlot.getItem() : null;
+        int clickedItemId = stackInSlot != null ? stackInSlot.getItem().id : 0;
+        ItemStack grabbedItem = this.mc.thePlayer.inventory.getHeldItemStack();
+
+        if (mouseButton == 1) action = InventoryAction.CLICK_RIGHT;
+
+        if (slot instanceof SlotResult) {
+            // Crafting behavior
+            if (this.mc.gameSettings.swapCraftingButtons.value) {
+                if (shiftPressed && ctrlPressed) {
+                    action = InventoryAction.MOVE_SIMILAR;
+                } else if (shiftPressed) {
+                    action = InventoryAction.MOVE_SINGLE_ITEM;
+                } else if (ctrlPressed) {
+                    action = InventoryAction.MOVE_STACK;
+                }
+            } else {
+                if (shiftPressed && ctrlPressed) {
+                    action = InventoryAction.MOVE_SIMILAR;
+                } else if (shiftPressed) {
+                    action = InventoryAction.MOVE_STACK;
+                } else if (ctrlPressed) {
+                    action = InventoryAction.MOVE_SINGLE_ITEM;
+                }
+            }
+        } else {
+            // Regular Slot behavior
+            if (spacePressed) {
+                action = InventoryAction.MOVE_ALL;
+            } else {
+                if (shiftPressed && ctrlPressed) {
+                    action = InventoryAction.MOVE_SIMILAR;
+                } else if (shiftPressed || altPressed) {
+                    action = InventoryAction.MOVE_STACK;
+                } else if (ctrlPressed) {
+                    action = InventoryAction.MOVE_SINGLE_ITEM;
+                }
+            }
+        }
+
+        if (slot instanceof SlotCreative) {
+            // Creative slot behavior
+            ItemStack heldItem = this.mc.thePlayer.inventory.getHeldItemStack();
+
+            if (heldItem != null) {
+                if (heldItem.canStackWith(stackInSlot)) {
+                    if (shiftPressed || ctrlPressed) {
+                        this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[]{slot.index, heldItem.getMaxStackSize()}, this.mc.thePlayer);
+                    } else {
+                        this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[]{slot.index, heldItem.stackSize + 1}, this.mc.thePlayer);
+                    }
+                } else {
+                    this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[]{slot.index, 0}, this.mc.thePlayer);
+                }
+            } else {
+                if (shiftPressed || ctrlPressed) {
+                    int amount = 1;
+                    if (shiftPressed && stackInSlot != null) amount = stackInSlot.getMaxStackSize();
+                    this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.CREATIVE_MOVE, new int[]{slot.index, amount}, this.mc.thePlayer);
+                } else {
+                    this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.CREATIVE_GRAB, new int[]{slot.index, 1}, this.mc.thePlayer);
+                }
+            }
+            return;
+        }
+
+        if (this.inventorySlots instanceof MenuInventory) {
+            if (itemInSlot instanceof IArmorItem) {
+                // Check for instanceof ItemArmor instead of canPutStackInSlot
+                // Pumpkins should not go into the armor slot when pressing shift
+                target = 2; // Into the armor slots
+            }
+        }
+        if (this.inventorySlots instanceof MenuFurnace) {
+            boolean isFuel, isIngredient = false;
+
+            for (RecipeEntryFurnace recipe : Registries.RECIPES.getAllFurnaceRecipes()) {
+                isIngredient = recipe.matches(stackInSlot);
+                if (isIngredient) {
+                    break;
+                }
+            }
+            isFuel = LookupFuelFurnace.instance.getFuelYield(clickedItemId) > 0;
+
+            if (isIngredient) {
+                target = 1; // Into the ingredient slot
+            } else if (isFuel) {
+                target = 2; // Into the fuel slot
+            }
+        }
+        if (this.inventorySlots instanceof MenuFurnaceBlast) {
+            boolean isFuel, isIngredient = false;
+
+            for (RecipeEntryBlastFurnace recipe : Registries.RECIPES.getAllBlastFurnaceRecipes()) {
+                RecipeSymbol[] input = recipe.getInput();
+                isIngredient = input[0].matches(stackInSlot);
+                if (input.length == 2) {
+                    isIngredient |= input[1].matches(stackInSlot);
+                }
+                if (isIngredient) {
+                    break;
+                }
+            }
+            isFuel = LookupFuelFurnaceBlast.instance.getFuelYield(clickedItemId) > 0;
+
+            if (isIngredient) {
+                target = 1; // Into the ingredient slot
+            } else if (isFuel) {
+                target = 2; // Into the fuel slot
+            }
+        }
+        if (this.inventorySlots instanceof MenuTrommel) {
+            if (LookupFuelFurnace.instance.getFuelYield(clickedItemId) > 0) {
+                target = 2; // Into the fuel slot
+            } else {
+                target = 1; // Into the item slots
+            }
+        }
+        if (this.inventorySlots instanceof MenuCrafting || this.inventorySlots instanceof MenuInventory) {
+            // Move items into crafting by holding alt
+
+            if (altPressed) target = 1; // Into the crafting grid
+        }
+        if (this.inventorySlots instanceof MenuInventoryCreative) {
+            // Delete items by holding alt in the creative inventory
+
+            if (altPressed) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.CREATIVE_DELETE, new int[]{slot.index}, this.mc.thePlayer);
+                return;
+            }
+        }
+
+        // ContainerInventory Interactions (Grabbed Item)
+        if (slot != null && slot.allowItemInteraction() && grabbedItem != null && grabbedItem.getItem().hasInventoryInteraction()) {
+            if (mouseButton == 1) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.INTERACT_GRABBED, new int[]{slot.index}, this.mc.thePlayer);
+                return;
+            }
+        }
+
+        // ContainerInventory Interactions (Clicked Item)
+        if (slot != null && stackInSlot != null && slot.allowItemInteraction() && stackInSlot.getItem().hasInventoryInteraction()) {
+            if (mouseButton == 1) {
+                this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, InventoryAction.INTERACT_SLOT, new int[]{slot.index}, this.mc.thePlayer);
+                return;
+            }
+        }
+
+        int[] args = new int[]{slotId, target};
+        this.mc.playerController.handleInventoryMouseClick(this.inventorySlots.containerId, action, args, this.mc.thePlayer);
+    }
+
+    public void controllerInput(@NotNull ControllerInput controller) {
+        Slot slot = controller.getSlotAtCursor(this);
 
 //		if(joyLeft.stoppedMoving()) {
 //			if(slot != null) {
 //				snapToSlot(guiContainer, slot);
 //			}
 //		}
-		if(slot != null) {
-			if(controller.digitalPad.right.pressedThisFrame()) {
-				Slot slot3 = null;
-				//Get Next Slot to the right
-				for(Slot slot2 : inventorySlots.slots) {
-					if(slot2.x > slot.x && Math.abs(slot2.y - slot.y) < 12) {
-						if(slot3 == null || slot2.x < slot3.x) {
-							slot3 = slot2;
-						}
-					}
-				}
-				if(slot3 == null) {
-					//Get First Slot on the left
-					for(Slot slot2 : inventorySlots.slots) {
-						if(Math.abs(slot2.y - slot.y) < 12) {
-							if(slot3 == null || slot2.x < slot3.x) {
-								slot3 = slot2;
-							}
-						}
-					}
-				}
-				controller.snapToSlot(this, slot3);
-			}
-			if(controller.digitalPad.left.pressedThisFrame()) {
-				Slot slot3 = null;
-				//Get Next Slot to the left
-				for(Slot slot2 : this.inventorySlots.slots) {
-					if(slot2.x < slot.x && Math.abs(slot2.y - slot.y) < 12) {
-						if(slot3 == null || slot2.x > slot3.x) {
-							slot3 = slot2;
-						}
-					}
-				}
-				if(slot3 == null) {
-					//Get First Slot on the right
-					for(Slot slot2 : this.inventorySlots.slots) {
-						if(Math.abs(slot2.y - slot.y) < 12) {
-							if(slot3 == null || slot2.x > slot3.x) {
-								slot3 = slot2;
-							}
-						}
-					}
-				}
-				controller.snapToSlot(this, slot3);
-			}
-			if(controller.digitalPad.up.pressedThisFrame()) {
-				Slot slot3 = null;
-				//Get Next Slot up
-				for(Slot slot2 : this.inventorySlots.slots) {
-					if(slot2.y < slot.y && Math.abs(slot2.x - slot.x) < 12) {
-						if(slot3 == null || slot2.y > slot3.y) {
-							slot3 = slot2;
-						}
-					}
-				}
-				if(slot3 == null) {
-					//Get First Slot on the bottom
-					for(Slot slot2 : this.inventorySlots.slots) {
-						if(Math.abs(slot2.x - slot.x) < 12) {
-							if(slot3 == null || slot2.y > slot3.y) {
-								slot3 = slot2;
-							}
-						}
-					}
-				}
-				controller.snapToSlot(this, slot3);
-			}
-			if(controller.digitalPad.down.pressedThisFrame()) {
-				Slot slot3 = null;
-				//Get Next Slot down
-				for(Slot slot2 : this.inventorySlots.slots) {
-					if(slot2.y > slot.y && Math.abs(slot2.x - slot.x) < 12) {
-						if(slot3 == null || slot2.y < slot3.y) {
-							slot3 = slot2;
-						}
-					}
-				}
-				if(slot3 == null) {
-					//Get First Slot on the top
-					for(Slot slot2 : this.inventorySlots.slots) {
-						if(Math.abs(slot2.x - slot.x) < 12) {
-							if(slot3 == null || slot2.y < slot3.y) {
-								slot3 = slot2;
-							}
-						}
-					}
-				}
-				controller.snapToSlot(this, slot3);
-			}
-		}
+        if (slot != null) {
+            if (controller.digitalPad.right.pressedThisFrame()) {
+                Slot slot3 = null;
+                //Get Next Slot to the right
+                for (Slot slot2 : this.inventorySlots.slots) {
+                    if (slot2.x > slot.x && Math.abs(slot2.y - slot.y) < 12) {
+                        if (slot3 == null || slot2.x < slot3.x) {
+                            slot3 = slot2;
+                        }
+                    }
+                }
+                if (slot3 == null) {
+                    //Get First Slot on the left
+                    for (Slot slot2 : this.inventorySlots.slots) {
+                        if (Math.abs(slot2.y - slot.y) < 12) {
+                            if (slot3 == null || slot2.x < slot3.x) {
+                                slot3 = slot2;
+                            }
+                        }
+                    }
+                }
+                controller.snapToSlot(this, slot3);
+            }
+            if (controller.digitalPad.left.pressedThisFrame()) {
+                Slot slot3 = null;
+                //Get Next Slot to the left
+                for (Slot slot2 : this.inventorySlots.slots) {
+                    if (slot2.x < slot.x && Math.abs(slot2.y - slot.y) < 12) {
+                        if (slot3 == null || slot2.x > slot3.x) {
+                            slot3 = slot2;
+                        }
+                    }
+                }
+                if (slot3 == null) {
+                    //Get First Slot on the right
+                    for (Slot slot2 : this.inventorySlots.slots) {
+                        if (Math.abs(slot2.y - slot.y) < 12) {
+                            if (slot3 == null || slot2.x > slot3.x) {
+                                slot3 = slot2;
+                            }
+                        }
+                    }
+                }
+                controller.snapToSlot(this, slot3);
+            }
+            if (controller.digitalPad.up.pressedThisFrame()) {
+                Slot slot3 = null;
+                //Get Next Slot up
+                for (Slot slot2 : this.inventorySlots.slots) {
+                    if (slot2.y < slot.y && Math.abs(slot2.x - slot.x) < 12) {
+                        if (slot3 == null || slot2.y > slot3.y) {
+                            slot3 = slot2;
+                        }
+                    }
+                }
+                if (slot3 == null) {
+                    //Get First Slot on the bottom
+                    for (Slot slot2 : this.inventorySlots.slots) {
+                        if (Math.abs(slot2.x - slot.x) < 12) {
+                            if (slot3 == null || slot2.y > slot3.y) {
+                                slot3 = slot2;
+                            }
+                        }
+                    }
+                }
+                controller.snapToSlot(this, slot3);
+            }
+            if (controller.digitalPad.down.pressedThisFrame()) {
+                Slot slot3 = null;
+                //Get Next Slot down
+                for (Slot slot2 : this.inventorySlots.slots) {
+                    if (slot2.y > slot.y && Math.abs(slot2.x - slot.x) < 12) {
+                        if (slot3 == null || slot2.y < slot3.y) {
+                            slot3 = slot2;
+                        }
+                    }
+                }
+                if (slot3 == null) {
+                    //Get First Slot on the top
+                    for (Slot slot2 : this.inventorySlots.slots) {
+                        if (Math.abs(slot2.x - slot.x) < 12) {
+                            if (slot3 == null || slot2.y < slot3.y) {
+                                slot3 = slot2;
+                            }
+                        }
+                    }
+                }
+                controller.snapToSlot(this, slot3);
+            }
+        }
 
 //		if(controller.buttonR.pressedThisFrame()) {
 //			slot = controller.getSlotAtCursor(this);
@@ -624,47 +605,38 @@ public abstract class ScreenContainerAbstract extends Screen
 //			}
 //		}
 
-		super.controllerInput(controller);
-	}
-
-	private int getSlotId(int x, int y) {
-		Slot slot = getSlotAtPosition(x, y);
-		int x2 = (width - xSize) / 2;
-		int y2 = (height - ySize) / 2;
-		boolean flag = x < x2 || y < y2 || x >= x2 + xSize || y >= y2 + ySize;
-		int slotId = -1;
-		if(slot != null) {
-			slotId = slot.index;
-		}
-		if(flag) {
-			slotId = -999;
-		}
-		return slotId;
-	}
-
-	@Override
-	public void removed()
-	{
-		if (mc.thePlayer == null)
-		{
-			return;
-		}
-		else
-		{
-			mc.playerController.handleCloseInventory(inventorySlots.containerId, mc.thePlayer);
-			return;
-		}
-	}
-
-
-	@Override
-	public void tick()
-	{
-		super.tick();
-		if (!mc.thePlayer.isAlive() || mc.thePlayer.removed)
-		{
-			mc.thePlayer.closeScreen();
-		}
-	}
+        super.controllerInput(controller);
+    }
+
+    private int getSlotId(int x, int y) {
+        Slot slot = getSlotAtPosition(x, y);
+        int x2 = (this.width - this.xSize) / 2;
+        int y2 = (this.height - this.ySize) / 2;
+        boolean flag = x < x2 || y < y2 || x >= x2 + this.xSize || y >= y2 + this.ySize;
+        int slotId = -1;
+        if (slot != null) {
+            slotId = slot.index;
+        }
+        if (flag) {
+            slotId = -999;
+        }
+        return slotId;
+    }
+
+    @Override
+    public void removed() {
+        if (this.mc.thePlayer != null) {
+            this.mc.playerController.handleCloseInventory(this.inventorySlots.containerId, this.mc.thePlayer);
+        }
+    }
+
+
+    @Override
+    public void tick() {
+        super.tick();
+        if (!this.mc.thePlayer.isAlive() || this.mc.thePlayer.removed) {
+            this.mc.thePlayer.closeScreen();
+        }
+    }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenCrafting.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenCrafting.java
index eb8c025c0..cb80e9f4e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenCrafting.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenCrafting.java
@@ -1,47 +1,42 @@
 package net.minecraft.client.gui.container;
 
 import net.minecraft.client.input.controller.ControllerInput;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.container.ContainerInventory;
 import net.minecraft.core.player.inventory.menu.MenuCrafting;
 import net.minecraft.core.world.World;
-import net.minecraft.core.world.pos.TilePos;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
-public class ScreenCrafting extends ScreenContainerAbstract
-{
-    public ScreenCrafting(@NotNull ContainerInventory inventory, @NotNull World world, @NotNull TilePosc tilePos)
-    {
+public class ScreenCrafting extends ScreenContainerAbstract {
+    public ScreenCrafting(@NotNull ContainerInventory inventory, @NotNull World world, @NotNull TilePosc tilePos) {
         super(new MenuCrafting(inventory, world, tilePos));
     }
 
     @Override
-	public void removed()
-    {
+    public void removed() {
         super.removed();
-        inventorySlots.onCraftGuiClosed(mc.thePlayer);
+        this.inventorySlots.onCraftGuiClosed(this.mc.thePlayer);
     }
 
     @Override
-	protected void drawGuiContainerForegroundLayer()
-    {
+    protected void drawGuiContainerForegroundLayer() {
         drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.crafting.label.crafting"), 28, 6, 0x404040);
-        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.crafting.label.inventory"), 8, (ySize - 96) + 2, 0x404040);
+        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.crafting.label.inventory"), 8, (this.ySize - 96) + 2, 0x404040);
     }
 
     @Override
-	protected void drawGuiContainerBackgroundLayer(float f)
-    {
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/crafting.png").bind();
-        int j = (width - xSize) / 2;
-        int k = (height - ySize) / 2;
-        drawTexturedModalRect(j, k, 0, 0, xSize, ySize);
+    protected void drawGuiContainerBackgroundLayer(float f) {
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/crafting.png").bind();
+        int left = (this.width - this.xSize) / 2;
+        int top = (this.height - this.ySize) / 2;
+        drawTexturedModalRect(left, top, 0, 0, this.xSize, this.ySize);
     }
+
     @Override
-    public void guiSpecificControllerInput(@NotNull ControllerInput controller){
+    public void guiSpecificControllerInput(@NotNull ControllerInput controller) {
         super.guiSpecificControllerInput(controller);
         controller.inventoryHandler.handleCrafting(this);
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenDispenser.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenDispenser.java
index 1e4b74938..32d814db7 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenDispenser.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenDispenser.java
@@ -1,33 +1,29 @@
 package net.minecraft.client.gui.container;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.block.entity.TileEntityDispenser;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.menu.MenuTrap;
 import net.minecraft.core.player.inventory.container.ContainerInventory;
-import org.lwjgl.opengl.GL11;
 
-public class ScreenDispenser extends ScreenContainerAbstract
-{
+public class ScreenDispenser extends ScreenContainerAbstract {
 
-    public ScreenDispenser(ContainerInventory inventoryplayer, TileEntityDispenser tileentitydispenser)
-    {
+    public ScreenDispenser(ContainerInventory inventoryplayer, TileEntityDispenser tileentitydispenser) {
         super(new MenuTrap(inventoryplayer, tileentitydispenser));
     }
 
     @Override
-	protected void drawGuiContainerForegroundLayer()
-    {
+    protected void drawGuiContainerForegroundLayer() {
         drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.dispenser.label.dispenser"), 60, 6, 0x404040);
-        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.dispenser.label.inventory"), 8, (ySize - 96) + 2, 0x404040);
+        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.dispenser.label.inventory"), 8, (this.ySize - 96) + 2, 0x404040);
     }
 
     @Override
-	protected void drawGuiContainerBackgroundLayer(float f)
-    {
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/dispenser.png").bind();
-        int j = (width - xSize) / 2;
-        int k = (height - ySize) / 2;
-        drawTexturedModalRect(j, k, 0, 0, xSize, ySize);
+    protected void drawGuiContainerBackgroundLayer(float f) {
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/dispenser.png").bind();
+        int left = (this.width - this.xSize) / 2;
+        int top = (this.height - this.ySize) / 2;
+        drawTexturedModalRect(left, top, 0, 0, this.xSize, this.ySize);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFlagEditor.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFlagEditor.java
index 8ad9ec4ba..f60947684 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFlagEditor.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFlagEditor.java
@@ -1,10 +1,11 @@
 package net.minecraft.client.gui.container;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ButtonElement;
 import net.minecraft.client.gui.ClickableLabelElement;
 import net.minecraft.client.gui.DrawableSurfaceElement;
 import net.minecraft.client.gui.TexturedButtonElement;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.block.entity.TileEntityFlag;
 import net.minecraft.core.entity.player.Player;
 import org.jetbrains.annotations.NotNull;
@@ -24,12 +25,10 @@ import net.minecraft.core.util.helper.MathHelper;
 
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
-import java.util.Arrays;
 
 public class ScreenFlagEditor
     extends ScreenContainerAbstract
-    implements IDrawableSurface<Byte>
-{
+    implements IDrawableSurface<Byte> {
     private final TileEntityFlag flagEntity;
     private final int CANVAS_SCALE = 4;
     private final int CANVAS_WIDTH = TileEntityFlag.CANVAS_WIDTH;
@@ -55,152 +54,134 @@ public class ScreenFlagEditor
 
     DrawableSurfaceElement flagSurface;
     DrawableSurfaceElement drawOverlaySurface;
-    
-    public ScreenFlagEditor(Player player, TileEntityFlag flagTileEntity)
-    {
+
+    public ScreenFlagEditor(Player player, TileEntityFlag flagTileEntity) {
         super(new MenuFlag(player.inventory, flagTileEntity));
         this.flagEntity = flagTileEntity;
-        xSize = 176;
-        ySize = 195;
+        this.xSize = 176;
+        this.ySize = 195;
         flagTileEntity.owner = player.uuid;
 
-        flagSurface = new DrawableSurfaceElement(CANVAS_WIDTH, CANVAS_HEIGHT, CANVAS_SCALE, flagTileEntity.flagColors);
-        flagSurfaceEditor = new DrawableEditor<>(flagSurface);
-        drawOverlaySurface = new DrawableSurfaceElement(CANVAS_WIDTH, CANVAS_HEIGHT, CANVAS_SCALE);
-        drawOverlaySurfaceEditor = new DrawableEditor<>(drawOverlaySurface);
+        this.flagSurface = new DrawableSurfaceElement(this.CANVAS_WIDTH, this.CANVAS_HEIGHT, this.CANVAS_SCALE, flagTileEntity.flagColors);
+        this.flagSurfaceEditor = new DrawableEditor<>(this.flagSurface);
+        this.drawOverlaySurface = new DrawableSurfaceElement(this.CANVAS_WIDTH, this.CANVAS_HEIGHT, this.CANVAS_SCALE);
+        this.drawOverlaySurfaceEditor = new DrawableEditor<>(this.drawOverlaySurface);
     }
 
     @Override
-    public void init()
-    {
+    public void init() {
         super.init();
-        buttons.clear();
+        this.buttons.clear();
 
-        canvasX = (width - xSize) / 2 + 27;
-        canvasY = (height - ySize) / 2 + 8;
+        this.canvasX = (this.width - this.xSize) / 2 + 27;
+        this.canvasY = (this.height - this.ySize) / 2 + 8;
 
-        toolBtns = new TexturedButtonElement[7];
+        this.toolBtns = new TexturedButtonElement[7];
 
-        for (int i = 0; i < 7; i++)
-        {
-            toolBtns[i] = new TexturedButtonElement(i, "/assets/minecraft/textures/gui/container/flag_editor.png", (width - xSize) / 2 + 12 + 22 * i, (height - ySize) / 2 + 76, 20 * i, 195, 20, 20);
-            if (i == activeTool) toolBtns[i].enabled = false;
-            buttons.add(toolBtns[i]);
+        for (int i = 0; i < 7; i++) {
+            this.toolBtns[i] = new TexturedButtonElement(i, "/assets/minecraft/textures/gui/container/flag_editor.png", (this.width - this.xSize) / 2 + 12 + 22 * i, (this.height - this.ySize) / 2 + 76, 20 * i, 195, 20, 20);
+            if (i == this.activeTool) this.toolBtns[i].enabled = false;
+            this.buttons.add(this.toolBtns[i]);
         }
 
-        colorLabels = new ClickableLabelElement[3];
+        this.colorLabels = new ClickableLabelElement[3];
 
-        for (int i = 0; i < 3; i++)
-        {
-            colorLabels[i] = new ClickableLabelElement(100 + i, (width - xSize) / 2 + 150, (height - ySize) / 2 + 12 + (i * 22), String.valueOf(i + 1), 0xFFFFFFFF, 0x00000000);
-            if (i != selectedColor) {
-                colorLabels[i].setTextColor(0xFF3F3F3F);
-                colorLabels[i].setShadow(false);
+        for (int i = 0; i < 3; i++) {
+            this.colorLabels[i] = new ClickableLabelElement(100 + i, (this.width - this.xSize) / 2 + 150, (this.height - this.ySize) / 2 + 12 + (i * 22), String.valueOf(i + 1), 0xFFFFFFFF, 0x00000000);
+            if (i != this.selectedColor) {
+                this.colorLabels[i].setTextColor(0xFF3F3F3F);
+                this.colorLabels[i].setShadow(false);
             }
-            buttons.add(colorLabels[i]);
+            this.buttons.add(this.colorLabels[i]);
         }
 
-        buttons.add(
+        this.buttons.add(
             new ButtonElement(50, (this.width - this.xSize) / 2 + 12, (this.height - this.ySize) / 2 + 61, 12, 12, "")
                 .setTextures("minecraft:gui/misc/button_flag_flip", "minecraft:gui/misc/button_flag_flip_highlighted", "minecraft:gui/misc/button_flag_flip_disabled.png")
         );
     }
 
-    private void renderCanvas()
-    {
-        canvasX = (width - xSize) / 2 + 27;
-        canvasY = (height - ySize) / 2 + 8;
+    private void renderCanvas() {
+        this.canvasX = (this.width - this.xSize) / 2 + 27;
+        this.canvasY = (this.height - this.ySize) / 2 + 8;
 
         int[] colors = new int[5];
-        for (int i = 1; i < 4; i++)
-        {
-            ItemStack stack = flagEntity.getItem(35 + i);
-            if (stack != null && stack.getItem() == Items.DYE)
-            {
+        for (int i = 1; i < 4; i++) {
+            ItemStack stack = this.flagEntity.getItem(35 + i);
+            if (stack != null && stack.getItem() == Items.DYE) {
                 colors[i] = Colors.allFlagColors[TextFormatting.get(15 - stack.getMetadata()).id].getARGB();
             }
         }
         colors[4] = 0xFFFFFFFF;
-        flagSurface.colors = colors;
-        drawOverlaySurface.colors = colors;
-        
-        GL11.glEnable(GL11.GL_BLEND);
+        this.flagSurface.colors = colors;
+        this.drawOverlaySurface.colors = colors;
+
+        GLRenderer.enableState(State.BLEND);
         GL11.glBlendFunc(GL11.GL_ONE_MINUS_SRC_COLOR, GL11.GL_SRC_COLOR);
-        flagSurface.render(canvasX, canvasY);
-        GL11.glDisable(GL11.GL_BLEND);
-        drawOverlaySurface.render(canvasX, canvasY);
+        this.flagSurface.render(this.canvasX, this.canvasY);
+        GLRenderer.disableState(State.BLEND);
+        this.drawOverlaySurface.render(this.canvasX, this.canvasY);
     }
 
     @Override
-    public void mouseClicked(int mx, int my, int buttonNum)
-    {
+    public void mouseClicked(int mx, int my, int buttonNum) {
         super.mouseClicked(mx, my, buttonNum);
-        
+
         // Do not draw with no color selected
-        if(flagEntity.getItem(36 + selectedColor) == null) {
-        	return;
+        if (this.flagEntity.getItem(36 + this.selectedColor) == null) {
+            return;
         }
-        
-        if (activeTool >= 0 && activeTool < 3) // Pen
+
+        if (this.activeTool >= 0 && this.activeTool < 3) // Pen
         {
-            if (!isDrawing)
-            {
-                int xInCanvas = (mx - canvasX) / CANVAS_SCALE;
-                int yInCanvas = (my - canvasY) / CANVAS_SCALE;
-                if (xInCanvas >= 0 && xInCanvas < CANVAS_WIDTH
-                        && yInCanvas >= 0 && yInCanvas < CANVAS_HEIGHT)
-                {
-                    isDrawing = true;
-                    xLast = xInCanvas;
-                    yLast = yInCanvas;
+            if (!this.isDrawing) {
+                int xInCanvas = (mx - this.canvasX) / this.CANVAS_SCALE;
+                int yInCanvas = (my - this.canvasY) / this.CANVAS_SCALE;
+                if (xInCanvas >= 0 && xInCanvas < this.CANVAS_WIDTH
+                    && yInCanvas >= 0 && yInCanvas < this.CANVAS_HEIGHT) {
+                    this.isDrawing = true;
+                    this.xLast = xInCanvas;
+                    this.yLast = yInCanvas;
                     this.mouseButton = buttonNum;
 
                     byte color = 0;
-                    if (this.mouseButton == 0)
-                    {
-                        color = (byte) (selectedColor + 1);
+                    if (this.mouseButton == 0) {
+                        color = (byte) (this.selectedColor + 1);
                     }
-                    flagSurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, activeTool + 1);
-                    flagEntity.isDirty = true;
+                    this.flagSurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, this.activeTool + 1);
+                    this.flagEntity.isDirty = true;
                 }
             }
-        }
-        else if (activeTool == 3) // Flood fill
+        } else if (this.activeTool == 3) // Flood fill
         {
-            if (!isDrawing)
-            {
-                int xInCanvas = (mx - canvasX) / CANVAS_SCALE;
-                int yInCanvas = (my - canvasY) / CANVAS_SCALE;
-                if (xInCanvas >= 0 && xInCanvas < CANVAS_WIDTH
-                        && yInCanvas >= 0 && yInCanvas < CANVAS_HEIGHT)
-                {
-                    isDrawing = true;
+            if (!this.isDrawing) {
+                int xInCanvas = (mx - this.canvasX) / this.CANVAS_SCALE;
+                int yInCanvas = (my - this.canvasY) / this.CANVAS_SCALE;
+                if (xInCanvas >= 0 && xInCanvas < this.CANVAS_WIDTH
+                    && yInCanvas >= 0 && yInCanvas < this.CANVAS_HEIGHT) {
+                    this.isDrawing = true;
                     this.mouseButton = buttonNum;
 
                     byte color = 0;
-                    if (this.mouseButton == 0)
-                    {
-                        color = (byte) (selectedColor + 1);
+                    if (this.mouseButton == 0) {
+                        color = (byte) (this.selectedColor + 1);
                     }
-                    flagSurfaceEditor.floodFill(xInCanvas, yInCanvas, color);
-                    flagEntity.isDirty = true;
+                    this.flagSurfaceEditor.floodFill(xInCanvas, yInCanvas, color);
+                    this.flagEntity.isDirty = true;
                 }
             }
-        }
-        else if (activeTool == 4 || activeTool == 5 || activeTool == 6) // Rectangle or Ellipse or Line
+        } else if (this.activeTool == 4 || this.activeTool == 5 || this.activeTool == 6) // Rectangle or Ellipse or Line
         {
-            if (!isDrawing)
-            {
-                int xInCanvas = (mx - canvasX) / CANVAS_SCALE;
-                int yInCanvas = (my - canvasY) / CANVAS_SCALE;
-                if (xInCanvas >= 0 && xInCanvas < CANVAS_WIDTH
-                        && yInCanvas >= 0 && yInCanvas < CANVAS_HEIGHT)
-                {
-                    isDrawing = true;
+            if (!this.isDrawing) {
+                int xInCanvas = (mx - this.canvasX) / this.CANVAS_SCALE;
+                int yInCanvas = (my - this.canvasY) / this.CANVAS_SCALE;
+                if (xInCanvas >= 0 && xInCanvas < this.CANVAS_WIDTH
+                    && yInCanvas >= 0 && yInCanvas < this.CANVAS_HEIGHT) {
+                    this.isDrawing = true;
                     this.mouseButton = buttonNum;
 
-                    xLast = xInCanvas;
-                    yLast = yInCanvas;
+                    this.xLast = xInCanvas;
+                    this.yLast = yInCanvas;
                 }
             }
         }
@@ -208,8 +189,8 @@ public class ScreenFlagEditor
 
     @Override
     public void tick() {
-        tickCount++;
-        if(mc.currentWorld.isClientSide && (tickCount % 40 == 0)) {
+        this.tickCount++;
+        if (this.mc.currentWorld.isClientSide && (this.tickCount % 40 == 0)) {
             sendUpdatePacket();
         }
     }
@@ -217,210 +198,173 @@ public class ScreenFlagEditor
     @Override
     public void removed() {
         super.removed();
-        if(this.mc.currentWorld != null && mc.currentWorld.isClientSide) {
+        if (this.mc.currentWorld != null && this.mc.currentWorld.isClientSide) {
             sendUpdatePacket();
         }
     }
 
     @Override
-    protected void buttonClicked(@NotNull ButtonElement button)
-    {
+    protected void buttonClicked(@NotNull ButtonElement button) {
         super.buttonClicked(button);
-        if (button.id >= 0 && button.id < 7)
-        {
-            toolBtns[activeTool].enabled = true;
-            activeTool = button.id;
+        if (button.id >= 0 && button.id < 7) {
+            this.toolBtns[this.activeTool].enabled = true;
+            this.activeTool = button.id;
             button.enabled = false;
         }
         if (button.id == 50) {
-            flagEntity.setFlipped(!flagEntity.getFlipped());
-            if(mc.currentWorld.isClientSide) {
+            this.flagEntity.setFlipped(!this.flagEntity.getFlipped());
+            if (this.mc.currentWorld.isClientSide) {
                 sendUpdatePacket();
             }
         }
-        if (button.id >= 100 && button.id < 103)
-        {
-            colorLabels[selectedColor].setTextColor(0xFF404040);
-            colorLabels[selectedColor].setShadow(false);
-            selectedColor = button.id - 100;
-            colorLabels[selectedColor].setTextColor(0xFFFFFFF);
-            colorLabels[selectedColor].setShadow(true);
+        if (button.id >= 100 && button.id < 103) {
+            this.colorLabels[this.selectedColor].setTextColor(0xFF404040);
+            this.colorLabels[this.selectedColor].setShadow(false);
+            this.selectedColor = button.id - 100;
+            this.colorLabels[this.selectedColor].setTextColor(0xFFFFFFF);
+            this.colorLabels[this.selectedColor].setShadow(true);
         }
     }
 
     @Override
-    public void mouseReleased(final int mx, final int my, final int buttonNum)
-    {
+    public void mouseReleased(final int mx, final int my, final int buttonNum) {
         super.mouseReleased(mx, my, buttonNum);
 
-        if (activeTool >= 0 && activeTool < 3) // Pen
+        if (this.activeTool >= 0 && this.activeTool < 3) // Pen
         {
-            if (isDrawing && buttonNum != -1)
-            {
-                isDrawing = false;
+            if (this.isDrawing && buttonNum != -1) {
+                this.isDrawing = false;
                 this.mouseButton = -1;
-            }
-            else if (isDrawing)
-            {
+            } else if (this.isDrawing) {
                 // divide by pixel scale
-                int xInCanvas = (mx - canvasX) / CANVAS_SCALE;
-                int yInCanvas = (my - canvasY) / CANVAS_SCALE;
+                int xInCanvas = (mx - this.canvasX) / this.CANVAS_SCALE;
+                int yInCanvas = (my - this.canvasY) / this.CANVAS_SCALE;
 
                 byte color = 0;
-                if (this.mouseButton == 0)
-                {
-                    color = (byte) (selectedColor + 1);
+                if (this.mouseButton == 0) {
+                    color = (byte) (this.selectedColor + 1);
                 }
 
-                if(MathHelper.abs(xLast - xInCanvas) <= 1 && MathHelper.abs(yLast - yInCanvas) <= 1)
-                {
-                    flagSurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, activeTool + 1);
-                    flagEntity.isDirty = true;
-                }
-                else
-                {
-                    flagSurfaceEditor.drawLine(xLast, yLast, xInCanvas, yInCanvas, color, activeTool + 1);
-                    flagEntity.isDirty = true;
+                if (MathHelper.abs(this.xLast - xInCanvas) <= 1 && MathHelper.abs(this.yLast - yInCanvas) <= 1) {
+                    this.flagSurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, this.activeTool + 1);
+                    this.flagEntity.isDirty = true;
+                } else {
+                    this.flagSurfaceEditor.drawLine(this.xLast, this.yLast, xInCanvas, yInCanvas, color, this.activeTool + 1);
+                    this.flagEntity.isDirty = true;
                 }
 
-                xLast = xInCanvas;
-                yLast = yInCanvas;
+                this.xLast = xInCanvas;
+                this.yLast = yInCanvas;
             }
-        }
-        else if (activeTool == 3) // Flood fill
+        } else if (this.activeTool == 3) // Flood fill
         {
-            if (isDrawing && buttonNum != -1)
-            {
-                isDrawing = false;
+            if (this.isDrawing && buttonNum != -1) {
+                this.isDrawing = false;
                 this.mouseButton = -1;
             }
-        }
-        else if (activeTool == 4) // Rectangle
+        } else if (this.activeTool == 4) // Rectangle
         {
-            if (isDrawing && buttonNum != -1)
-            {
-                isDrawing = false;
+            if (this.isDrawing && buttonNum != -1) {
+                this.isDrawing = false;
 
                 // divide by pixel scale
-                int xInCanvas = (mx - canvasX) / CANVAS_SCALE;
-                int yInCanvas = (my - canvasY) / CANVAS_SCALE;
+                int xInCanvas = (mx - this.canvasX) / this.CANVAS_SCALE;
+                int yInCanvas = (my - this.canvasY) / this.CANVAS_SCALE;
 
                 byte color = 0;
-                if (this.mouseButton == 0)
-                {
-                    color = (byte) (selectedColor + 1);
+                if (this.mouseButton == 0) {
+                    color = (byte) (this.selectedColor + 1);
                 }
 
-                flagSurfaceEditor.drawRectangle(xLast, yLast, xInCanvas, yInCanvas, color);
-                flagEntity.isDirty = true;
+                this.flagSurfaceEditor.drawRectangle(this.xLast, this.yLast, xInCanvas, yInCanvas, color);
+                this.flagEntity.isDirty = true;
                 this.mouseButton = -1;
             }
-        }
-        else if (activeTool == 5) // Ellipse
+        } else if (this.activeTool == 5) // Ellipse
         {
-            if (isDrawing && buttonNum != -1)
-            {
-                isDrawing = false;
+            if (this.isDrawing && buttonNum != -1) {
+                this.isDrawing = false;
 
                 // divide by pixel scale
-                int xInCanvas = (mx - canvasX) / CANVAS_SCALE;
-                int yInCanvas = (my - canvasY) / CANVAS_SCALE;
+                int xInCanvas = (mx - this.canvasX) / this.CANVAS_SCALE;
+                int yInCanvas = (my - this.canvasY) / this.CANVAS_SCALE;
 
                 byte color = 0;
-                if (this.mouseButton == 0)
-                {
-                    color = (byte) (selectedColor + 1);
+                if (this.mouseButton == 0) {
+                    color = (byte) (this.selectedColor + 1);
                 }
 
-                flagSurfaceEditor.drawEllipse(xLast, yLast, xInCanvas, yInCanvas, color);
-                flagEntity.isDirty = true;
+                this.flagSurfaceEditor.drawEllipse(this.xLast, this.yLast, xInCanvas, yInCanvas, color);
+                this.flagEntity.isDirty = true;
                 this.mouseButton = -1;
             }
-        }
-        else if (activeTool == 6) // Line
+        } else if (this.activeTool == 6) // Line
         {
-            if (isDrawing && buttonNum != -1)
-            {
-                isDrawing = false;
+            if (this.isDrawing && buttonNum != -1) {
+                this.isDrawing = false;
 
                 // divide by pixel scale
-                int xInCanvas = (mx - canvasX) / CANVAS_SCALE;
-                int yInCanvas = (my - canvasY) / CANVAS_SCALE;
+                int xInCanvas = (mx - this.canvasX) / this.CANVAS_SCALE;
+                int yInCanvas = (my - this.canvasY) / this.CANVAS_SCALE;
 
                 byte color = 0;
-                if (this.mouseButton == 0)
-                {
-                    color = (byte) (selectedColor + 1);
+                if (this.mouseButton == 0) {
+                    color = (byte) (this.selectedColor + 1);
                 }
 
-                flagSurfaceEditor.drawLine(xLast, yLast, xInCanvas, yInCanvas, color, 1);
-                flagEntity.isDirty = true;
+                this.flagSurfaceEditor.drawLine(this.xLast, this.yLast, xInCanvas, yInCanvas, color, 1);
+                this.flagEntity.isDirty = true;
                 this.mouseButton = -1;
             }
         }
     }
 
     @Override
-    protected void drawGuiContainerBackgroundLayer(float f) 
-    {
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/flag_editor.png").bind();
-        int j = (width - xSize) / 2;
-        int k = (height - ySize) / 2;
-        drawTexturedModalRect(j, k, 0, 0, xSize, ySize);
-        drawTexturedModalRect(j + 127,  k + 8 + selectedColor * 22, 176, 0, 20, 20);
+    protected void drawGuiContainerBackgroundLayer(float f) {
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/flag_editor.png").bind();
+        int j = (this.width - this.xSize) / 2;
+        int k = (this.height - this.ySize) / 2;
+        drawTexturedModalRect(j, k, 0, 0, this.xSize, this.ySize);
+        drawTexturedModalRect(j + 127, k + 8 + this.selectedColor * 22, 176, 0, 20, 20);
     }
 
     @Override
-    public void render(int mx, int my, float partialTick)
-    {
+    public void render(int mx, int my, float partialTick) {
         super.render(mx, my, partialTick);
-        drawOverlaySurface.clear();
+        this.drawOverlaySurface.clear();
 
-        int xInCanvas = (mx - canvasX) / CANVAS_SCALE;
-        int yInCanvas = (my - canvasY) / CANVAS_SCALE;
-        byte color = (byte) (selectedColor + 1);
+        int xInCanvas = (mx - this.canvasX) / this.CANVAS_SCALE;
+        int yInCanvas = (my - this.canvasY) / this.CANVAS_SCALE;
+        byte color = (byte) (this.selectedColor + 1);
         if (this.mouseButton == 1) color = 4;
 
-        if (activeTool >= 0 && activeTool < 3) // Pen
+        if (this.activeTool >= 0 && this.activeTool < 3) // Pen
         {
-            drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, activeTool + 1);
-        }
-        else if (activeTool == 3) // Flood fill
+            this.drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, this.activeTool + 1);
+        } else if (this.activeTool == 3) // Flood fill
         {
-            drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, 1);
-        }
-        else if (activeTool == 4) // Rectangle
+            this.drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, 1);
+        } else if (this.activeTool == 4) // Rectangle
         {
-            if (isDrawing)
-            {
-                drawOverlaySurfaceEditor.drawRectangle(xLast, yLast, xInCanvas, yInCanvas, color);
-            }
-            else
-            {
-                drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, 1);
+            if (this.isDrawing) {
+                this.drawOverlaySurfaceEditor.drawRectangle(this.xLast, this.yLast, xInCanvas, yInCanvas, color);
+            } else {
+                this.drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, 1);
             }
-        }
-        else if (activeTool == 5) // Ellipse
+        } else if (this.activeTool == 5) // Ellipse
         {
-            if (isDrawing)
-            {
-                drawOverlaySurfaceEditor.drawEllipse(xLast, yLast, xInCanvas, yInCanvas, color);
-            }
-            else
-            {
-                drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, 1);
+            if (this.isDrawing) {
+                this.drawOverlaySurfaceEditor.drawEllipse(this.xLast, this.yLast, xInCanvas, yInCanvas, color);
+            } else {
+                this.drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, 1);
             }
-        }
-        else if (activeTool == 6) // Line
+        } else if (this.activeTool == 6) // Line
         {
-            if (isDrawing)
-            {
-                drawOverlaySurfaceEditor.drawLine(xLast, yLast, xInCanvas, yInCanvas, color, 1);
-            }
-            else
-            {
-                drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, 1);
+            if (this.isDrawing) {
+                this.drawOverlaySurfaceEditor.drawLine(this.xLast, this.yLast, xInCanvas, yInCanvas, color, 1);
+            } else {
+                this.drawOverlaySurfaceEditor.drawLine(xInCanvas, yInCanvas, xInCanvas, yInCanvas, color, 1);
             }
         }
 
@@ -429,72 +373,67 @@ public class ScreenFlagEditor
 
     @Override
     protected void drawGuiContainerForegroundLayer() {
-        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.edit_flag.label.inventory"), 8, (ySize - 96) + 2, 0xFF404040);
+        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.edit_flag.label.inventory"), 8, (this.ySize - 96) + 2, 0xFF404040);
     }
 
     @Override
-    public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
-    {
-        if (eventKey == Keyboard.KEY_ESCAPE || mc.gameSettings.keyInventory.isKeyboardKey(eventKey) || eventKey == Keyboard.KEY_BACK)
-        {
-            mc.thePlayer.closeScreen();
+    public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
+        if (eventKey == Keyboard.KEY_ESCAPE || this.mc.gameSettings.keyInventory.isKeyboardKey(eventKey) || eventKey == Keyboard.KEY_BACK) {
+            this.mc.thePlayer.closeScreen();
         }
 
         if (eventKey == Keyboard.KEY_1 || eventKey == Keyboard.KEY_2 || eventKey == Keyboard.KEY_3) {
-            colorLabels[selectedColor].setTextColor(0xFF404040);
-            colorLabels[selectedColor].setShadow(false);
-            selectedColor = eventKey - Keyboard.KEY_1;
-            colorLabels[selectedColor].setTextColor(0xFFFFFFFF);
-            colorLabels[selectedColor].setShadow(true);
+            this.colorLabels[this.selectedColor].setTextColor(0xFF404040);
+            this.colorLabels[this.selectedColor].setShadow(false);
+            this.selectedColor = eventKey - Keyboard.KEY_1;
+            this.colorLabels[this.selectedColor].setTextColor(0xFFFFFFFF);
+            this.colorLabels[this.selectedColor].setShadow(true);
 
         }
         super.keyPressed(eventCharacter, eventKey, mx, my);
     }
 
     @Override
-    public int getWidth()
-    {
-        return CANVAS_WIDTH;
+    public int getWidth() {
+        return this.CANVAS_WIDTH;
     }
 
     @Override
-    public int getHeight()
-    {
-        return CANVAS_HEIGHT;
+    public int getHeight() {
+        return this.CANVAS_HEIGHT;
     }
 
     @Override
-    public Byte getPixelValue(int x, int y)
-    {
-        if(x < 0 || x >= CANVAS_WIDTH)
+    public Byte getPixelValue(int x, int y) {
+        if (x < 0 || x >= this.CANVAS_WIDTH)
             return 0;
-        if(y < 0 || y >= CANVAS_HEIGHT)
+        if (y < 0 || y >= this.CANVAS_HEIGHT)
             return 0;
-        return flagEntity.flagColors[x + 24 * y];
+        return this.flagEntity.flagColors[x + 24 * y];
     }
 
     @Override
-    public boolean setPixelValue(int x, int y, Byte value)
-    {
-        if(x < 0 || x >= CANVAS_WIDTH)
+    public boolean setPixelValue(int x, int y, Byte value) {
+        if (x < 0 || x >= this.CANVAS_WIDTH)
             return false;
-        if(y < 0 || y >= CANVAS_HEIGHT)
+        if (y < 0 || y >= this.CANVAS_HEIGHT)
             return false;
-        flagEntity.flagColors[x + 24 * y] = value;
-        flagEntity.isDirty = true;
+        this.flagEntity.flagColors[x + 24 * y] = value;
+        this.flagEntity.isDirty = true;
         return true;
     }
 
     private static final ByteBuffer flagBuffer = ByteBuffer.allocate(1 + TileEntityFlag.CANVAS_HEIGHT * TileEntityFlag.CANVAS_WIDTH).order(ByteOrder.LITTLE_ENDIAN);
+
     public void sendUpdatePacket() {
         flagBuffer.clear();
 
         byte header = 0;
-        if (flagEntity.flipped) header |= 0b0000_0001;
+        if (this.flagEntity.flipped) header |= 0b0000_0001;
 
         flagBuffer.put(header);
-        flagBuffer.put(flagEntity.flagColors);
+        flagBuffer.put(this.flagEntity.flagColors);
 
-        mc.getSendQueue().addToSendQueue(new PacketCustomPayload(PacketCustomPayload.CHANNEL_FLAG, (ByteBuffer) flagBuffer.flip()));
+        this.mc.getSendQueue().addToSendQueue(new PacketCustomPayload(PacketCustomPayload.CHANNEL_FLAG, flagBuffer.flip()));
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFurnace.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFurnace.java
index da552c1f2..ebb468b32 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFurnace.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFurnace.java
@@ -1,49 +1,44 @@
 package net.minecraft.client.gui.container;
 
 import net.minecraft.client.input.controller.ControllerInput;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.block.entity.TileEntityFurnace;
-import net.minecraft.core.block.entity.TileEntityFurnaceBlast;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.menu.MenuFurnace;
 import net.minecraft.core.player.inventory.container.ContainerInventory;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
-public class ScreenFurnace extends ScreenContainerAbstract
-{
+public class ScreenFurnace extends ScreenContainerAbstract {
 
-    public ScreenFurnace(ContainerInventory inventory, TileEntityFurnace tileEntityFurnace)
-    {
+    public ScreenFurnace(ContainerInventory inventory, TileEntityFurnace tileEntityFurnace) {
         super(new MenuFurnace(inventory, tileEntityFurnace));
-        furnaceInventory = tileEntityFurnace;
+        this.furnaceInventory = tileEntityFurnace;
     }
 
     @Override
-	protected void drawGuiContainerForegroundLayer()
-    {
+    protected void drawGuiContainerForegroundLayer() {
         I18n i18n = I18n.getInstance();
         drawStringNoShadow(this.fontRenderer, i18n.translateKey("gui.furnace.label.furnace"), 60, 6, 0x404040);
-        drawStringNoShadow(this.fontRenderer, i18n.translateKey("gui.furnace.label.inventory"), 8, (ySize - 96) + 2, 0x404040);
+        drawStringNoShadow(this.fontRenderer, i18n.translateKey("gui.furnace.label.inventory"), 8, (this.ySize - 96) + 2, 0x404040);
     }
 
     @Override
-	protected void drawGuiContainerBackgroundLayer(float f)
-    {
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/furnace.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        int x = (width - xSize) / 2;
-        int y = (height - ySize) / 2;
-        drawTexturedModalRect(x, y, 0, 0, xSize, ySize);
-        if(furnaceInventory.isBurning())
-        {
-            int fireHeight = furnaceInventory.getBurnTimeRemainingScaled(12);
+    protected void drawGuiContainerBackgroundLayer(float f) {
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/furnace.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        int x = (this.width - this.xSize) / 2;
+        int y = (this.height - this.ySize) / 2;
+        drawTexturedModalRect(x, y, 0, 0, this.xSize, this.ySize);
+        if (this.furnaceInventory.isBurning()) {
+            int fireHeight = this.furnaceInventory.getBurnTimeRemainingScaled(12);
             drawTexturedModalRect(x + 56, y + 36 + 12 - fireHeight, 176, 12 - fireHeight, 14, fireHeight + 2);
-            int arrowWidth = furnaceInventory.getCookProgressScaled(24);
+            int arrowWidth = this.furnaceInventory.getCookProgressScaled(24);
             drawTexturedModalRect(x + 79, y + 34, 176, 14, arrowWidth + 1, 16);
         }
     }
+
     @Override
-    public void guiSpecificControllerInput(@NotNull ControllerInput controller){
+    public void guiSpecificControllerInput(@NotNull ControllerInput controller) {
         super.guiSpecificControllerInput(controller);
         controller.inventoryHandler.handleFurnace(this);
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFurnaceBlast.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFurnaceBlast.java
index 0b856472b..2eb8e39e0 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFurnaceBlast.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenFurnaceBlast.java
@@ -1,14 +1,12 @@
 package net.minecraft.client.gui.container;
 
 import net.minecraft.client.input.controller.ControllerInput;
-import net.minecraft.core.block.entity.TileEntityFurnace;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.block.entity.TileEntityFurnaceBlast;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.container.ContainerInventory;
-import net.minecraft.core.player.inventory.menu.MenuFurnace;
 import net.minecraft.core.player.inventory.menu.MenuFurnaceBlast;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 public class ScreenFurnaceBlast
     extends ScreenContainerAbstract
@@ -30,7 +28,7 @@ public class ScreenFurnaceBlast
     @Override
     protected void drawGuiContainerBackgroundLayer(final float f) {
         this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/blastfurnace.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         final int x = (this.width - this.xSize) / 2;
         final int y = (this.height - this.ySize) / 2;
         drawTexturedModalRect(x, y, 0, 0, this.xSize, this.ySize);
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenInventory.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenInventory.java
index cacf3487d..47d3a97d4 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenInventory.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenInventory.java
@@ -1,10 +1,5 @@
 package net.minecraft.client.gui.container;
 
-import static org.lwjgl.opengl.GL11.*;
-
-import java.util.ArrayList;
-import java.util.List;
-
 import it.unimi.dsi.fastutil.ints.IntArrayList;
 import it.unimi.dsi.fastutil.ints.IntList;
 import net.minecraft.client.gui.ButtonElement;
@@ -13,6 +8,9 @@ import net.minecraft.client.gui.ListLayout;
 import net.minecraft.client.gui.options.OverlayButtonElement;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.render.entity.EntityRenderer;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.achievement.Achievements;
 import net.minecraft.core.entity.player.Player;
@@ -23,298 +21,286 @@ import net.minecraft.core.item.ItemStack;
 import net.minecraft.client.option.GameSettings;
 import net.minecraft.core.player.gamemode.Gamemode;
 import net.minecraft.client.render.Lighting;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.client.render.EntityRenderDispatcher;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.core.util.helper.Color;
 import net.minecraft.core.util.helper.DamageType;
 import net.minecraft.client.option.OptionBoolean;
-import org.lwjgl.opengl.GL12;
 
-public class ScreenInventory extends ScreenContainerAbstract
-{
-	
-	private ButtonElement armorButton;
+public class ScreenInventory extends ScreenContainerAbstract {
+
+    private ButtonElement armorButton;
     protected int armourValuesFloat = 130;
     protected int armourButtonFloatX = 20;
-	protected ListLayout overlayButtonsLayout = new ListLayout(this).setAlign(0.5, 0.5).setVertical(false).setElementSize(11, 11).setOffset(-(xSize / 2), -(ySize / 2) - 10).setMargin(1);
-	private final IntList uvs = new IntArrayList();
-	
-	private DamageType hoveredDamageType;
+    protected float xSize_lo;
+    protected float ySize_lo;
+    protected ListLayout overlayButtonsLayout = new ListLayout(this).setAlign(0.5, 0.5).setVertical(false).setElementSize(11, 11).setOffset(-(this.xSize / 2), -(this.ySize / 2) - 10).setMargin(1);
+    private final IntList uvs = new IntArrayList();
+
+    private DamageType hoveredDamageType;
 
-    public ScreenInventory(Player player)
-    {
+
+    public ScreenInventory(Player player) {
         super(player.inventorySlots);
-        passEvents = true;
+        this.passEvents = true;
         player.addStat(Achievements.OPEN_INVENTORY, 1);
     }
 
     @Override
-	public void init()
-    {
-        buttons.clear();
+    public void init() {
+        this.buttons.clear();
 
 
-        armorButton = new ButtonElement(100, width / 2 - armourButtonFloatX, height / 2 - 74, 9, 9, "");
-        armorButton.visible = false;
+        this.armorButton = new ButtonElement(100, this.width / 2 - this.armourButtonFloatX, this.height / 2 - 74, 9, 9, "");
+        this.armorButton.visible = false;
         checkForArmor();
-        buttons.add(armorButton);
+        this.buttons.add(this.armorButton);
 
-		updateOverlayButtons();
+        updateOverlayButtons();
     }
 
     @Override
-    public void tick(){
+    public void tick() {
         checkForArmor();
     }
-    protected void checkForArmor(){
+
+    protected void checkForArmor() {
         boolean enableArmorButton = false;
 
-        for(int i = 0; i < mc.thePlayer.inventory.armorInventory.length; i++) {
-            ItemStack itemStack = mc.thePlayer.getItemInArmorSlot(HumanArmorShape.values()[i]);
-            if(itemStack != null) {
+        for (int i = 0; i < this.mc.thePlayer.inventory.armorInventory.length; i++) {
+            ItemStack itemStack = this.mc.thePlayer.getItemInArmorSlot(HumanArmorShape.values()[i]);
+            if (itemStack != null) {
                 enableArmorButton = true;
                 break;
             }
         }
 
-        armorButton.enabled = enableArmorButton;
+        this.armorButton.enabled = enableArmorButton;
     }
-    
+
     public void updateOverlayButtons() {
-        GameSettings settings = mc.gameSettings;
-        
-		boolean clock = false;
-		boolean compass = false;
-		boolean rotaryCalendar = false;
-
-		if (mc.thePlayer.getGamemode() == Gamemode.creative) {
-			clock = true;
-			compass = true;
-			rotaryCalendar = true;
-		} else {
-			for (int iinv = 0; iinv < mc.thePlayer.inventory.getContainerSize(); iinv++) {
-				ItemStack item = mc.thePlayer.inventory.getItem(iinv);
-				if (item != null) {
-					if (item.itemID == Items.TOOL_CLOCK.id) {
-						clock = true;
-					}
-					if (item.itemID == Items.TOOL_COMPASS.id) {
-						compass = true;
-					}
-					if (item.itemID == Items.TOOL_CALENDAR.id) {
-						rotaryCalendar = true;
-					}
-				}
-			}
-		}
-		
-		
-        overlayButtonsLayout.elements.clear();
-        
-        if(compass) {
-        	overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowCoords));
-        	uvs.add(0);
-        	overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowDirection));
-        	uvs.add(1);
+        GameSettings settings = this.mc.gameSettings;
+
+        boolean clock = false;
+        boolean compass = false;
+        boolean rotaryCalendar = false;
+
+        if (this.mc.thePlayer.getGamemode() == Gamemode.creative) {
+            clock = true;
+            compass = true;
+            rotaryCalendar = true;
+        } else {
+            for (int iinv = 0; iinv < this.mc.thePlayer.inventory.getContainerSize(); iinv++) {
+                ItemStack item = this.mc.thePlayer.inventory.getItem(iinv);
+                if (item != null) {
+                    if (item.itemID == Items.TOOL_CLOCK.id) {
+                        clock = true;
+                    }
+                    if (item.itemID == Items.TOOL_COMPASS.id) {
+                        compass = true;
+                    }
+                    if (item.itemID == Items.TOOL_CALENDAR.id) {
+                        rotaryCalendar = true;
+                    }
+                }
+            }
         }
-        if(clock) {
-        	overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowTime));
-        	uvs.add(2);
+
+
+        this.overlayButtonsLayout.elements.clear();
+
+        if (compass) {
+            this.overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowCoords));
+            this.uvs.add(0);
+            this.overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowDirection));
+            this.uvs.add(1);
         }
-        if(rotaryCalendar) {
-        	overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowSeason));
-        	uvs.add(3);
-        	overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowWeather));
-        	uvs.add(4);
-        	overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowBiome));
-        	uvs.add(5);
+        if (clock) {
+            this.overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowTime));
+            this.uvs.add(2);
         }
-        
-        overlayButtonsLayout.updateElementPositions();
-        
-        for (GuiElement element : overlayButtonsLayout.elements) {
-    		ButtonElement button = (ButtonElement) element;
-    		button.visible = false;
-    		buttons.add(button);
+        if (rotaryCalendar) {
+            this.overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowSeason));
+            this.uvs.add(3);
+            this.overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowWeather));
+            this.uvs.add(4);
+            this.overlayButtonsLayout.addElement(new OverlayButtonElement<>(settings, settings.overlayShowBiome));
+            this.uvs.add(5);
+        }
+
+        this.overlayButtonsLayout.updateElementPositions();
+
+        for (GuiElement element : this.overlayButtonsLayout.elements) {
+            ButtonElement button = (ButtonElement) element;
+            button.visible = false;
+            this.buttons.add(button);
         }
     }
 
     @Override
-	protected void drawGuiContainerForegroundLayer()
-    {
+    protected void drawGuiContainerForegroundLayer() {
         drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.inventory.label.crafting"), 86, 16, 0x404040);
     }
 
     @Override
-	public void render(int mx, int my, float partialTick)
-    {
+    public void render(int mx, int my, float partialTick) {
         super.render(mx, my, partialTick);
-        xSize_lo = mx;
-        ySize_lo = my;
+        this.xSize_lo = mx;
+        this.ySize_lo = my;
 
-        if(mc.gameSettings.armorProtectionOverlay.value && armorButton.enabled) {
-        	drawProtectionOverlay(mx, my);
+        if (this.mc.gameSettings.armorProtectionOverlay.value && this.armorButton.enabled) {
+            drawProtectionOverlay(mx, my);
         }
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/inventory.png").bind();
-        
-        glColor4d(1.0, 1.0, 1.0, 1.0);
-        glDisable(GL_BLEND);
-        glEnable(GL_TEXTURE_2D);
-        
-        if(armorButton.enabled) {
-            if(armorButton.isHovered(mx, my)) {
-            	drawTexturedModalRect(armorButton.xPosition, armorButton.yPosition, 185, 0, armorButton.width, armorButton.height);
-            }else {
-            	drawTexturedModalRect(armorButton.xPosition, armorButton.yPosition, 176, 0, armorButton.width, armorButton.height);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/inventory.png").bind();
+
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+        GLRenderer.enableState(State.BLEND);
+
+        if (this.armorButton.enabled) {
+            if (this.armorButton.isHovered(mx, my)) {
+                drawTexturedModalRect(this.armorButton.xPosition, this.armorButton.yPosition, 185, 0, this.armorButton.width, this.armorButton.height);
+            } else {
+                drawTexturedModalRect(this.armorButton.xPosition, this.armorButton.yPosition, 176, 0, this.armorButton.width, this.armorButton.height);
             }
         }
-        
-        for(int i=0; i < overlayButtonsLayout.elements.size(); i++) {
-        	OverlayButtonElement<?> button = (OverlayButtonElement<?>) overlayButtonsLayout.elements.get(i);
-        	drawTexturedModalRect(button.xPosition + 1, button.yPosition + 1, 176, 9 + 9 * uvs.getInt(i), 9, 9);
-        	boolean val = true;
-        	if(button.option instanceof OptionBoolean) val = (Boolean) button.option.value;
-        	if(!val) drawTexturedModalRect(button.xPosition + 1, button.yPosition + 1, 194, 0, 9, 9);
+
+        for (int i = 0; i < this.overlayButtonsLayout.elements.size(); i++) {
+            OverlayButtonElement<?> button = (OverlayButtonElement<?>) this.overlayButtonsLayout.elements.get(i);
+            drawTexturedModalRect(button.xPosition + 1, button.yPosition + 1, 176, 9 + 9 * this.uvs.getInt(i), 9, 9);
+            boolean val = true;
+            if (button.option instanceof OptionBoolean) val = (Boolean) button.option.value;
+            if (!val) drawTexturedModalRect(button.xPosition + 1, button.yPosition + 1, 194, 0, 9, 9);
         }
 
-        for(int i=0; i < overlayButtonsLayout.elements.size(); i++) {
-        	OverlayButtonElement<?> button = (OverlayButtonElement<?>) overlayButtonsLayout.elements.get(i);
-        	if(button.isHovered(mx, my))
-            {
-                tooltipElement.render(button.option.getDisplayStringName() + ": " + button.displayString, mx, my, 8, -8);
-        	}
+        for (int i = 0; i < this.overlayButtonsLayout.elements.size(); i++) {
+            OverlayButtonElement<?> button = (OverlayButtonElement<?>) this.overlayButtonsLayout.elements.get(i);
+            if (button.isHovered(mx, my)) {
+                this.tooltipElement.render(button.option.getDisplayStringName() + ": " + button.displayString, mx, my, 8, -8);
+            }
         }
-        
+
     }
-    
+
     protected Color protectionOverlayBgColor = new Color().setRGBA(0, 0, 0, 127);
 
+
     public void drawProtectionOverlay(int mouseX, int mouseY) {
-        hoveredDamageType = null;
-        
-    	int x = width / 2 - armourValuesFloat - 4;
-    	int y = height / 2 - 79;
-    	
-    	int w = 44;
-    	int h = 44;
+        this.hoveredDamageType = null;
 
-        glEnable(GL_BLEND);
-        drawGradientRect(x, y, x + w, y + h, protectionOverlayBgColor.getARGB(), protectionOverlayBgColor.getARGB());
+        int x = this.width / 2 - this.armourValuesFloat - 4;
+        int y = this.height / 2 - 79;
 
-        glDisable(GL_BLEND);
-        glDisable(GL_CULL_FACE);
+        int w = 44;
+        int h = 44;
+
+        drawGradientRect(x, y, x + w, y + h, this.protectionOverlayBgColor.getARGB(), this.protectionOverlayBgColor.getARGB());
+
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.disableState(State.CULL_FACE);
 
         int w2 = 26;
-		int x2 = x;
-		int h2 = 4;
-		
-        int i=0;
-        for(DamageType damageType : DamageType.values()) {
-        	if(damageType.shouldDisplay()) {
-        		int y2 = y + i * 10;
-        		
-            	float protection = mc.thePlayer.getTotalProtectionAmount(damageType);
-            	if(protection > 1) protection = 1.0f;
+        int x2 = x;
+        int h2 = 4;
+
+        int i = 0;
+        for (DamageType damageType : DamageType.values()) {
+            if (damageType.shouldDisplay()) {
+                int y2 = y + i * 10;
+
+                float protection = this.mc.thePlayer.getTotalProtectionAmount(damageType);
+                if (protection > 1) protection = 1.0f;
 
                 int l = (int) (protection * 255);
-    			final int color = (255 - l << 16 | l << 8) | 0xFF000000;
+                final int color = (255 - l << 16 | l << 8) | 0xFF000000;
 //    			fontRenderer.drawStringWithShadow(Utils.percent(protection)+"%", x + 15, y + 3 + i * 10, color);
-    			
-    			glEnable(GL_TEXTURE_2D);
-    			glColor4d(1.0, 1.0, 1.0, 1.0);
+
+                GLRenderer.setColor4f(1f, 1f, 1f, 1f);
                 drawGuiIcon(x2 + 2, y2 + 2, 9, 9, TextureRegistry.getTexture(damageType.getIcon()));
-    			
-    			glDisable(GL_TEXTURE_2D);
-    			
-    			drawRectWidthHeight(x2 + 14, y2 + 4, w2+2, h2+1, 0xFF000000);
-    			drawRectWidthHeight(x2 + 15, y2 + 4, (int)(protection * w2), h2, color);
-    			
-    			if(mouseX >= x2&& mouseY >= y2 + 2 && mouseX <= x2 + w && mouseY <= y2 + 12 ) {
-    				hoveredDamageType = damageType;
-    			}
-        	}
-        	i++;
+
+
+                drawRectWidthHeight(x2 + 14, y2 + 4, w2 + 2, h2 + 1, 0xFF000000);
+                drawRectWidthHeight(x2 + 15, y2 + 4, (int) (protection * w2), h2, color);
+
+                if (mouseX >= x2 && mouseY >= y2 + 2 && mouseX <= x2 + w && mouseY <= y2 + 12) {
+                    this.hoveredDamageType = damageType;
+                }
+            }
+            i++;
         }
-        
-        glEnable(GL_TEXTURE_2D);
-        
-        if(hoveredDamageType != null) {
-        	int protection = Math.round(mc.thePlayer.getTotalProtectionAmount(hoveredDamageType) * 100);
-        	if(protection < 0) {
-        		protection = 0;
-        	}
-        	if(protection > 100) {
-        		protection = 100;
-        	}
-
-        	String str = I18n.getInstance().translateKey(hoveredDamageType.getLanguageKey()) + ":\n" + protection + " / 100";
-        	
-        	tooltipElement.render(str, mouseX, mouseY, 8, -8);
+
+        if (this.hoveredDamageType != null) {
+            int protection = Math.round(this.mc.thePlayer.getTotalProtectionAmount(this.hoveredDamageType) * 100);
+            if (protection < 0) {
+                protection = 0;
+            }
+            if (protection > 100) {
+                protection = 100;
+            }
+
+            String str = I18n.getInstance().translateKey(this.hoveredDamageType.getLanguageKey()) + ":\n" + protection + " / 100";
+
+            this.tooltipElement.render(str, mouseX, mouseY, 8, -8);
         }
     }
 
     @Override
-	protected void drawGuiContainerBackgroundLayer(float f)
-    {
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/inventory.png").bind();
-        int j = (width - xSize) / 2;
-        int k = (height - ySize) / 2;
-        drawTexturedModalRect(j, k, 0, 0, xSize, ySize);
-
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glPushMatrix();
-        GL11.glTranslatef(j + 51, k + 75, 50F);
+    protected void drawGuiContainerBackgroundLayer(float f) {
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/inventory.png").bind();
+        int j = (this.width - this.xSize) / 2;
+        int k = (this.height - this.ySize) / 2;
+        drawTexturedModalRect(j, k, 0, 0, this.xSize, this.ySize);
+
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.WORLD);
+        GLRenderer.getFogState().disable();
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.modelM4f().translate(j + 51, k + 75, 50F);
         float f1 = 30F;
-        GL11.glScalef(-f1, f1, f1);
-        GL11.glRotatef(180F, 0.0F, 0.0F, 1.0F);
-        float f2 = mc.thePlayer.yBodyRot;
-        float f3 = mc.thePlayer.yRot;
-        float f4 = mc.thePlayer.xRot;
-        float f5 = (float)(j + 51) - xSize_lo;
-        float f6 = (float)((k + 75) - 50) - ySize_lo;
-        GL11.glRotatef(135F, 0.0F, 1.0F, 0.0F);
+        GLRenderer.modelM4f().scale(-f1, f1, f1);
+        GLRenderer.modelM4f().rotateZ(org.joml.Math.toRadians(180F));
+        float f2 = this.mc.thePlayer.yBodyRot;
+        float f3 = this.mc.thePlayer.yRot;
+        float f4 = this.mc.thePlayer.xRot;
+        float f5 = (float) (j + 51) - this.xSize_lo;
+        float f6 = (float) ((k + 75) - 50) - this.ySize_lo;
+        GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(135F));
         Lighting.enableLight();
-        GL11.glRotatef(-135F, 0.0F, 1.0F, 0.0F);
-        GL11.glRotatef(-(float)Math.atan(f6 / 40F) * 20F, 1.0F, 0.0F, 0.0F);
-        mc.thePlayer.yBodyRot = (float)Math.atan(f5 / 40F) * 20F;
-        mc.thePlayer.yRot = (float)Math.atan(f5 / 40F) * 40F;
-        mc.thePlayer.xRot = -(float)Math.atan(f6 / 40F) * 20F;
-        mc.thePlayer.entityBrightness = 1.0F;
-        GL11.glTranslatef(0.0F, mc.thePlayer.heightOffset, 0.0F);
-        EntityRenderDispatcher.instance.viewLerpYaw = 180F;
+        GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(-135F));
+        GLRenderer.modelM4f().rotateX(org.joml.Math.toRadians(-(float) Math.atan(f6 / 40F) * 20F));
+        this.mc.thePlayer.yBodyRot = (float) Math.atan(f5 / 40F) * 20F;
+        this.mc.thePlayer.yRot = (float) Math.atan(f5 / 40F) * 40F;
+        this.mc.thePlayer.xRot = -(float) Math.atan(f6 / 40F) * 20F;
+        this.mc.thePlayer.entityBrightness = 1.0F;
+        GLRenderer.modelM4f().translate(0.0F, this.mc.thePlayer.heightOffset, 0.0F);
+        EntityRendererDispatcher.instance.viewLerpYaw = 180F;
         EntityRenderer.renderShadows = false;
-        EntityRenderDispatcher.instance.renderEntityPreviewWithPosYaw(Tessellator.instance, mc.thePlayer, 0.0D, 0.0D, 0.0D, 0.0F, 1.0F);
+        GLRenderer.globalGetNormalTransformMatrix().scale(1, -1, 1);
+        EntityRendererDispatcher.instance.renderEntityPreviewWithPosYaw(GLRenderer.getTessellator(), this.mc.thePlayer, 0.0D, 0.0D, 0.0D, 0.0F, 1.0F);
         EntityRenderer.renderShadows = true;
-        mc.thePlayer.entityBrightness = 0.0F;
-        mc.thePlayer.yBodyRot = f2;
-        mc.thePlayer.yRot = f3;
-        mc.thePlayer.xRot = f4;
-        GL11.glPopMatrix();
+        this.mc.thePlayer.entityBrightness = 0.0F;
+        this.mc.thePlayer.yBodyRot = f2;
+        this.mc.thePlayer.yRot = f3;
+        this.mc.thePlayer.xRot = f4;
+        GLRenderer.popFrame();
         Lighting.disable();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 
     @Override
-	protected void buttonClicked(@NotNull ButtonElement button)
-    {
-        if (button == armorButton) {
-        	mc.gameSettings.armorProtectionOverlay.toggle();
+    protected void buttonClicked(@NotNull ButtonElement button) {
+        if (button == this.armorButton) {
+            this.mc.gameSettings.armorProtectionOverlay.toggle();
         }
     }
 
     @Override
-    public void guiSpecificControllerInput(@NotNull ControllerInput controller){
+    public void guiSpecificControllerInput(@NotNull ControllerInput controller) {
         super.guiSpecificControllerInput(controller);
         controller.inventoryHandler.handleInventory(this);
     }
 
-    protected float xSize_lo;
-    protected float ySize_lo;
-
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenInventoryCreative.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenInventoryCreative.java
index 85daf0176..91b920e26 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenInventoryCreative.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenInventoryCreative.java
@@ -4,242 +4,221 @@ import net.minecraft.client.gui.ButtonElement;
 import net.minecraft.client.gui.TextFieldElement;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.render.entity.EntityRenderer;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.InventoryAction;
 import net.minecraft.core.entity.player.Player;
 import net.minecraft.client.gui.options.OptionsButtonElement;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.menu.MenuInventoryCreative;
 import net.minecraft.client.render.Lighting;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.client.render.EntityRenderDispatcher;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.gui.TextFieldElement.ITextChangeListener;
-import org.lwjgl.opengl.GL12;
-
-public class ScreenInventoryCreative extends ScreenInventory implements ITextChangeListener
-{
-	protected ButtonElement lastPageButton;
-	protected ButtonElement nextPageButton;
-	protected ButtonElement clearSearchButton;
-	protected TextFieldElement searchField;
-	protected MenuInventoryCreative container;
-	protected String pageString = "1/1";
-	
-	public ScreenInventoryCreative(Player entityplayer)
-	{
-		super(entityplayer);
-		xSize = 298;
-		container = (MenuInventoryCreative)entityplayer.inventorySlots;
-		armourValuesFloat = 186;
-		armourButtonFloatX = 81;
-		overlayButtonsLayout.setOffset(-(xSize / 2), -(ySize / 2) - 10);
-	}
-	
-	@Override
-	public void init()
-	{
-		super.init();
-		buttons.add(lastPageButton = new ButtonElement(500, 0, 0, 20, 20, "<"));
-		buttons.add(nextPageButton = new ButtonElement(501, 0, 0, 20, 20, ">"));
-		buttons.add(clearSearchButton = new OptionsButtonElement(0, 0, 10, 12, 20, "").setTextures("minecraft:gui/screen/creative/clear", "minecraft:gui/screen/creative/clear_highlighted", null));
-		searchField = new TextFieldElement(this, fontRenderer, 0, 0, 96, 18, container.searchText, I18n.getInstance().translateKey("gui.inventory.creative.label.search"));
-		searchField.drawBackground =false;
-		searchField.setMaxStringLength(14);
-		searchField.setTextChangeListener(this);
-		updatePageSwitcher();
-		Keyboard.enableRepeatEvents(true);
-	}
-	
-	public void scroll(int direction) {
-		if(direction == 0) return;
-		int count = 1;
-		if(Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL)) {
-			count = 10;
-			if(Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT)) {
-				count = 100;
-			}
-		}
-		while(lastPageButton.enabled && direction > 0 && count > 0) {
-			container.lastPage();
-			updatePageSwitcher();
-			count--;
-		}
-		while(nextPageButton.enabled && direction < 0 && count > 0) {
-			container.nextPage();
-			updatePageSwitcher();
-			count--;
-		}
-	}
-
-	@Override
-	public void tick()
-	{
-		super.tick();
-		searchField.updateCursorCounter();
-	}
-
-	@Override
-	public void removed()
-	{
-		super.removed();
-		Keyboard.enableRepeatEvents(false);
-	}
-
-	protected void updatePageSwitcher()
-	{
-		lastPageButton.enabled = container.page != 0;
-		nextPageButton.enabled = container.page != container.maxPage;
-		
-		pageString = (container.page + 1) + "/" + (container.maxPage + 1);
-	}
-	
+
+public class ScreenInventoryCreative extends ScreenInventory implements ITextChangeListener {
+    protected ButtonElement lastPageButton;
+    protected ButtonElement nextPageButton;
+    protected ButtonElement clearSearchButton;
+    protected TextFieldElement searchField;
+    protected MenuInventoryCreative container;
+    protected String pageString = "1/1";
+
+    public ScreenInventoryCreative(Player entityplayer) {
+        super(entityplayer);
+        this.xSize = 298;
+        this.container = (MenuInventoryCreative) entityplayer.inventorySlots;
+        this.armourValuesFloat = 186;
+        this.armourButtonFloatX = 81;
+        this.overlayButtonsLayout.setOffset(-(this.xSize / 2), -(this.ySize / 2) - 10);
+    }
+
+    @Override
+    public void init() {
+        super.init();
+        this.buttons.add(this.lastPageButton = new ButtonElement(500, 0, 0, 20, 20, "<"));
+        this.buttons.add(this.nextPageButton = new ButtonElement(501, 0, 0, 20, 20, ">"));
+        this.buttons.add(this.clearSearchButton = new OptionsButtonElement(0, 0, 10, 12, 20, "").setTextures("minecraft:gui/screen/creative/clear", "minecraft:gui/screen/creative/clear_highlighted", null));
+        this.searchField = new TextFieldElement(this, this.fontRenderer, 0, 0, 96, 18, this.container.searchText, I18n.getInstance().translateKey("gui.inventory.creative.label.search"));
+        this.searchField.drawBackground = false;
+        this.searchField.setMaxStringLength(14);
+        this.searchField.setTextChangeListener(this);
+        updatePageSwitcher();
+        Keyboard.enableRepeatEvents(true);
+    }
+
+    public void scroll(int direction) {
+        if (direction == 0) return;
+        int count = 1;
+        if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL)) {
+            count = 10;
+            if (Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT)) {
+                count = 100;
+            }
+        }
+        while (this.lastPageButton.enabled && direction > 0 && count > 0) {
+            this.container.lastPage();
+            updatePageSwitcher();
+            count--;
+        }
+        while (this.nextPageButton.enabled && direction < 0 && count > 0) {
+            this.container.nextPage();
+            updatePageSwitcher();
+            count--;
+        }
+    }
+
     @Override
-	protected void buttonClicked(@NotNull ButtonElement button)
-    {
-		super.buttonClicked(button);
-    	if (!button.enabled)
-    	{
-    		return;
-    	}
-    	
-    	if (button == lastPageButton)
-    	{
-    		scroll(1);
-    	}
-    	else if (button == nextPageButton)
-    	{
-    		scroll(-1);
-    	}
-    	else if (button == clearSearchButton)
-    	{
-			if (Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT))
-			{
-				for(int i = 0; i < container.inventory.getContainerSize() + container.craftSlots.getContainerSize() + container.resultSlots.getContainerSize(); i++) {
-					mc.playerController.handleInventoryMouseClick(container.containerId, InventoryAction.CREATIVE_DELETE, new int[]{i}, mc.thePlayer);
-				}
-			}
-			else
-			{
-				searchField.setText("");
-				container.searchPage("");
-				updatePageSwitcher();
-			}
-    	}
-    	
-    	updatePageSwitcher();
+    public void tick() {
+        super.tick();
+        this.searchField.updateCursorCounter();
     }
 
-	@Override
-	public void render(int mx, int my, float partialTick) {
-		super.render(mx, my, partialTick);
-		searchField.updateCursor(mc, mx, my);
-	}
+    @Override
+    public void removed() {
+        super.removed();
+        Keyboard.enableRepeatEvents(false);
+    }
+
+    protected void updatePageSwitcher() {
+        this.lastPageButton.enabled = this.container.page != 0;
+        this.nextPageButton.enabled = this.container.page != this.container.maxPage;
+
+        this.pageString = (this.container.page + 1) + "/" + (this.container.maxPage + 1);
+    }
+
+    @Override
+    protected void buttonClicked(@NotNull ButtonElement button) {
+        super.buttonClicked(button);
+        if (!button.enabled) {
+            return;
+        }
+
+        if (button == this.lastPageButton) {
+            scroll(1);
+        } else if (button == this.nextPageButton) {
+            scroll(-1);
+        } else if (button == this.clearSearchButton) {
+            if (Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT)) {
+                for (int i = 0; i < this.container.inventory.getContainerSize() + this.container.craftSlots.getContainerSize() + this.container.resultSlots.getContainerSize(); i++) {
+                    this.mc.playerController.handleInventoryMouseClick(this.container.containerId, InventoryAction.CREATIVE_DELETE, new int[]{i}, this.mc.thePlayer);
+                }
+            } else {
+                this.searchField.setText("");
+                this.container.searchPage("");
+                updatePageSwitcher();
+            }
+        }
 
-	@Override
-	public void mouseClicked(int mx, int my, int buttonNum)
-    {
+        updatePageSwitcher();
+    }
+
+    @Override
+    public void render(int mx, int my, float partialTick) {
+        super.render(mx, my, partialTick);
+        this.searchField.updateCursor(this.mc, mx, my);
+    }
+
+    @Override
+    public void mouseClicked(int mx, int my, int buttonNum) {
         super.mouseClicked(mx, my, buttonNum);
-        searchField.mouseClicked(mx, my, buttonNum);
+        this.searchField.mouseClicked(mx, my, buttonNum);
     }
-    
+
     @Override
-	public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
-    {
-    	if (searchField.isFocused && eventKey != Keyboard.KEY_ESCAPE)
-    	{
-    		searchField.textboxKeyTyped(eventCharacter, eventKey);
-    		container.searchPage(searchField.getText());
-    		updatePageSwitcher();
-    	}
-    	else if (!searchField.isFocused && eventCharacter == 't')
-    	{
-    		searchField.setFocused(true);
-    	}
-    	else
-    	{
-    		super.keyPressed(eventCharacter, eventKey, mx, my);
-    	}
+    public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
+        if (this.searchField.isFocused && eventKey != Keyboard.KEY_ESCAPE) {
+            this.searchField.textboxKeyTyped(eventCharacter, eventKey);
+            this.container.searchPage(this.searchField.getText());
+            updatePageSwitcher();
+        } else if (!this.searchField.isFocused && eventCharacter == 't') {
+            this.searchField.setFocused(true);
+        } else {
+            super.keyPressed(eventCharacter, eventKey, mx, my);
+        }
     }
-    
+
     @Override
-	protected void drawGuiContainerForegroundLayer()
-    {
-    	super.drawGuiContainerForegroundLayer();
-    	drawStringCenteredNoShadow(fontRenderer, pageString, 238, 146, 0x404040);
+    protected void drawGuiContainerForegroundLayer() {
+        super.drawGuiContainerForegroundLayer();
+        drawStringCenteredNoShadow(this.fontRenderer, this.pageString, 238, 146, 0x404040);
     }
-	
+
     @Override
-	protected void drawGuiContainerBackgroundLayer(float f)
-    {
-		scroll(Mouse.getDWheel());
-
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-		mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/creative.png").bind();
-        int x = (width - xSize) / 2;
-        int y = (height - ySize) / 2;
-        lastPageButton.xPosition = x + 182;
-        lastPageButton.yPosition = y + 140;
-        nextPageButton.xPosition = x + 272;
-        nextPageButton.yPosition = y + 140;
-        clearSearchButton.xPosition = x + 280;
-        clearSearchButton.yPosition = y + 6;
-        searchField.xPosition = x + 183;
-        searchField.yPosition = y + 7;
-        drawTexturedModalRect((double)x, (double)y, 0, 0, xSize, ySize, xSize / 2, ySize / 2);
-
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glPushMatrix();
-        GL11.glTranslatef(x + 51, y + 75, 50F);
+    protected void drawGuiContainerBackgroundLayer(float f) {
+        scroll(Mouse.getDWheel());
+
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/creative.png").bind();
+        int x = (this.width - this.xSize) / 2;
+        int y = (this.height - this.ySize) / 2;
+        this.lastPageButton.xPosition = x + 182;
+        this.lastPageButton.yPosition = y + 140;
+        this.nextPageButton.xPosition = x + 272;
+        this.nextPageButton.yPosition = y + 140;
+        this.clearSearchButton.xPosition = x + 280;
+        this.clearSearchButton.yPosition = y + 6;
+        this.searchField.xPosition = x + 183;
+        this.searchField.yPosition = y + 7;
+        drawTexturedModalRect(x, (double) y, 0, 0, this.xSize, this.ySize, this.xSize / 2, this.ySize / 2);
+
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.setShader(Shaders.WORLD);
+        GLRenderer.getFogState().disable();
+        GLRenderer.modelM4f().translate(x + 51, y + 75, 50F);
         float f1 = 30F;
-        GL11.glScalef(-f1, f1, f1);
-        GL11.glRotatef(180F, 0.0F, 0.0F, 1.0F);
-        float f2 = mc.thePlayer.yBodyRot;
-        float f3 = mc.thePlayer.yRot;
-        float f4 = mc.thePlayer.xRot;
-        float f5 = (float)(x + 51) - xSize_lo;
-        float f6 = (float)((y + 75) - 50) - ySize_lo;
-        GL11.glRotatef(135F, 0.0F, 1.0F, 0.0F);
+        GLRenderer.modelM4f().scale(-f1, f1, f1);
+        GLRenderer.modelM4f().rotateZ(org.joml.Math.toRadians(180F));
+        float f2 = this.mc.thePlayer.yBodyRot;
+        float f3 = this.mc.thePlayer.yRot;
+        float f4 = this.mc.thePlayer.xRot;
+        float f5 = (float) (x + 51) - this.xSize_lo;
+        float f6 = (float) ((y + 75) - 50) - this.ySize_lo;
+        GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(135F));
         Lighting.enableLight();
-        GL11.glRotatef(-135F, 0.0F, 1.0F, 0.0F);
-        GL11.glRotatef(-(float)Math.atan(f6 / 40F) * 20F, 1.0F, 0.0F, 0.0F);
-        mc.thePlayer.yBodyRot = (float)Math.atan(f5 / 40F) * 20F;
-        mc.thePlayer.yRot = (float)Math.atan(f5 / 40F) * 40F;
-        mc.thePlayer.xRot = -(float)Math.atan(f6 / 40F) * 20F;
-        mc.thePlayer.entityBrightness = 1.0F;
-        GL11.glTranslatef(0.0F, mc.thePlayer.heightOffset, 0.0F);
-        EntityRenderDispatcher.instance.viewLerpYaw = 180F;
-		EntityRenderer.renderShadows = false;
-        EntityRenderDispatcher.instance.renderEntityPreviewWithPosYaw(Tessellator.instance, mc.thePlayer, 0.0D, 0.0D, 0.0D, 0.0F, 1.0F);
-		EntityRenderer.renderShadows = true;
-		mc.thePlayer.entityBrightness = 0.0F;
-        mc.thePlayer.yBodyRot = f2;
-        mc.thePlayer.yRot = f3;
-        mc.thePlayer.xRot = f4;
-        GL11.glPopMatrix();
+        GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(-135F));
+        GLRenderer.modelM4f().rotateX(org.joml.Math.toRadians(-(float) Math.atan(f6 / 40F) * 20F));
+        this.mc.thePlayer.yBodyRot = (float) Math.atan(f5 / 40F) * 20F;
+        this.mc.thePlayer.yRot = (float) Math.atan(f5 / 40F) * 40F;
+        this.mc.thePlayer.xRot = -(float) Math.atan(f6 / 40F) * 20F;
+        this.mc.thePlayer.entityBrightness = 1.0F;
+        GLRenderer.modelM4f().translate(0.0F, this.mc.thePlayer.heightOffset, 0.0F);
+        EntityRendererDispatcher.instance.viewLerpYaw = 180F;
+        EntityRenderer.renderShadows = false;
+        GLRenderer.globalGetNormalTransformMatrix().scale(1, -1, 1);
+        EntityRendererDispatcher.instance.renderEntityPreviewWithPosYaw(GLRenderer.getTessellator(), this.mc.thePlayer, 0.0D, 0.0D, 0.0D, 0.0F, 1.0F);
+        EntityRenderer.renderShadows = true;
+        this.mc.thePlayer.entityBrightness = 0.0F;
+        this.mc.thePlayer.yBodyRot = f2;
+        this.mc.thePlayer.yRot = f3;
+        this.mc.thePlayer.xRot = f4;
+        GLRenderer.popFrame();
         Lighting.disable();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
-        searchField.drawTextBox();
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        this.searchField.drawTextBox();
     }
 
-	@Override
+    @Override
     public void textChanged(TextFieldElement textField) {
-		container.searchPage(textField.getText());
-		updatePageSwitcher();
-	}
-	@Override
-	public void guiSpecificControllerInput(@NotNull ControllerInput controller){
-		if(controller.buttonLeftShoulder.pressedThisFrame()) {
-			this.scroll(1);
-		}
-		if(controller.buttonRightShoulder.pressedThisFrame()) {
-			this.scroll(-1);
-		}
-		super.guiSpecificControllerInput(controller);
-	}
+        this.container.searchPage(textField.getText());
+        updatePageSwitcher();
+    }
+
+    @Override
+    public void guiSpecificControllerInput(@NotNull ControllerInput controller) {
+        if (controller.buttonLeftShoulder.pressedThisFrame()) {
+            this.scroll(1);
+        }
+        if (controller.buttonRightShoulder.pressedThisFrame()) {
+            this.scroll(-1);
+        }
+        super.guiSpecificControllerInput(controller);
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenTrommel.java b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenTrommel.java
index 3319ff80d..7ba7105f2 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/container/ScreenTrommel.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/container/ScreenTrommel.java
@@ -1,48 +1,44 @@
 package net.minecraft.client.gui.container;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.block.entity.TileEntityTrommel;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.container.ContainerInventory;
 import net.minecraft.core.player.inventory.menu.MenuTrommel;
 import org.lwjgl.opengl.GL11;
 
-public class ScreenTrommel extends ScreenContainerAbstract
-{
+public class ScreenTrommel extends ScreenContainerAbstract {
+    private final TileEntityTrommel trommelInventory;
 
-    public ScreenTrommel(ContainerInventory inventoryplayer, TileEntityTrommel tileentitytrommel)
-    {
-        super(new MenuTrommel(inventoryplayer, tileentitytrommel));
-        ySize = 192;
-        trommelInventory = tileentitytrommel;
+
+    public ScreenTrommel(ContainerInventory containerInventory, TileEntityTrommel tileentitytrommel) {
+        super(new MenuTrommel(containerInventory, tileentitytrommel));
+        this.ySize = 192;
+        this.trommelInventory = tileentitytrommel;
     }
 
     @Override
-	protected void drawGuiContainerForegroundLayer()
-    {
+    protected void drawGuiContainerForegroundLayer() {
         drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.trommel.label.trommel"), 60, 6, 0x404040);
-        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.trommel.label.inventory"), 8, (ySize - 96) + 2, 0x404040);
+        drawStringNoShadow(this.fontRenderer, I18n.getInstance().translateKey("gui.trommel.label.inventory"), 8, (this.ySize - 96) + 2, 0x404040);
     }
 
     @Override
-	protected void drawGuiContainerBackgroundLayer(float f)
-    {
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/trommel.png").bind();
-        int j = (width - xSize) / 2;
-        int k = (height - ySize) / 2;
-        drawTexturedModalRect(j, k, 0, 0, xSize, ySize);
-        if(trommelInventory.isBurning())
-        {
-            int l = trommelInventory.getBurnTimeRemainingScaled(12);
+    protected void drawGuiContainerBackgroundLayer(float f) {
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/trommel.png").bind();
+        int j = (this.width - this.xSize) / 2;
+        int k = (this.height - this.ySize) / 2;
+        drawTexturedModalRect(j, k, 0, 0, this.xSize, this.ySize);
+        if (this.trommelInventory.isBurning()) {
+            int l = this.trommelInventory.getBurnTimeRemainingScaled(12);
             drawTexturedModalRect(j + 33, (k + 33 + 12) - l, 176, 12 - l, 14, l + 2);
         }
-        int i1 = (int)trommelInventory.getCookProgressPercent(8)%4;
-        GL11.glPushMatrix();
-        GL11.glTranslatef((j+105), (k+50), 0.0F);
-        drawTexturedModalRect(0, 0, 176+(i1*16), 16, 16, 16);
-        GL11.glPopMatrix();
+        int i1 = (int) this.trommelInventory.getCookProgressPercent(8) % 4;
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((j + 105), (k + 50), 0.0F);
+        drawTexturedModalRect(0, 0, 176 + (i1 * 16), 16, 16, 16);
+        GLRenderer.popFrame();
 
     }
-
-    private TileEntityTrommel trommelInventory;
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/error/ScreenMissingMinecraft.java b/game/client/src/main/java/net/minecraft/client/gui/error/ScreenMissingMinecraft.java
index cd0b82495..4be4956b8 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/error/ScreenMissingMinecraft.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/error/ScreenMissingMinecraft.java
@@ -4,7 +4,9 @@ import com.mojang.logging.LogUtils;
 import net.minecraft.client.gui.ButtonElement;
 import net.minecraft.client.gui.ClickableLabelElement;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.util.helper.UrlHelper;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.util.helper.MathHelper;
@@ -12,46 +14,41 @@ import org.jetbrains.annotations.NotNull;
 import org.lwjgl.opengl.GL11;
 import org.slf4j.Logger;
 
-import java.awt.*;
-import java.net.URI;
-
 public class ScreenMissingMinecraft extends Screen {
     private static final Logger LOGGER = LogUtils.getLogger();
     public int ticks = 0;
+
     @Override
-    public void init()
-    {
+    public void init() {
         I18n i = I18n.getInstance();
-        buttons.clear();
+        this.buttons.clear();
         String downloadString = i.translateKey("gui.no_minecraft.button.guide");
-        buttons.add(new ButtonElement(0, width / 2 - 100, height / 4 + 120 + 12, i.translateKey("gui.no_minecraft.button.quit")));
-        ClickableLabelElement installLabel = new ClickableLabelElement(1, width / 2 - 170, (height / 4 - 60) + 60 + 64, downloadString, 0x7C99EA);
-        buttons.add(installLabel);
-        buttons.add(new ClickableLabelElement(2, 0,  height - mc.font.getFont().fontHeight() - 4, i.translateKey("gui.main_menu.button.discord"), 0x5865F2));
+        this.buttons.add(new ButtonElement(0, this.width / 2 - 100, this.height / 4 + 120 + 12, i.translateKey("gui.no_minecraft.button.quit")));
+        ClickableLabelElement installLabel = new ClickableLabelElement(1, this.width / 2 - 170, (this.height / 4 - 60) + 60 + 64, downloadString, 0x7C99EA);
+        this.buttons.add(installLabel);
+        this.buttons.add(new ClickableLabelElement(2, 0, this.height - this.mc.font.getFont().fontHeight() - 4, i.translateKey("gui.main_menu.button.discord"), 0x5865F2));
     }
+
     @Override
-    public void render(int mx, int my, float partialTick)
-    {
+    public void render(int mx, int my, float partialTick) {
         I18n i = I18n.getInstance();
         drawBackground(partialTick);
-        drawStringCenteredShadow(fontRenderer, i.translateKey("gui.no_minecraft.label.title"), width / 2, (height / 4 - 60) + 20, 0xffff60);
-        drawStringShadow(fontRenderer, i.translateKey("gui.no_minecraft.label.body.1"), width / 2 - 170, (height / 4 - 60) + 60 + 0, 0xdedede);
-        drawStringShadow(fontRenderer, i.translateKey("gui.no_minecraft.label.body.2"), width / 2 - 170, (height / 4 - 60) + 60 + 18, 0xdedede);
-        drawStringShadow(fontRenderer, i.translateKey("gui.no_minecraft.label.body.3"), width / 2 - 170, (height / 4 - 60) + 60 + 27, 0xdedede);
-        drawStringShadow(fontRenderer, i.translateKey("gui.no_minecraft.label.body.4"), width / 2 - 170, (height / 4 - 60) + 60 + 45, 0xdedede);
-        drawStringShadow(fontRenderer, i.translateKey("gui.no_minecraft.label.body.5"), width / 2 - 170, (height / 4 - 60) + 60 + 54, 0xdedede);
+        drawStringCenteredShadow(this.fontRenderer, i.translateKey("gui.no_minecraft.label.title"), this.width / 2, (this.height / 4 - 60) + 20, 0xffff60);
+        drawStringShadow(this.fontRenderer, i.translateKey("gui.no_minecraft.label.body.1"), this.width / 2 - 170, (this.height / 4 - 60) + 60, 0xdedede);
+        drawStringShadow(this.fontRenderer, i.translateKey("gui.no_minecraft.label.body.2"), this.width / 2 - 170, (this.height / 4 - 60) + 60 + 18, 0xdedede);
+        drawStringShadow(this.fontRenderer, i.translateKey("gui.no_minecraft.label.body.3"), this.width / 2 - 170, (this.height / 4 - 60) + 60 + 27, 0xdedede);
+        drawStringShadow(this.fontRenderer, i.translateKey("gui.no_minecraft.label.body.4"), this.width / 2 - 170, (this.height / 4 - 60) + 60 + 45, 0xdedede);
+        drawStringShadow(this.fontRenderer, i.translateKey("gui.no_minecraft.label.body.5"), this.width / 2 - 170, (this.height / 4 - 60) + 60 + 54, 0xdedede);
         super.render(mx, my, partialTick);
     }
+
     @Override
-    protected void buttonClicked(@NotNull ButtonElement button)
-    {
-        if(!button.enabled)
-        {
+    protected void buttonClicked(@NotNull ButtonElement button) {
+        if (!button.enabled) {
             return;
         }
-        if(button.id == 0)
-        {
-            mc.shutdown();
+        if (button.id == 0) {
+            this.mc.shutdown();
         }
         if (button.id == 1) {
             UrlHelper.openURL("https://www.betterthanadventure.net/installation-guide/");
@@ -59,44 +56,44 @@ public class ScreenMissingMinecraft extends Screen {
             UrlHelper.openURL("https://betterthanadventure.net/discord");
         }
     }
+
     @Override
-    public void tick(){
-        ticks += 30;
+    public void tick() {
+        this.ticks += 30;
     }
 
-    public void drawBackground(float partialTick)
-    {
-        GL11.glDisable(GL11.GL_LIGHTING);
+    public void drawBackground(float partialTick) {
+        GLRenderer.globalSetLightEnabled(false);
         GL11.glDisable(GL11.GL_FOG);
 
-        Tessellator tessellator = Tessellator.instance;
-        mc.textureManager.loadTexture("/assets/minecraft/textures/block/cobbled_netherrack_mossy.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glEnable(GL11.GL_BLEND);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/block/cobbled_netherrack_mossy.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.enableState(State.BLEND);
 
         // Draw mossy netherrack first
         float f = 32F;
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0x404040);
-        tessellator.addVertexWithUV(0.0D, height, 0.0D, 0.0D, (float)height / f);
-        tessellator.addVertexWithUV(width, height, 0.0D, (float)width / f, (float)height / f);
-        tessellator.addVertexWithUV(width, 0.0D, 0.0D, (float)width / f, 0);
+        tessellator.setColorOpaque1i(0x404040);
+        tessellator.addVertexWithUV(0.0D, this.height, 0.0D, 0.0D, (float) this.height / f);
+        tessellator.addVertexWithUV(this.width, this.height, 0.0D, (float) this.width / f, (float) this.height / f);
+        tessellator.addVertexWithUV(this.width, 0.0D, 0.0D, (float) this.width / f, 0);
         tessellator.addVertexWithUV(0.0D, 0.0D, 0.0D, 0.0D, 0);
         tessellator.draw();
 
-        mc.textureManager.loadTexture("/assets/minecraft/textures/block/dirt.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0f);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/block/dirt.png").bind();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0f);
 
         // Then Draw dirt texture
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_F(64/255f, 64/255f, 64/255f, MathHelper.clamp(1f - ((float)ticks + partialTick)/80000f, 0f, 1f)); // Fade from dirt texture to mossy netherrack in the span of 66.6 minutes :)
-        tessellator.addVertexWithUV(0.0D, height, 0.0D, 0.0D, (float)height / f);
-        tessellator.addVertexWithUV(width, height, 0.0D, (float)width / f, (float)height / f);
-        tessellator.addVertexWithUV(width, 0.0D, 0.0D, (float)width / f, 0);
+        tessellator.setColor4f(64 / 255f, 64 / 255f, 64 / 255f, MathHelper.clamp(1f - ((float) this.ticks + partialTick) / 80000f, 0f, 1f)); // Fade from dirt texture to mossy netherrack in the span of 66.6 minutes :)
+        tessellator.addVertexWithUV(0.0D, this.height, 0.0D, 0.0D, (float) this.height / f);
+        tessellator.addVertexWithUV(this.width, this.height, 0.0D, (float) this.width / f, (float) this.height / f);
+        tessellator.addVertexWithUV(this.width, 0.0D, 0.0D, (float) this.width / f, 0);
         tessellator.addVertexWithUV(0.0D, 0.0D, 0.0D, 0.0D, 0);
         tessellator.draw();
 
         // Then gradient
-        drawGradientRect(0, 0, width, height, 0x22402020, 0xff501010);
+        drawGradientRect(0, 0, this.width, this.height, 0x22402020, 0xff501010);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/GuidebookPage.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/GuidebookPage.java
index 439660536..4560d6fa7 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/GuidebookPage.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/GuidebookPage.java
@@ -3,6 +3,7 @@ package net.minecraft.client.gui.guidebook;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.Color;
 import org.lwjgl.opengl.GL11;
@@ -22,9 +23,9 @@ public abstract class GuidebookPage
     }
 
     protected void renderBackground(TextureManager re, int x, int y) {
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         re.bindTexture(re.loadTexture("/assets/minecraft/textures/gui/container/guidebook/guidebook.png"));
-        drawTexturedModalRect(x, y, 0, 0, width, height);
+        drawTexturedModalRect(x, y, 0, 0, this.width, this.height);
     }
 
     protected abstract void renderForeground(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks);
@@ -38,28 +39,33 @@ public abstract class GuidebookPage
         renderForeground(re, sr, x, y, mouseX, mouseY, partialTicks);
     }
 
-    protected void renderOverlay(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) { };
+    protected void renderOverlay(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
+    }
 
-    public void onMouseDown(int x, int y, int mouseX, int mouseY, int button) { }
+    public void onMouseDown(int x, int y, int mouseX, int mouseY, int button) {
+    }
 
     public boolean keyTyped(char c, int key, int x, int y, int mouseX, int mouseY) {
         return false;
     }
 
-    public void onTick() { }
+    public void onTick() {
+    }
 
-    public void onBecomeVisible() { }
+    public void onBecomeVisible() {
+    }
 
-    public void onStopBeingVisible() { }
+    public void onStopBeingVisible() {
+    }
 
 
-    public void drawSlot(int x, int y, int argb){
+    public void drawSlot(int x, int y, int argb) {
 
         float a = Color.alphaFromInt(argb) / 255F;
         float r = Color.redFromInt(argb) / 255F;
         float g = Color.greenFromInt(argb) / 255F;
         float b = Color.blueFromInt(argb) / 255F;
-        GL11.glColor4f(r,g,b,a);
+        GLRenderer.setColor4f(r, g, b, a);
         drawGuiIcon(x, y, 18, 18, TextureRegistry.getTexture("minecraft:gui/screen/guidebook/slot"));
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/GuidebookSections.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/GuidebookSections.java
index 133124187..65141c59d 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/GuidebookSections.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/GuidebookSections.java
@@ -10,6 +10,7 @@ import net.minecraft.client.gui.guidebook.smelting.GuidebookSectionSmelting;
 import net.minecraft.client.gui.guidebook.trommeling.GuidebookSectionTrommel;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.item.ItemStack;
+import org.jetbrains.annotations.NotNull;
 
 import java.util.ArrayList;
 import java.util.Collections;
@@ -19,14 +20,14 @@ public abstract class GuidebookSections {
     private static boolean initialized = false;
     private static List<GuidebookSection> sectionList = new ArrayList<>();
 
-    public static GuidebookSection COVER;
-    public static GuidebookSection INDEX;
-    public static GuidebookSection SEARCH;
-    public static GuidebookSection MOB;
-    public static GuidebookSection CRAFTING;
-    public static GuidebookSection FURNACE;
-    public static GuidebookSection BLAST_FURNACE;
-    public static GuidebookSection TROMMEL;
+    public static GuidebookSectionCover COVER;
+    public static GuidebookSectionIndex INDEX;
+    public static GuidebookSectionSearch SEARCH;
+    public static GuidebookSectionMob MOB;
+    public static GuidebookSectionCrafting CRAFTING;
+    public static GuidebookSectionSmelting FURNACE;
+    public static GuidebookSectionBlastSmelting BLAST_FURNACE;
+    public static GuidebookSectionTrommel TROMMEL;
 
     public static void init() {
         if (initialized) return;
@@ -42,7 +43,7 @@ public abstract class GuidebookSections {
         MOB = register(new GuidebookSectionMob());
     }
 
-    public static GuidebookSection register(GuidebookSection section) {
+    public static <T extends GuidebookSection> @NotNull T register(@NotNull T section) {
         sectionList.add(section);
 
         return section;
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/ScreenGuidebook.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/ScreenGuidebook.java
index b617c7e2c..cfea9c8e4 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/ScreenGuidebook.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/ScreenGuidebook.java
@@ -8,12 +8,13 @@ import net.minecraft.client.gui.guidebook.search.GuidebookPageSearch;
 import net.minecraft.client.gui.guidebook.search.GuidebookSectionSearch;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.render.Lighting;
-import net.minecraft.client.render.OpenGLHelper;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.entity.EntityRendererItem;
 import net.minecraft.client.render.font.FontRenderer;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.achievement.Achievements;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.lang.I18n;
@@ -22,8 +23,6 @@ import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 
 import java.util.List;
 import java.util.Random;
@@ -32,6 +31,7 @@ public class ScreenGuidebook
     extends Screen {
     private static final int TABS_PER_SIDE = 8;
     private static GuidebookPageManager guidebookPageManager = null;
+
     public static GuidebookPageManager getPageManager() {
         GuidebookSections.init();
         if (guidebookPageManager == null) guidebookPageManager = new GuidebookPageManager();
@@ -56,7 +56,7 @@ public class ScreenGuidebook
     @Override
     public void init() {
         super.init();
-        mc.thePlayer.triggerAchievement(Achievements.OPEN_GUIDEBOOK);
+        this.mc.thePlayer.triggerAchievement(Achievements.OPEN_GUIDEBOOK);
 
         initTabList();
         Keyboard.enableRepeatEvents(true);
@@ -71,11 +71,11 @@ public class ScreenGuidebook
     }
 
     private void initTabList() {
-        tabs = new Tab[TABS_PER_SIDE * 2];
+        this.tabs = new Tab[TABS_PER_SIDE * 2];
         List<GuidebookSection> sections = GuidebookSections.getSectionList();
         int numTabs = sections.size();
-        for (int i = 0; i < tabs.length && i < numTabs; i++) {
-            tabs[i] = new Tab(sections.get(i));
+        for (int i = 0; i < this.tabs.length && i < numTabs; i++) {
+            this.tabs[i] = new Tab(sections.get(i));
         }
 
         updateTabList();
@@ -84,54 +84,54 @@ public class ScreenGuidebook
     private void updateTabList() {
         boolean hasLeftPage = guidebookPageManager.getLeftPage() != null;
         boolean hasRightPage = guidebookPageManager.getRightPage() != null;
-        int left = width / 2 - xSize / (hasLeftPage && hasRightPage ? 2 : 4);
-        int right = width / 2 + xSize / (hasLeftPage && hasRightPage ? 2 : 4);
-        int top = height / 2 - ySize / 2;
+        int left = this.width / 2 - this.xSize / (hasLeftPage && hasRightPage ? 2 : 4);
+        int right = this.width / 2 + this.xSize / (hasLeftPage && hasRightPage ? 2 : 4);
+        int top = this.height / 2 - this.ySize / 2;
 
         List<GuidebookSection> sections = GuidebookSections.getSectionList();
         int numTabs = sections.size();
 
         // Left tabs
         for (int i = 0; i < TABS_PER_SIDE && i < numTabs; i++) {
-            tabs[i].setX(left - Tab.WIDTH);
-            tabs[i].setY(top + i * (Tab.HEIGHT + 2) + 7);
-            tabs[i].setFlipped(false);
-            if (sections.get(i) instanceof SearchableGuidebookSection && GuidebookPageManager.searchQuery != null) {
-                List<GuidebookPage> search = ((SearchableGuidebookSection) sections.get(i)).searchPages(GuidebookPageManager.searchQuery);
-                if (search.size() > 0) {
-                    tabs[i].setActive(search.get(0) == guidebookPageManager.getLeftPage() || search.get(0) == guidebookPageManager.getRightPage());
+            this.tabs[i].setX(left - Tab.WIDTH);
+            this.tabs[i].setY(top + i * (Tab.HEIGHT + 2) + 7);
+            this.tabs[i].setFlipped(false);
+            if (sections.get(i) instanceof SearchableGuidebookSection searchableGuidebookSection && GuidebookPageManager.searchQuery != null) {
+                List<GuidebookPage> search = searchableGuidebookSection.searchPages(GuidebookPageManager.searchQuery);
+                if (!search.isEmpty()) {
+                    this.tabs[i].setActive(search.get(0) == guidebookPageManager.getLeftPage() || search.get(0) == guidebookPageManager.getRightPage());
                 } else {
-                    tabs[i].setActive(false);
+                    this.tabs[i].setActive(false);
                 }
             } else {
                 List<GuidebookPage> pages = sections.get(i).getPages();
-                if (pages.size() > 0) {
-                    tabs[i].setActive((pages.get(0) == guidebookPageManager.getLeftPage()) || (pages.get(0) == guidebookPageManager.getRightPage()));
+                if (!pages.isEmpty()) {
+                    this.tabs[i].setActive((pages.get(0) == guidebookPageManager.getLeftPage()) || (pages.get(0) == guidebookPageManager.getRightPage()));
                 } else {
-                    tabs[i].setActive(false);
+                    this.tabs[i].setActive(false);
                 }
             }
         }
 
         // Right tabs
         for (int i = TABS_PER_SIDE; i < TABS_PER_SIDE * 2 && i < numTabs; i++) {
-            tabs[i].setX(right);
-            tabs[i].setY(top + (i - TABS_PER_SIDE) * (Tab.HEIGHT + 2) + 7);
-            tabs[i].setFlipped(true);
-            if (sections.get(i).getPages().size() > 0) {
-                if (sections.get(i) instanceof SearchableGuidebookSection && GuidebookPageManager.searchQuery != null) {
-                    List<GuidebookPage> search = ((SearchableGuidebookSection) sections.get(i)).searchPages(GuidebookPageManager.searchQuery);
-                    if (search.size() > 0) {
-                        tabs[i].setActive(search.get(0) == guidebookPageManager.getLeftPage() || search.get(0) == guidebookPageManager.getRightPage());
+            this.tabs[i].setX(right);
+            this.tabs[i].setY(top + (i - TABS_PER_SIDE) * (Tab.HEIGHT + 2) + 7);
+            this.tabs[i].setFlipped(true);
+            if (!sections.get(i).getPages().isEmpty()) {
+                if (sections.get(i) instanceof SearchableGuidebookSection searchableGuidebookSection && GuidebookPageManager.searchQuery != null) {
+                    List<GuidebookPage> search = searchableGuidebookSection.searchPages(GuidebookPageManager.searchQuery);
+                    if (!search.isEmpty()) {
+                        this.tabs[i].setActive(search.get(0) == guidebookPageManager.getLeftPage() || search.get(0) == guidebookPageManager.getRightPage());
                     } else {
-                        tabs[i].setActive(false);
+                        this.tabs[i].setActive(false);
                     }
                 } else {
                     List<GuidebookPage> pages = sections.get(i).getPages();
-                    if (pages.size() > 0) {
-                        tabs[i].setActive((pages.get(0) == guidebookPageManager.getLeftPage()) || (pages.get(0) == guidebookPageManager.getRightPage()));
+                    if (!pages.isEmpty()) {
+                        this.tabs[i].setActive((pages.get(0) == guidebookPageManager.getLeftPage()) || (pages.get(0) == guidebookPageManager.getRightPage()));
                     } else {
-                        tabs[i].setActive(false);
+                        this.tabs[i].setActive(false);
                     }
                 }
             }
@@ -145,7 +145,7 @@ public class ScreenGuidebook
 
     @Override
     public void render(int mx, int my, float renderPartialTicks) {
-        lastPage = guidebookPageManager.getLeftPage();
+        this.lastPage = guidebookPageManager.getLeftPage();
         scroll(Mouse.getDWheel());
 
         int xOffset = 0;
@@ -160,7 +160,7 @@ public class ScreenGuidebook
         drawTabs(mx, my);
         drawCurrentPages(mx, my, xOffset, renderPartialTicks);
         drawHeaders(xOffset);
-        drawCurrentPageOverlays(mx, my,xOffset,renderPartialTicks);
+        drawCurrentPageOverlays(mx, my, xOffset, renderPartialTicks);
         drawPageTurnIndicator(mx, my, xOffset);
         drawTooltip(mx, my);
     }
@@ -207,10 +207,10 @@ public class ScreenGuidebook
 
         int size = 24;
 
-        int top = height / 2 - ySize / 2;
-        int bottom = height / 2 + ySize / 2;
-        int left = width / 2 - xSize / 2 + xOffset;
-        int right = width / 2 + xSize / 2 + xOffset;
+        int top = this.height / 2 - this.ySize / 2;
+        int bottom = this.height / 2 + this.ySize / 2;
+        int left = this.width / 2 - this.xSize / 2 + xOffset;
+        int right = this.width / 2 + this.xSize / 2 + xOffset;
 
         if (guidebookPageManager.getLeftPage() != null && guidebookPageManager.hasPreviousPage()) {
             if (mx >= left && mx <= left + size && my >= top && my <= top + size) {
@@ -241,13 +241,13 @@ public class ScreenGuidebook
             }
         }
 
-        if (guidebookPageManager.getLeftPage() != null && mx > left && mx < left + xSize / 2 && my > top && my < bottom) {
+        if (guidebookPageManager.getLeftPage() != null && mx > left && mx < left + this.xSize / 2 && my > top && my < bottom) {
             guidebookPageManager.getLeftPage().onMouseDown(left, top, mx, my, buttonNum);
             updateTabList();
             return;
         }
-        if (guidebookPageManager.getRightPage() != null && mx > left + xSize / 2 && mx < right && my > top && my < bottom) {
-            guidebookPageManager.getRightPage().onMouseDown(left + xSize / 2, top, mx, my, buttonNum);
+        if (guidebookPageManager.getRightPage() != null && mx > left + this.xSize / 2 && mx < right && my > top && my < bottom) {
+            guidebookPageManager.getRightPage().onMouseDown(left + this.xSize / 2, top, mx, my, buttonNum);
             updateTabList();
             return;
         }
@@ -258,10 +258,10 @@ public class ScreenGuidebook
     @Override
     public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
         if (eventKey == Keyboard.KEY_ESCAPE) {
-            mc.displayScreen(getParentScreen());
+            this.mc.displayScreen(getParentScreen());
             return;
         }
-        if(eventKey != Keyboard.KEY_BACK) super.keyPressed(eventCharacter, eventKey, mx, my);
+        if (eventKey != Keyboard.KEY_BACK) super.keyPressed(eventCharacter, eventKey, mx, my);
 
         int xOffset = 0;
         if (guidebookPageManager.getLeftPage() == null) {
@@ -271,8 +271,8 @@ public class ScreenGuidebook
             xOffset = 158 / 2;
         }
 
-        int top = height / 2 - ySize / 2;
-        int left = width / 2 - xSize / 2 + xOffset;
+        int top = this.height / 2 - this.ySize / 2;
+        int left = this.width / 2 - this.xSize / 2 + xOffset;
 
         if (allowArrowKeyNavigation) {
             if (eventKey == Keyboard.KEY_LEFT) {
@@ -291,17 +291,17 @@ public class ScreenGuidebook
             updateTabList();
         }
         if (guidebookPageManager.getRightPage() != null) {
-            consumedInput |= guidebookPageManager.getRightPage().keyTyped(eventCharacter, eventKey, left + xSize / 2, top, mx, my);
+            consumedInput |= guidebookPageManager.getRightPage().keyTyped(eventCharacter, eventKey, left + this.xSize / 2, top, mx, my);
             updateTabList();
         }
 
-        if (!consumedInput && mc.gameSettings.keyGuidebook.isKeyboardKey(eventKey)) { // If R pressed and not consumed by page exit guidebook
-            mc.displayScreen(getParentScreen());
+        if (!consumedInput && this.mc.gameSettings.keyGuidebook.isKeyboardKey(eventKey)) { // If R pressed and not consumed by page exit guidebook
+            this.mc.displayScreen(getParentScreen());
         }
     }
 
     private void handleTabClicks(int mouseX, int mouseY) {
-        for (Tab tab : tabs) {
+        for (Tab tab : this.tabs) {
             if (tab == null) return;
             if (tab.mouseOver(mouseX, mouseY)) {
                 guidebookPageManager.setCurrentPage(guidebookPageManager.getSectionIndex(tab.getSection()), true);
@@ -313,59 +313,59 @@ public class ScreenGuidebook
     }
 
     private void playPageSound() {
-        if (!canPlaySound || lastPage == guidebookPageManager.getLeftPage()) return;
-        canPlaySound = false;
+        if (!this.canPlaySound || this.lastPage == guidebookPageManager.getLeftPage()) return;
+        this.canPlaySound = false;
         Random r = new Random();
-        mc.sndManager.playSound("random.page", SoundCategory.GUI_SOUNDS, 0.8f, 0.9f + (r.nextFloat() - r.nextFloat()) * 0.1f);
+        this.mc.sndManager.playSound("random.page", SoundCategory.GUI_SOUNDS, 0.8f, 0.9f + (r.nextFloat() - r.nextFloat()) * 0.1f);
     }
 
-    public void guiSpecificControllerInput(@NotNull ControllerInput controller){
+    public void guiSpecificControllerInput(@NotNull ControllerInput controller) {
         super.guiSpecificControllerInput(controller);
-        if (controller.digitalPad.left.pressedThisFrame() || (controller.digitalPad.left.isPressed() && controller.digitalPad.left.getHoldTime() % 4 == 0)){
+        if (controller.digitalPad.left.pressedThisFrame() || (controller.digitalPad.left.isPressed() && controller.digitalPad.left.getHoldTime() % 4 == 0)) {
             guidebookPageManager.offsetPage(-2);
             updateTabList();
         }
-        if (controller.digitalPad.right.pressedThisFrame() || (controller.digitalPad.right.isPressed() && controller.digitalPad.right.getHoldTime() % 4 == 0)){
+        if (controller.digitalPad.right.pressedThisFrame() || (controller.digitalPad.right.isPressed() && controller.digitalPad.right.getHoldTime() % 4 == 0)) {
             guidebookPageManager.offsetPage(2);
             updateTabList();
         }
-        if (controller.buttonRightShoulder.pressedThisFrame()){
+        if (controller.buttonRightShoulder.pressedThisFrame()) {
             Tab t = getTab(guidebookPageManager.getCurrentSection(), true);
-            if (t != null){
+            if (t != null) {
                 int currentPage = guidebookPageManager.getPageIndex(guidebookPageManager.getLeftPage());
                 guidebookPageManager.setCurrentPage(guidebookPageManager.getSectionIndex(t.getSection()), true);
-                if (currentPage == guidebookPageManager.getPageIndex(guidebookPageManager.getLeftPage())){
+                if (currentPage == guidebookPageManager.getPageIndex(guidebookPageManager.getLeftPage())) {
                     guidebookPageManager.offsetPage(2);
                 }
                 updateTabList();
             }
         }
-        if (controller.buttonLeftShoulder.pressedThisFrame()){
+        if (controller.buttonLeftShoulder.pressedThisFrame()) {
             Tab t = getTab(guidebookPageManager.getCurrentSection(), false);
-            if (t != null){
+            if (t != null) {
                 int currentPage = guidebookPageManager.getPageIndex(guidebookPageManager.getLeftPage());
                 guidebookPageManager.setCurrentPage(guidebookPageManager.getSectionIndex(t.getSection()), true);
-                if (currentPage == guidebookPageManager.getPageIndex(guidebookPageManager.getLeftPage())){
+                if (currentPage == guidebookPageManager.getPageIndex(guidebookPageManager.getLeftPage())) {
                     guidebookPageManager.offsetPage(-2);
                 }
                 updateTabList();
             }
         }
         if (controller.buttonB.pressedThisFrame()) {
-            mc.displayScreen(getParentScreen());
+            this.mc.displayScreen(getParentScreen());
         }
     }
 
-    private Tab getTab(GuidebookSection section, boolean searchForward){
+    private Tab getTab(GuidebookSection section, boolean searchForward) {
         Tab tab = null;
         int index = -1;
-        for (int i = 0; i < tabs.length; i++) {
-            Tab t = tabs[i];
+        for (int i = 0; i < this.tabs.length; i++) {
+            Tab t = this.tabs[i];
             if (t == null) continue;
-            if (t.getSection() == section){
-                if (section instanceof GuidebookSectionSearch){
+            if (t.getSection() == section) {
+                if (section instanceof GuidebookSectionSearch) {
                     index = i + 1;
-                    tab = tabs[i + 1];
+                    tab = this.tabs[i + 1];
                 } else {
                     index = i;
                     tab = t;
@@ -374,9 +374,9 @@ public class ScreenGuidebook
             }
         }
         if (tab == null) return null;
-        for (int i = 1; i < tabs.length; i++) {
-            int searchDex = (tabs.length + index + (searchForward ? i : -i)) % tabs.length;
-            if (tabs[searchDex] != null) return tabs[searchDex];
+        for (int i = 1; i < this.tabs.length; i++) {
+            int searchDex = (this.tabs.length + index + (searchForward ? i : -i)) % this.tabs.length;
+            if (this.tabs[searchDex] != null) return this.tabs[searchDex];
         }
         return null;
     }
@@ -385,7 +385,7 @@ public class ScreenGuidebook
     public void tick() {
         super.tick();
 
-        canPlaySound = true;
+        this.canPlaySound = true;
 
         if (guidebookPageManager.getLeftPage() != null) {
             guidebookPageManager.getLeftPage().onTick();
@@ -398,89 +398,89 @@ public class ScreenGuidebook
     }
 
     private void drawTabs(int mouseX, int mouseY) {
-        for (Tab tab : tabs) {
+        for (Tab tab : this.tabs) {
             if (tab == null) break;
-            tab.render(mc.textureManager, mc.font, mouseX, mouseY);
+            tab.render(this.mc.textureManager, this.mc.font, mouseX, mouseY);
         }
     }
 
     private void drawTooltip(int mouseX, int mouseY) {
-        for (Tab tab : tabs) {
+        for (Tab tab : this.tabs) {
             if (tab == null) break;
             if (tab.mouseOver(mouseX, mouseY)) {
-                tab.renderTooltip(tooltip, mouseX, mouseY);
+                tab.renderTooltip(this.tooltip, mouseX, mouseY);
             }
         }
     }
 
     private void drawCurrentPages(int mouseX, int mouseY, int xOffset, float partialTicks) {
-        int top = height / 2 - ySize / 2;
-        int bottom = height / 2 + ySize / 2;
-        int left = width / 2 - xSize / 2 + xOffset;
-        int right = width / 2 + xSize / 2 + xOffset;
+        int top = this.height / 2 - this.ySize / 2;
+        int bottom = this.height / 2 + this.ySize / 2;
+        int left = this.width / 2 - this.xSize / 2 + xOffset;
+        int right = this.width / 2 + this.xSize / 2 + xOffset;
 
         GuidebookPage leftPage = guidebookPageManager.getLeftPage();
         GuidebookPage rightPage = guidebookPageManager.getRightPage();
 
         if (leftPage != null) {
-            leftPage.render(mc.textureManager, mc.font, left, top, mouseX, mouseY, partialTicks);
+            leftPage.render(this.mc.textureManager, this.mc.font, left, top, mouseX, mouseY, partialTicks);
         }
         if (rightPage != null) {
-            rightPage.render(mc.textureManager, mc.font, right - 158, top, mouseX, mouseY, partialTicks);
+            rightPage.render(this.mc.textureManager, this.mc.font, right - 158, top, mouseX, mouseY, partialTicks);
         }
     }
 
-    private void drawCurrentPageOverlays(int mouseX, int mouseY, int xOffset, float partialTicks){
-        int top = height / 2 - ySize / 2;
-        int bottom = height / 2 + ySize / 2;
-        int left = width / 2 - xSize / 2 + xOffset;
-        int right = width / 2 + xSize / 2 + xOffset;
+    private void drawCurrentPageOverlays(int mouseX, int mouseY, int xOffset, float partialTicks) {
+        int top = this.height / 2 - this.ySize / 2;
+        int bottom = this.height / 2 + this.ySize / 2;
+        int left = this.width / 2 - this.xSize / 2 + xOffset;
+        int right = this.width / 2 + this.xSize / 2 + xOffset;
 
         GuidebookPage leftPage = guidebookPageManager.getLeftPage();
         GuidebookPage rightPage = guidebookPageManager.getRightPage();
 
         if (leftPage != null) {
-            leftPage.renderOverlay(mc.textureManager, mc.font,left,top,mouseX,mouseY,partialTicks);
+            leftPage.renderOverlay(this.mc.textureManager, this.mc.font, left, top, mouseX, mouseY, partialTicks);
         }
         if (rightPage != null) {
-            rightPage.renderOverlay(mc.textureManager, mc.font,right - 158,top,mouseX,mouseY,partialTicks);
+            rightPage.renderOverlay(this.mc.textureManager, this.mc.font, right - 158, top, mouseX, mouseY, partialTicks);
         }
     }
 
     private void drawHeaders(int xOffset) {
-        int bottom = height / 2 + ySize / 2;
-        int left = width / 2 - xSize / 2 + xOffset;
-        int right = width / 2 + xSize / 2 + xOffset;
+        int bottom = this.height / 2 + this.ySize / 2;
+        int left = this.width / 2 - this.xSize / 2 + xOffset;
+        int right = this.width / 2 + this.xSize / 2 + xOffset;
 
         GuidebookPage leftPage = guidebookPageManager.getLeftPage();
         GuidebookPage rightPage = guidebookPageManager.getRightPage();
 
         //find a way how to display the total number of pages properly maybe
         if (leftPage != null && leftPage.drawHeaders()) {
-            drawStringNoShadow(fontRenderer, String.valueOf(guidebookPageManager.getPageIndex(leftPage)) /*+ "/" + guidebookPageManager.getNumPages()*/, left + 12, bottom - 20, 0xFF000000);
-            drawStringCenteredNoShadow(fontRenderer, I18n.getInstance().translateKey(guidebookPageManager.getLeftPage().getSection().getTranslationKey()), left + 158 / 2, bottom - 20, 0xFF808080);
+            drawStringNoShadow(this.fontRenderer, String.valueOf(guidebookPageManager.getPageIndex(leftPage)) /*+ "/" + guidebookPageManager.getNumPages()*/, left + 12, bottom - 20, 0xFF000000);
+            drawStringCenteredNoShadow(this.fontRenderer, I18n.getInstance().translateKey(guidebookPageManager.getLeftPage().getSection().getTranslationKey()), left + 158 / 2, bottom - 20, 0xFF808080);
         }
         if (rightPage != null && rightPage.drawHeaders()) {
             String str = String.valueOf(guidebookPageManager.getPageIndex(rightPage)); /*+ "/" + guidebookPageManager.getNumPages();*/
-            drawStringNoShadow(fontRenderer, str, right - 12 - MathHelper.ceil(fontRenderer.stringWidthDouble(str)), bottom - 20, 0xFF000000);
-            drawStringCenteredNoShadow(fontRenderer, I18n.getInstance().translateKey(guidebookPageManager.getRightPage().getSection().getTranslationKey()), right - 158 / 2, bottom - 20, 0xFF808080);
+            drawStringNoShadow(this.fontRenderer, str, right - 12 - MathHelper.ceil(this.fontRenderer.stringWidthDouble(str)), bottom - 20, 0xFF000000);
+            drawStringCenteredNoShadow(this.fontRenderer, I18n.getInstance().translateKey(guidebookPageManager.getRightPage().getSection().getTranslationKey()), right - 158 / 2, bottom - 20, 0xFF808080);
         }
     }
 
     private void drawPageTurnIndicator(int mouseX, int mouseY, int xOffset) {
         int size = 24;
 
-        int top = height / 2 - ySize / 2;
-        int bottom = height / 2 + ySize / 2;
-        int left = width / 2 - xSize / 2 + xOffset;
-        int right = width / 2 + xSize / 2 + xOffset;
+        int top = this.height / 2 - this.ySize / 2;
+        int bottom = this.height / 2 + this.ySize / 2;
+        int left = this.width / 2 - this.xSize / 2 + xOffset;
+        int right = this.width / 2 + this.xSize / 2 + xOffset;
 
-        mc.textureManager.bindTexture(mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/guidebook/guidebook.png"));
+        this.mc.textureManager.bindTexture(this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/container/guidebook/guidebook.png"));
 
-        GL11.glColor4f(1, 1, 1, 1);
+        GLRenderer.setColor4f(1, 1, 1, 1);
         if (guidebookPageManager.getLeftPage() != null && guidebookPageManager.hasPreviousPage()) {
             if (mouseX >= left && mouseX <= left + size && mouseY >= top && mouseY <= top + size) {
-                drawTexturedModalRect(left, top, 24 * 0, 220, 24, 24);
+                drawTexturedModalRect(left, top, 0, 220, 24, 24);
             }
             if (mouseX >= left && mouseX <= left + size && mouseY >= bottom - size && mouseY <= bottom) {
                 drawTexturedModalRect(left, bottom - size, 24 * 2, 220, 24, 24);
@@ -488,7 +488,7 @@ public class ScreenGuidebook
         }
         if (guidebookPageManager.getRightPage() != null && guidebookPageManager.hasNextPage()) {
             if (mouseX >= right - size && mouseX <= right && mouseY >= top && mouseY <= top + size) {
-                drawTexturedModalRect(right - size, top, 24 * 1, 220, 24, 24);
+                drawTexturedModalRect(right - size, top, 24, 220, 24, 24);
             }
             if (mouseX >= right - size && mouseX <= right && mouseY >= bottom - size && mouseY <= bottom) {
                 drawTexturedModalRect(right - size, bottom - size, 24 * 3, 220, 24, 24);
@@ -498,7 +498,7 @@ public class ScreenGuidebook
 
     private static class Tab
         extends Gui {
-        private static EntityRendererItem itemRenderer = new EntityRendererItem();
+        private static final EntityRendererItem itemRenderer = new EntityRendererItem();
         private static final int WIDTH = 36;
         private static final int HEIGHT = 24;
         private final GuidebookSection section;
@@ -512,7 +512,7 @@ public class ScreenGuidebook
         }
 
         public GuidebookSection getSection() {
-            return section;
+            return this.section;
         }
 
         public void setX(int x) {
@@ -537,54 +537,54 @@ public class ScreenGuidebook
             re.bindTexture(re.loadTexture("/assets/minecraft/textures/gui/container/guidebook/guidebook.png"));
 
             int xo = 16;
-            if (mouseOver || active) {
+            if (mouseOver || this.active) {
                 xo = 0;
             }
-            if (flipped) {
+            if (this.flipped) {
                 xo = -xo;
             }
 
             int u = 158;
             int v = 0;
-            if (flipped) v = 48;
+            if (this.flipped) v = 48;
 
-            int bgColor = section.getBackgroundColor();
-            int fgColor = section.getForegroundColor();
-            ItemStack icon = section.getTabIcon();
+            int bgColor = this.section.getBackgroundColor();
+            int fgColor = this.section.getForegroundColor();
+            ItemStack icon = this.section.getTabIcon();
 
-            OpenGLHelper.glColor1i(0xFF000000 | bgColor);
-            drawTexturedModalRect(x + xo, y, u, v, WIDTH, HEIGHT);
-            OpenGLHelper.glColor1i(0xFF000000 | fgColor);
-            drawTexturedModalRect(x + xo, y, u, v + HEIGHT, WIDTH, HEIGHT);
+            GLRenderer.setColor1i(0xFF000000 | bgColor);
+            drawTexturedModalRect(this.x + xo, this.y, u, v, WIDTH, HEIGHT);
+            GLRenderer.setColor1i(0xFF000000 | fgColor);
+            drawTexturedModalRect(this.x + xo, this.y, u, v + HEIGHT, WIDTH, HEIGHT);
 
             if (icon != null) {
-                int iconOffset = flipped ? 4 : 12 + 4;
+                int iconOffset = this.flipped ? 4 : 12 + 4;
 
-                GL11.glDepthMask(true);
+                GLRenderer.setDepthMask(true);
                 Lighting.enableInventoryLight();
-                GL11.glColor4f(1, 1, 1, 1);
-                GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+                GLRenderer.setColor4f(1, 1, 1, 1);
+//                GL11.glEnable(GL12.GL_RESCALE_NORMAL);
 
-                GL11.glEnable(GL11.GL_DEPTH_TEST);
-//                ItemModelDispatcher.getInstance().getDispatch(icon).renderItemIntoGui(Tessellator.instance, fr, re, icon, x + iconOffset + xo, y + 4, 1.0f);
-                ItemModelDispatcher.getInstance().getDispatch(icon).renderGui(Tessellator.instance, null, icon, x + iconOffset + xo, y + 4, 1.0f, 1f, 1f);
-                GL11.glDisable(GL11.GL_DEPTH_TEST);
+                GLRenderer.enableState(State.DEPTH_TEST);
+//                ItemModelDispatcher.getInstance().getDispatch(icon).renderItemIntoGui(GLRenderer.getTessellator(), fr, re, icon, x + iconOffset + xo, y + 4, 1.0f);
+                ItemModelDispatcher.getInstance().getDispatch(icon).renderGui(GLRenderer.getTessellator(), null, icon, this.x + iconOffset + xo, this.y + 4, LightmapHelper.getLightmapCoord(15, 15), 1f);
+                GLRenderer.disableState(State.DEPTH_TEST);
 
-                GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+//                GL11.glDisable(GL12.GL_RESCALE_NORMAL);
                 Lighting.disable();
-                GL11.glDisable(GL11.GL_LIGHTING);
-                GL11.glDisable(GL11.GL_DEPTH_TEST);
+                GLRenderer.globalSetLightEnabled(false);
+                GLRenderer.disableState(State.DEPTH_TEST);
             }
         }
 
         public void renderTooltip(TooltipElement tooltip, int mouseX, int mouseY) {
             if (mouseOver(mouseX, mouseY)) {
-                tooltip.render(I18n.getInstance().translateKey(section.getTranslationKey()), mouseX, mouseY, 8, -8);
+                tooltip.render(I18n.getInstance().translateKey(this.section.getTranslationKey()), mouseX, mouseY, 8, -8);
             }
         }
 
         public boolean mouseOver(int mouseX, int mouseY) {
-            return mouseX >= x && mouseX <= x + WIDTH && mouseY >= y && mouseY <= y + HEIGHT;
+            return mouseX >= this.x && mouseX <= this.x + WIDTH && mouseY >= this.y && mouseY <= this.y + HEIGHT;
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/crafting/RecipePageCrafting.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/crafting/RecipePageCrafting.java
index 9de269fac..08887a0c9 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/crafting/RecipePageCrafting.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/crafting/RecipePageCrafting.java
@@ -23,7 +23,7 @@ import net.minecraft.client.gui.guidebook.search.GuidebookPageSearch;
 import net.minecraft.client.option.enums.DescriptionPromptEnum;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.core.achievement.Achievements;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.data.registry.recipe.RecipeEntryBase;
 import net.minecraft.core.data.registry.recipe.SearchQuery;
 import net.minecraft.core.data.registry.recipe.entry.RecipeEntryCrafting;
@@ -37,12 +37,9 @@ import net.minecraft.core.data.registry.recipe.entry.RecipeEntryMapDuplication;
 import net.minecraft.core.data.registry.recipe.entry.RecipeEntryRepairable;
 import net.minecraft.core.data.registry.recipe.entry.RecipeEntryScrap;
 import net.minecraft.core.data.registry.recipe.entry.RecipeEntryUndyeing;
-import net.minecraft.core.entity.player.Player;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.slot.Slot;
 import net.minecraft.client.gui.guidebook.SlotGuidebook;
-import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.HashMap;
@@ -50,11 +47,11 @@ import java.util.List;
 import java.util.Map;
 
 public class RecipePageCrafting
-    extends RecipePage<RecipeEntryCrafting<?,?>> {
+    extends RecipePage<RecipeEntryCrafting<?, ?>> {
     public static final int RECIPES_PER_PAGE = 3;
 
     public List<SlotGuidebook> slots;
-    public Map<RecipeEntryCrafting<?,?>,List<SlotGuidebook>> map;
+    public Map<RecipeEntryCrafting<?, ?>, List<SlotGuidebook>> map;
 
     public static Map<Class<? extends RecipeEntryCrafting<?, ?>>, RecipeDisplayAdapter<?>> recipeToDisplayAdapterMap = new HashMap<>();
 
@@ -76,22 +73,22 @@ public class RecipePageCrafting
     private static final Minecraft mc = Minecraft.getMinecraft();
     private static long ticks = 0;
 
-    public RecipePageCrafting(GuidebookSection section, List<RecipeEntryCrafting<?,?>> recipes) {
+    public RecipePageCrafting(GuidebookSection section, List<RecipeEntryCrafting<?, ?>> recipes) {
         super(section);
         this.recipes = recipes;
         this.slots = new ArrayList<>();
         this.map = new HashMap<>();
-        tooltipElement = new TooltipElement(mc);
-        itemElement = new ItemElement(mc);
+        this.tooltipElement = new TooltipElement(mc);
+        this.itemElement = new ItemElement(mc);
         int recipeAmount = 0;
         int xOffset = 32;
         int yOffset = 12;
-        for (RecipeEntryCrafting<?,?> recipe : recipes) {
+        for (RecipeEntryCrafting<?, ?> recipe : recipes) {
             if (recipeToDisplayAdapterMap.containsKey(recipe.getClass())) {
                 RecipeDisplayAdapter adapter = recipeToDisplayAdapterMap.get(recipe.getClass());
                 List<SlotGuidebook> recipeSlots = adapter.getSlots(recipe, recipeAmount, xOffset, yOffset);
-                map.put(recipe,recipeSlots);
-                slots.addAll(recipeSlots);
+                this.map.put(recipe, recipeSlots);
+                this.slots.addAll(recipeSlots);
                 yOffset += 10;
                 recipeAmount++;
             }
@@ -102,10 +99,10 @@ public class RecipePageCrafting
     @Override
     public void onTick() {
         ticks++;
-        for (SlotGuidebook slot : slots) {
-            if(ticks > 20) {
+        for (SlotGuidebook slot : this.slots) {
+            if (ticks > 20) {
                 slot.showRandomItem();
-                if(slots.get(slots.size()-1) == slot){
+                if (this.slots.get(this.slots.size() - 1) == slot) {
                     ticks = 0;
                 }
             }
@@ -114,36 +111,35 @@ public class RecipePageCrafting
 
     @Override
     protected void renderForeground(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
-        if(recipes.isEmpty()){
-            drawStringCenteredNoShadow(sr, I18n.getInstance().translateKey("guidebook.section.search.error.no_recipes"), x+width/2,y+height/2,0xFF808080);
+        if (this.recipes.isEmpty()) {
+            drawStringCenteredNoShadow(sr, I18n.getInstance().translateKey("guidebook.section.search.error.no_recipes"), x + this.width / 2, y + this.height / 2, 0xFF808080);
         }
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            if(slot.item != null){
-                if(!slot.isOutput) slot.item.stackSize = 1;
+        for (SlotGuidebook slot : this.slots) {
+            if (slot.item != null) {
+                if (!slot.isOutput) slot.item.stackSize = 1;
             }
-            drawSlot(x+slot.x -1,y+slot.y -1,0xFFFFFFFF);
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            itemElement.render(slot.getItemStack(),x+slot.x,y+slot.y,mouseOverSlot == slot,slot);
+            drawSlot(x + slot.x - 1, y + slot.y - 1, 0xFFFFFFFF);
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            this.itemElement.render(slot.getItemStack(), x + slot.x, y + slot.y, mouseOverSlot == slot, slot);
         }
     }
 
-    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY)
-    {
-        return mouseX >= x+slot.x - 1 && mouseX < x+slot.x + 16 + 1 && mouseY >= y+slot.y - 1 && mouseY < y+slot.y + 16 + 1;
+    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY) {
+        return mouseX >= x + slot.x - 1 && mouseX < x + slot.x + 16 + 1 && mouseY >= y + slot.y - 1 && mouseY < y + slot.y + 16 + 1;
     }
 
     @Override
     public boolean keyTyped(char c, int key, int x, int y, int mouseX, int mouseY) {
         super.keyTyped(c, key, x, y, mouseX, mouseY);
-        if(mc.gameSettings.keyShowRecipe.isKeyboardKey(key)){
-            SlotGuidebook hoveringSlot= null;
-            for (SlotGuidebook slot : slots) {
-                if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) hoveringSlot = slot;
+        if (mc.gameSettings.keyShowRecipe.isKeyboardKey(key)) {
+            SlotGuidebook hoveringSlot = null;
+            for (SlotGuidebook slot : this.slots) {
+                if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) hoveringSlot = slot;
             }
-            if(hoveringSlot != null){
-                if(hoveringSlot.hasItem()){
-                    String query = "r:"+hoveringSlot.getItemStack().getDisplayName()+"!";
+            if (hoveringSlot != null) {
+                if (hoveringSlot.hasItem()) {
+                    String query = "r:" + hoveringSlot.getItemStack().getDisplayName() + "!";
                     GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
                     GuidebookPageSearch.searchField.setText(query);
                     ScreenGuidebook.getPageManager().updatePages();
@@ -152,11 +148,11 @@ public class RecipePageCrafting
                 }
             }
         } else if (mc.gameSettings.keyShowUsage.isKeyboardKey(key)) {
-            SlotGuidebook hoveringSlot= null;
-            for (SlotGuidebook slot : slots) {
-                if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) hoveringSlot = slot;
+            SlotGuidebook hoveringSlot = null;
+            for (SlotGuidebook slot : this.slots) {
+                if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) hoveringSlot = slot;
             }
-            if(hoveringSlot != null) {
+            if (hoveringSlot != null) {
                 if (hoveringSlot.hasItem()) {
                     String query = "u:" + hoveringSlot.getItemStack().getDisplayName() + "!";
                     GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
@@ -180,10 +176,10 @@ public class RecipePageCrafting
     protected void renderBackground(TextureManager re, int x, int y) {
         super.renderBackground(re, x, y);
         re.bindTexture(re.loadTexture("/assets/minecraft/textures/gui/container/guidebook/guidebook.png"));
-        for (int i = 1; i <= recipes.size(); i++) {
-            RecipeEntryCrafting<?, ?> recipe = recipes.get(i-1);
-            List<SlotGuidebook> list = map.get(recipe);
-            drawTexturedModalRect(x + list.get(list.size()-1).x - 25, y +  list.get(list.size()-1).y, 234, 0, 22, 15);
+        for (int i = 1; i <= this.recipes.size(); i++) {
+            RecipeEntryCrafting<?, ?> recipe = this.recipes.get(i - 1);
+            List<SlotGuidebook> list = this.map.get(recipe);
+            drawTexturedModalRect(x + list.get(list.size() - 1).x - 25, y + list.get(list.size() - 1).y, 234, 0, 22, 15);
         }
     }
 
@@ -191,16 +187,14 @@ public class RecipePageCrafting
     protected void renderOverlay(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
         super.renderOverlay(re, sr, x, y, mouseX, mouseY, partialTicks);
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-            if (mouseOverSlot != null && mouseOverSlot.hasItem())
-            {
+        for (SlotGuidebook slot : this.slots) {
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            if (mouseOverSlot != null && mouseOverSlot.hasItem()) {
                 boolean showDescription = DescriptionPromptEnum.showDescription(mc);
-                String str = tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
-                if(!str.isEmpty())
-                {
-                    tooltipElement.render(str, mouseX, mouseY, 8, -8);
+                String str = this.tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
+                if (!str.isEmpty()) {
+                    this.tooltipElement.render(str, mouseX, mouseY, 8, -8);
                 }
             }
         }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/mobs/GuidebookPageMob.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/mobs/GuidebookPageMob.java
index 0aeff3f7c..885d0090c 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/mobs/GuidebookPageMob.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/mobs/GuidebookPageMob.java
@@ -9,7 +9,9 @@ import net.minecraft.client.gui.guidebook.GuidebookSection;
 import net.minecraft.client.option.enums.DescriptionPromptEnum;
 import net.minecraft.client.render.*;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.world.WorldClient;
 import net.minecraft.core.achievement.stat.StatList;
@@ -22,10 +24,6 @@ import net.minecraft.core.player.gamemode.Gamemode;
 import net.minecraft.core.player.inventory.slot.Slot;
 import net.minecraft.client.gui.guidebook.SlotGuidebook;
 import net.minecraft.core.util.helper.MathHelper;
-import net.minecraft.core.world.World;
-import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 import org.slf4j.Logger;
 
 import java.util.*;
@@ -44,7 +42,6 @@ public class GuidebookPageMob
     private boolean discovered;
 
 
-
     public GuidebookPageMob(GuidebookSection section, Class<? extends Mob> mobClass, MobInfoRegistry.MobInfo mobInfo) {
         super(section);
 
@@ -60,18 +57,18 @@ public class GuidebookPageMob
         if (example != null) example.setSkinVariant(0);
 
         if (mobInfo.getDrops() != null && mobInfo.getDrops().length > 0) {
-            slots = new ArrayList<>();
-            dropSlotMap = new HashMap<>();
+            this.slots = new ArrayList<>();
+            this.dropSlotMap = new HashMap<>();
             for (int i = 0; i < mobInfo.getDrops().length; i++) {
                 MobInfoRegistry.MobDrop drop = mobInfo.getDrops()[i];
                 SlotGuidebook slot = new SlotGuidebook(i, 0, 0, new RecipeSymbol(drop.getStack()), false, null);
-                slots.add(slot);
-                dropSlotMap.put(drop, slot);
+                this.slots.add(slot);
+                this.dropSlotMap.put(drop, slot);
             }
         }
 
         EntityDispatcher.EntityDispatcherEntry<?> entry = EntityDispatcher.getInstance().entryForClass(mobClass);
-        discovered = mc.statsCounter.readStat(StatList.mobEncounterStats.get(entry != null ? entry.namespaceID : null)) > 0;
+        this.discovered = mc.statsCounter.readStat(StatList.mobEncounterStats.get(entry != null ? entry.namespaceID : null)) > 0;
     }
 
     private static String[] createDescLines(FontRenderer sr, String languageKey) {
@@ -103,72 +100,73 @@ public class GuidebookPageMob
 
     @Override
     protected void renderBackground(TextureManager re, int x, int y) {
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         re.bindTexture(re.loadTexture("/assets/minecraft/textures/gui/container/guidebook/mob.png"));
         drawTexturedModalRect(x, y, 0, 0, 158, 220);
     }
 
     @Override
     protected void renderForeground(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
-        EntityDispatcher.EntityDispatcherEntry<?> entry = EntityDispatcher.getInstance().entryForClass(mobClass);
-        discovered = mc.statsCounter.readStat(StatList.mobEncounterStats.get(entry != null ? entry.namespaceID : null)) > 0;
-        if (mc.thePlayer.getGamemode() == Gamemode.creative || !mc.gameSettings.hideUndiscoveredItems.value) discovered = true;
+        EntityDispatcher.EntityDispatcherEntry<?> entry = EntityDispatcher.getInstance().entryForClass(this.mobClass);
+        this.discovered = mc.statsCounter.readStat(StatList.mobEncounterStats.get(entry != null ? entry.namespaceID : null)) > 0;
+        if (mc.thePlayer.getGamemode() == Gamemode.creative || !mc.gameSettings.hideUndiscoveredItems.value)
+            this.discovered = true;
 
         Lighting.disable();
-        if(mobInfo != null) {
+        if (this.mobInfo != null) {
             I18n i18n = I18n.getInstance();
 
             String[] lines;
-            if (!discovered) {
+            if (!this.discovered) {
                 lines = createDescLines(sr, "guidebook.section.mob.undiscovered");
             } else {
-                lines = createDescLines(sr, mobInfo.getDescriptionTranslationKey());
+                lines = createDescLines(sr, this.mobInfo.getDescriptionTranslationKey());
             }
 
             // Display name
             int yOffset = y + 8;
-            String name = i18n.translateKey(mobInfo.getNameTranslationKey());
-            if (!discovered) {
+            String name = i18n.translateKey(this.mobInfo.getNameTranslationKey());
+            if (!this.discovered) {
                 name = new String(new char[name.length()]).replace("\0", "?");
             }
             drawStringNoShadow(sr, name, x + 66, y + 8, 0x000000);
 
-            if (discovered) {
+            if (this.discovered) {
                 // Display health
-                if (mobInfo.getHealth() > 0) {
-                    if(mobInfo.getHealth() > 40){
+                if (this.mobInfo.getHealth() > 0) {
+                    if (this.mobInfo.getHealth() > 40) {
                         yOffset += 12;
                         drawStringNoShadow(sr, i18n.translateKey("guidebook.section.mob.health"), x + 66, yOffset, 0x505050);
                         yOffset += 6;
-                        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+                        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
                         yOffset += 4;
                         drawGuiIcon(x + 66, yOffset, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/container"));
                         drawGuiIcon(x + 66, yOffset, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/full"));
-                        drawStringNoShadow(sr, "x "+mobInfo.getHealth()/2, x + 66 + 12, yOffset, 0x505050);
+                        drawStringNoShadow(sr, "x " + this.mobInfo.getHealth() / 2, x + 66 + 12, yOffset, 0x505050);
 
                     } else {
                         yOffset += 12;
                         drawStringNoShadow(sr, i18n.translateKey("guidebook.section.mob.health"), x + 66, yOffset, 0x505050);
                         yOffset += 6;
-                        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-                        for (int i = 0; i < mobInfo.getHealth() / 2; i++) {
+                        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+                        for (int i = 0; i < this.mobInfo.getHealth() / 2; i++) {
                             if (i % 10 == 0) {
                                 yOffset += 4;
                             }
                             drawGuiIcon(x + 66 + (i % 10) * 8, yOffset, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/container"));
                             drawGuiIcon(x + 66 + (i % 10) * 8, yOffset, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/full"));
                         }
-                        if (mobInfo.getHealth() % 2 == 1) {
-                            drawGuiIcon(x + 66 + ((mobInfo.getHealth() / 2) % 10) * 8, yOffset, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/container"));
-                            drawGuiIcon(x + 66 + ((mobInfo.getHealth() / 2) % 10) * 8, yOffset, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/half"));
+                        if (this.mobInfo.getHealth() % 2 == 1) {
+                            drawGuiIcon(x + 66 + ((this.mobInfo.getHealth() / 2) % 10) * 8, yOffset, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/container"));
+                            drawGuiIcon(x + 66 + ((this.mobInfo.getHealth() / 2) % 10) * 8, yOffset, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/half"));
                         }
                     }
                 }
 
                 // Display score
-                if (mobInfo.getScore() > 0) {
+                if (this.mobInfo.getScore() > 0) {
                     yOffset += 11;
-                    drawStringNoShadow(sr, i18n.translateKeyAndFormat("guidebook.section.mob.score", mobInfo.getScore()), x + 66, yOffset, 0x505050);
+                    drawStringNoShadow(sr, i18n.translateKeyAndFormat("guidebook.section.mob.score", this.mobInfo.getScore()), x + 66, yOffset, 0x505050);
                 }
             }
 
@@ -179,23 +177,23 @@ public class GuidebookPageMob
                 yOffset += 10;
             }
 
-            if (discovered) {
+            if (this.discovered) {
                 // Display drops
-                if (mobInfo.getDrops() != null && mobInfo.getDrops().length > 0) {
+                if (this.mobInfo.getDrops() != null && this.mobInfo.getDrops().length > 0) {
                     yOffset += 4;
                     drawStringNoShadow(sr, i18n.translateKey("guidebook.section.mob.drops"), x + 8, yOffset, 0x000000);
                     yOffset += 12;
-                    for (int i = 0; i < mobInfo.getDrops().length; i++) {
-                        SlotGuidebook slot = slots.get(i);
+                    for (int i = 0; i < this.mobInfo.getDrops().length; i++) {
+                        SlotGuidebook slot = this.slots.get(i);
                         slot.x = 7 + (i % 7) * 21;
                         slot.y = (yOffset - y) + (i / 7) * 20;
-                        MobInfoRegistry.MobDrop drop = mobInfo.getDrops()[i];
+                        MobInfoRegistry.MobDrop drop = this.mobInfo.getDrops()[i];
                         boolean mouseOver = getIsMouseOverSlot(slot, x, y, mouseX, mouseY);
                         drawSlot(x + 7 + (i % 7) * 21, yOffset + (i / 7) * 20, 0xFFFFFFFF);
-                        GL11.glPushMatrix();
-                        GL11.glTranslatef(0, 0, 50f);
+                        GLRenderer.pushFrame();
+                        GLRenderer.modelM4f().translate(0, 0, 50f);
                         itemElement.render(slot.getItemStack(), x + 8 + (i % 7) * 21, yOffset + 1 + (i / 7) * 20, mouseOver, slot);
-                        GL11.glPopMatrix();
+                        GLRenderer.popFrame();
                         if (slot.getIsDiscovered(mc.thePlayer)) {
                             String amountString = drop.getMinAmount() == drop.getMaxAmount() ? String.valueOf(drop.getMinAmount()) : drop.getMinAmount() + "-" + drop.getMaxAmount();
                             int width = MathHelper.ceil(sr.stringWidthDouble(amountString));
@@ -205,7 +203,7 @@ public class GuidebookPageMob
                 }
             }
         } else {
-            drawStringCenteredNoShadow(sr,"No results :(" ,x+width/2,y+height/2,0xFF808080);
+            drawStringCenteredNoShadow(sr, "No results :(", x + this.width / 2, y + this.height / 2, 0xFF808080);
         }
 
         renderMob(x, y, mouseX, mouseY, partialTicks);
@@ -215,14 +213,14 @@ public class GuidebookPageMob
     public void onMouseDown(int x, int y, int mouseX, int mouseY, int button) {
         super.onMouseDown(x, y, mouseX, mouseY, button);
 
-        if (example == null) {
+        if (this.example == null) {
             return;
         }
 
-        if (discovered) {
+        if (this.discovered) {
             if (mouseX > x + 9 && mouseX < x + 9 + 52 && mouseY > y + 9 && mouseY < y + 9 + 70) {
-                String livingSound = example.getLivingSound();
-                if (example.cycleVariant() && livingSound != null) {
+                String livingSound = this.example.getLivingSound();
+                if (this.example.cycleVariant() && livingSound != null) {
                     Minecraft mc = Minecraft.getMinecraft();
                     Random random = new Random();
                     mc.currentWorld.playSoundAtEntity(null, mc.thePlayer, livingSound, 0.25f, (random.nextFloat() - random.nextFloat()) * 0.2F + 1.0F);
@@ -233,42 +231,44 @@ public class GuidebookPageMob
     }
 
     private void renderMob(int x, int y, int mouseX, int mouseY, float partialTicks) {
-        if (example == null) {
+        if (this.example == null) {
             return;
         }
-        if (!discovered) return;
+        if (!this.discovered) return;
 
         float heightFactor = 50f / 1.8f;
 
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
 
         Scissor.enable(x + 9, y + 9, 52, 70);
 
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glPushMatrix();
-        GL11.glTranslatef(x + 34, y + 44 + 32, 50F);
-        float f1 = 30F;
-        GL11.glScalef(-f1, f1, f1);
-        GL11.glRotatef(180F, 0.0F, 0.0F, 1.0F);
-        float f5 = (float)(x + 34) - mouseX;
-        float f6 = (float)(y + 44 + 32) - (heightFactor * example.bbHeight) - mouseY;
-        GL11.glRotatef(135F, 0.0F, 1.0F, 0.0F);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glEnable(GL11.GL_COLOR_MATERIAL);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.WORLD);
+        GLRenderer.modelM4f().translate(x + 34, y + 44 + 32, 50F);
+        float scale = 30F;
+        GLRenderer.modelM4f().scale(-scale, scale, scale);
+        GLRenderer.modelM4f().rotateZ(org.joml.Math.toRadians(180F));
+        float f5 = (float) (x + 34) - mouseX;
+        float f6 = (float) (y + 44 + 32) - (heightFactor * this.example.bbHeight) - mouseY;
+        GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(135F));
         Lighting.enableLight();
-        GL11.glRotatef(-135F, 0.0F, 1.0F, 0.0F);
-        GL11.glRotatef(-(float)Math.atan(f6 / 40F) * 20F, 1.0F, 0.0F, 0.0F);
-        example.yBodyRot = (float)Math.atan(f5 / 40F) * 20F;
-        example.yRot = (float)Math.atan(f5 / 40F) * 40F;
-        example.xRot = -(float)Math.atan(f6 / 40F) * 20F;
-        example.entityBrightness = 1.0F;
-        GL11.glTranslatef(0.0F, example.heightOffset, 0.0F);
-        EntityRenderDispatcher.instance.viewLerpYaw = 180F;
-        EntityRenderDispatcher.instance.renderEntityPreviewWithPosYaw(Tessellator.instance, example, 0.0D, 0.0D, 0.0D, 0.0F, 1.0F);
-        GL11.glPopMatrix();
+        GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(-135F));
+        GLRenderer.modelM4f().rotateX(org.joml.Math.toRadians(-(float) Math.atan(f6 / 40F) * 20F));
+        this.example.yBodyRot = (float) Math.atan(f5 / 40F) * 20F;
+        this.example.yRot = (float) Math.atan(f5 / 40F) * 40F;
+        this.example.xRot = -(float) Math.atan(f6 / 40F) * 20F;
+        this.example.entityBrightness = 1.0F;
+        GLRenderer.modelM4f().translate(0.0F, this.example.heightOffset, 0.0F);
+        EntityRendererDispatcher.instance.viewLerpYaw = 180F;
+        GLRenderer.globalGetNormalTransformMatrix().scale(1, -1, 1);
+        EntityRendererDispatcher.instance.renderEntityPreviewWithPosYaw(GLRenderer.getTessellator(), this.example, 0.0D, 0.0D, 0.0D, 0.0F, 1.0F);
+        GLRenderer.popFrame();
         Lighting.disable();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.disableState(State.DEPTH_TEST);
 
         Scissor.disable();
     }
@@ -276,17 +276,15 @@ public class GuidebookPageMob
     @Override
     protected void renderOverlay(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
         super.renderOverlay(re, sr, x, y, mouseX, mouseY, partialTicks);
-        if (slots == null) return;
+        if (this.slots == null) return;
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-            if (mouseOverSlot != null && mouseOverSlot.hasItem())
-            {
+        for (SlotGuidebook slot : this.slots) {
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            if (mouseOverSlot != null && mouseOverSlot.hasItem()) {
                 boolean showDescription = DescriptionPromptEnum.showDescription(mc);
                 String str = tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
-                if(!str.isEmpty())
-                {
+                if (!str.isEmpty()) {
                     tooltipElement.render(str, mouseX, mouseY, 8, -8);
                 }
             }
@@ -294,9 +292,8 @@ public class GuidebookPageMob
 
     }
 
-    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY)
-    {
-        return mouseX >= x+slot.x - 1 && mouseX < x+slot.x + 16 + 1 && mouseY >= y+slot.y - 1 && mouseY < y+slot.y + 16 + 1;
+    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY) {
+        return mouseX >= x + slot.x - 1 && mouseX < x + slot.x + 16 + 1 && mouseY >= y + slot.y - 1 && mouseY < y + slot.y + 16 + 1;
     }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/mobs/MobInfoRegistry.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/mobs/MobInfoRegistry.java
index 5a3d58c88..d9e4ea1b1 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/mobs/MobInfoRegistry.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/mobs/MobInfoRegistry.java
@@ -1,6 +1,6 @@
 package net.minecraft.client.gui.guidebook.mobs;
 
-import net.minecraft.client.render.EntityRenderDispatcher;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import net.minecraft.client.render.entity.EntityRenderer;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.entity.Entity;
@@ -214,7 +214,7 @@ public abstract class MobInfoRegistry {
         }
 
         public EntityRenderer<?> getRenderer() {
-            return EntityRenderDispatcher.instance.getRenderer(entityClass);
+            return EntityRendererDispatcher.instance.getRenderer(entityClass);
         }
 
         public String getNameTranslationKey() {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/smelting/RecipePageBlastSmelting.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/smelting/RecipePageBlastSmelting.java
index c1770801b..ee3eb4e8f 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/smelting/RecipePageBlastSmelting.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/smelting/RecipePageBlastSmelting.java
@@ -12,16 +12,13 @@ import net.minecraft.client.gui.guidebook.search.GuidebookPageSearch;
 import net.minecraft.client.option.enums.DescriptionPromptEnum;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.core.achievement.Achievements;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.data.registry.recipe.RecipeSymbol;
 import net.minecraft.core.data.registry.recipe.SearchQuery;
 import net.minecraft.core.data.registry.recipe.entry.RecipeEntryBlastFurnace;
-import net.minecraft.core.entity.player.Player;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.slot.Slot;
 import net.minecraft.client.gui.guidebook.SlotGuidebook;
-import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.HashMap;
@@ -32,40 +29,41 @@ public class RecipePageBlastSmelting
     extends RecipePage<RecipeEntryBlastFurnace> {
     public static final int RECIPES_PER_PAGE = 6;
     public List<SlotGuidebook> slots;
-    public Map<RecipeEntryBlastFurnace,List<SlotGuidebook>> map;
+    public Map<RecipeEntryBlastFurnace, List<SlotGuidebook>> map;
     private final TooltipElement tooltipElement;
     private final ItemElement itemElement;
     private static final Minecraft mc = Minecraft.getMinecraft();
     private static long ticks = 0;
+
     public RecipePageBlastSmelting(GuidebookSection section, ArrayList<RecipeEntryBlastFurnace> recipes) {
         super(section);
         this.recipes = recipes;
         this.slots = new ArrayList<>();
         this.map = new HashMap<>();
-        tooltipElement = new TooltipElement(mc);
-        itemElement = new ItemElement(mc);
+        this.tooltipElement = new TooltipElement(mc);
+        this.itemElement = new ItemElement(mc);
 
         for (RecipeEntryBlastFurnace recipe : recipes) {
             List<SlotGuidebook> recipeSlots = new ArrayList<>();
-            recipeSlots.add(new SlotGuidebook(0, (width/2)-52, 32*(map.size()+1)-16, recipe.getInput()[0], false,recipe));
+            recipeSlots.add(new SlotGuidebook(0, (this.width / 2) - 52, 32 * (this.map.size() + 1) - 16, recipe.getInput()[0], false, recipe));
             if (recipe.getInput().length == 2) {
-                recipeSlots.add(new SlotGuidebook(1, (width/2)-32, 32*(map.size()+1)-16, recipe.getInput()[1], false,recipe));
+                recipeSlots.add(new SlotGuidebook(1, (this.width / 2) - 32, 32 * (this.map.size() + 1) - 16, recipe.getInput()[1], false, recipe));
             } else {
-                recipeSlots.add(new SlotGuidebook(0, (width/2)-32, 32*(map.size()+1)-16, null, false,recipe));
+                recipeSlots.add(new SlotGuidebook(0, (this.width / 2) - 32, 32 * (this.map.size() + 1) - 16, null, false, recipe));
             }
-            recipeSlots.add(new SlotGuidebook(2, (width/2)+24, 32*(map.size()+1)-16, new RecipeSymbol(recipe.getOutput()), false,recipe));
-            map.put(recipe,recipeSlots);
-            slots.addAll(recipeSlots);
+            recipeSlots.add(new SlotGuidebook(2, (this.width / 2) + 24, 32 * (this.map.size() + 1) - 16, new RecipeSymbol(recipe.getOutput()), false, recipe));
+            this.map.put(recipe, recipeSlots);
+            this.slots.addAll(recipeSlots);
         }
     }
 
     @Override
     public void onTick() {
         ticks++;
-        for (SlotGuidebook slot : slots) {
-            if(ticks > 20) {
+        for (SlotGuidebook slot : this.slots) {
+            if (ticks > 20) {
                 slot.showRandomItem();
-                if(slots.get(slots.size()-1) == slot){
+                if (this.slots.get(this.slots.size() - 1) == slot) {
                     ticks = 0;
                 }
             }
@@ -74,33 +72,32 @@ public class RecipePageBlastSmelting
 
     @Override
     protected void renderForeground(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
-        if(recipes.isEmpty()){
-            drawStringCenteredNoShadow(sr, I18n.getInstance().translateKey("guidebook.section.search.error.no_recipes") ,x+width/2,y+height/2,0xFF808080);
+        if (this.recipes.isEmpty()) {
+            drawStringCenteredNoShadow(sr, I18n.getInstance().translateKey("guidebook.section.search.error.no_recipes"), x + this.width / 2, y + this.height / 2, 0xFF808080);
         }
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            drawSlot(x+slot.x -1,y+slot.y -1,0xFFFFFFFF);
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            itemElement.render(slot.getItemStack(),x+slot.x,y+slot.y,mouseOverSlot == slot,slot);
+        for (SlotGuidebook slot : this.slots) {
+            drawSlot(x + slot.x - 1, y + slot.y - 1, 0xFFFFFFFF);
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            this.itemElement.render(slot.getItemStack(), x + slot.x, y + slot.y, mouseOverSlot == slot, slot);
         }
     }
 
-    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY)
-    {
-        return mouseX >= x+slot.x - 1 && mouseX < x+slot.x + 16 + 1 && mouseY >= y+slot.y - 1 && mouseY < y+slot.y + 16 + 1;
+    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY) {
+        return mouseX >= x + slot.x - 1 && mouseX < x + slot.x + 16 + 1 && mouseY >= y + slot.y - 1 && mouseY < y + slot.y + 16 + 1;
     }
 
     @Override
     public boolean keyTyped(char c, int key, int x, int y, int mouseX, int mouseY) {
         super.keyTyped(c, key, x, y, mouseX, mouseY);
-        if(mc.gameSettings.keyShowRecipe.isKeyboardKey(key)){
-            SlotGuidebook hoveringSlot= null;
-            for (SlotGuidebook slot : slots) {
-                if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) hoveringSlot = slot;
+        if (mc.gameSettings.keyShowRecipe.isKeyboardKey(key)) {
+            SlotGuidebook hoveringSlot = null;
+            for (SlotGuidebook slot : this.slots) {
+                if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) hoveringSlot = slot;
             }
-            if(hoveringSlot != null){
-                if(hoveringSlot.hasItem()){
-                    String query = "r:"+hoveringSlot.getItemStack().getDisplayName()+"!";
+            if (hoveringSlot != null) {
+                if (hoveringSlot.hasItem()) {
+                    String query = "r:" + hoveringSlot.getItemStack().getDisplayName() + "!";
                     GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
                     GuidebookPageSearch.searchField.setText(query);
                     ScreenGuidebook.getPageManager().updatePages();
@@ -109,11 +106,11 @@ public class RecipePageBlastSmelting
                 }
             }
         } else if (mc.gameSettings.keyShowUsage.isKeyboardKey(key)) {
-            SlotGuidebook hoveringSlot= null;
-            for (SlotGuidebook slot : slots) {
-                if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) hoveringSlot = slot;
+            SlotGuidebook hoveringSlot = null;
+            for (SlotGuidebook slot : this.slots) {
+                if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) hoveringSlot = slot;
             }
-            if(hoveringSlot != null) {
+            if (hoveringSlot != null) {
                 if (hoveringSlot.hasItem()) {
                     String query = "u:" + hoveringSlot.getItemStack().getDisplayName() + "!";
                     GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
@@ -137,10 +134,10 @@ public class RecipePageBlastSmelting
     protected void renderBackground(TextureManager re, int x, int y) {
         super.renderBackground(re, x, y);
         re.bindTexture(re.loadTexture("/assets/minecraft/textures/gui/container/guidebook/guidebook.png"));
-        for (int i = 1; i <= recipes.size(); i++) {
-            RecipeEntryBlastFurnace recipe = recipes.get(i-1);
-            List<SlotGuidebook> list = map.get(recipe);
-            drawTexturedModalRect(x + list.get(list.size()-1).x - 32, y +  list.get(list.size()-1).y, 234, 0, 22, 15);
+        for (int i = 1; i <= this.recipes.size(); i++) {
+            RecipeEntryBlastFurnace recipe = this.recipes.get(i - 1);
+            List<SlotGuidebook> list = this.map.get(recipe);
+            drawTexturedModalRect(x + list.get(list.size() - 1).x - 32, y + list.get(list.size() - 1).y, 234, 0, 22, 15);
         }
     }
 
@@ -148,16 +145,14 @@ public class RecipePageBlastSmelting
     protected void renderOverlay(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
         super.renderOverlay(re, sr, x, y, mouseX, mouseY, partialTicks);
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-            if (mouseOverSlot != null && mouseOverSlot.hasItem())
-            {
+        for (SlotGuidebook slot : this.slots) {
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            if (mouseOverSlot != null && mouseOverSlot.hasItem()) {
                 boolean showDescription = DescriptionPromptEnum.showDescription(mc);
-                String str = tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
-                if(!str.isEmpty())
-                {
-                    tooltipElement.render(str, mouseX, mouseY, 8, -8);
+                String str = this.tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
+                if (!str.isEmpty()) {
+                    this.tooltipElement.render(str, mouseX, mouseY, 8, -8);
                 }
             }
         }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/smelting/RecipePageSmelting.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/smelting/RecipePageSmelting.java
index d75779401..7c68cde75 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/smelting/RecipePageSmelting.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/smelting/RecipePageSmelting.java
@@ -12,16 +12,13 @@ import net.minecraft.client.gui.guidebook.search.GuidebookPageSearch;
 import net.minecraft.client.option.enums.DescriptionPromptEnum;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.core.achievement.Achievements;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.data.registry.recipe.RecipeSymbol;
 import net.minecraft.core.data.registry.recipe.SearchQuery;
 import net.minecraft.core.data.registry.recipe.entry.RecipeEntryFurnace;
-import net.minecraft.core.entity.player.Player;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.slot.Slot;
 import net.minecraft.client.gui.guidebook.SlotGuidebook;
-import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.HashMap;
@@ -32,35 +29,36 @@ public class RecipePageSmelting
     extends RecipePage<RecipeEntryFurnace> {
     public static final int RECIPES_PER_PAGE = 6;
     public List<SlotGuidebook> slots;
-    public Map<RecipeEntryFurnace,List<SlotGuidebook>> map;
+    public Map<RecipeEntryFurnace, List<SlotGuidebook>> map;
     private final TooltipElement tooltipElement;
     private final ItemElement itemElement;
     private static final Minecraft mc = Minecraft.getMinecraft();
     private static long ticks = 0;
+
     public RecipePageSmelting(GuidebookSection section, ArrayList<RecipeEntryFurnace> recipes) {
         super(section);
         this.recipes = recipes;
         this.slots = new ArrayList<>();
         this.map = new HashMap<>();
-        tooltipElement = new TooltipElement(mc);
-        itemElement = new ItemElement(mc);
+        this.tooltipElement = new TooltipElement(mc);
+        this.itemElement = new ItemElement(mc);
 
         for (RecipeEntryFurnace recipe : recipes) {
             List<SlotGuidebook> recipeSlots = new ArrayList<>();
-            recipeSlots.add(new SlotGuidebook(0, (width/2)-32, 32*(map.size()+1)-16, recipe.getInput(), false,recipe));
-            recipeSlots.add(new SlotGuidebook(1, (width/2)+24, 32*(map.size()+1)-16, new RecipeSymbol(recipe.getOutput()), false,recipe));
-            map.put(recipe,recipeSlots);
-            slots.addAll(recipeSlots);
+            recipeSlots.add(new SlotGuidebook(0, (this.width / 2) - 32, 32 * (this.map.size() + 1) - 16, recipe.getInput(), false, recipe));
+            recipeSlots.add(new SlotGuidebook(1, (this.width / 2) + 24, 32 * (this.map.size() + 1) - 16, new RecipeSymbol(recipe.getOutput()), false, recipe));
+            this.map.put(recipe, recipeSlots);
+            this.slots.addAll(recipeSlots);
         }
     }
 
     @Override
     public void onTick() {
         ticks++;
-        for (SlotGuidebook slot : slots) {
-            if(ticks > 20) {
+        for (SlotGuidebook slot : this.slots) {
+            if (ticks > 20) {
                 slot.showRandomItem();
-                if(slots.get(slots.size()-1) == slot){
+                if (this.slots.get(this.slots.size() - 1) == slot) {
                     ticks = 0;
                 }
             }
@@ -69,33 +67,32 @@ public class RecipePageSmelting
 
     @Override
     protected void renderForeground(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
-        if(recipes.isEmpty()){
-            drawStringCenteredNoShadow(sr, I18n.getInstance().translateKey("guidebook.section.search.error.no_recipes") ,x+width/2,y+height/2,0xFF808080);
+        if (this.recipes.isEmpty()) {
+            drawStringCenteredNoShadow(sr, I18n.getInstance().translateKey("guidebook.section.search.error.no_recipes"), x + this.width / 2, y + this.height / 2, 0xFF808080);
         }
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            drawSlot(x+slot.x -1,y+slot.y -1,0xFFFFFFFF);
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            itemElement.render(slot.getItemStack(),x+slot.x,y+slot.y,mouseOverSlot == slot,slot);
+        for (SlotGuidebook slot : this.slots) {
+            drawSlot(x + slot.x - 1, y + slot.y - 1, 0xFFFFFFFF);
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            this.itemElement.render(slot.getItemStack(), x + slot.x, y + slot.y, mouseOverSlot == slot, slot);
         }
     }
 
-    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY)
-    {
-        return mouseX >= x+slot.x - 1 && mouseX < x+slot.x + 16 + 1 && mouseY >= y+slot.y - 1 && mouseY < y+slot.y + 16 + 1;
+    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY) {
+        return mouseX >= x + slot.x - 1 && mouseX < x + slot.x + 16 + 1 && mouseY >= y + slot.y - 1 && mouseY < y + slot.y + 16 + 1;
     }
 
     @Override
     public boolean keyTyped(char c, int key, int x, int y, int mouseX, int mouseY) {
         super.keyTyped(c, key, x, y, mouseX, mouseY);
-        if(mc.gameSettings.keyShowRecipe.isKeyboardKey(key)){
-            SlotGuidebook hoveringSlot= null;
-            for (SlotGuidebook slot : slots) {
-                if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) hoveringSlot = slot;
+        if (mc.gameSettings.keyShowRecipe.isKeyboardKey(key)) {
+            SlotGuidebook hoveringSlot = null;
+            for (SlotGuidebook slot : this.slots) {
+                if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) hoveringSlot = slot;
             }
-            if(hoveringSlot != null){
-                if(hoveringSlot.hasItem()){
-                    String query = "r:"+hoveringSlot.getItemStack().getDisplayName()+"!";
+            if (hoveringSlot != null) {
+                if (hoveringSlot.hasItem()) {
+                    String query = "r:" + hoveringSlot.getItemStack().getDisplayName() + "!";
                     GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
                     GuidebookPageSearch.searchField.setText(query);
                     ScreenGuidebook.getPageManager().updatePages();
@@ -104,11 +101,11 @@ public class RecipePageSmelting
                 }
             }
         } else if (mc.gameSettings.keyShowUsage.isKeyboardKey(key)) {
-            SlotGuidebook hoveringSlot= null;
-            for (SlotGuidebook slot : slots) {
-                if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) hoveringSlot = slot;
+            SlotGuidebook hoveringSlot = null;
+            for (SlotGuidebook slot : this.slots) {
+                if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) hoveringSlot = slot;
             }
-            if(hoveringSlot != null) {
+            if (hoveringSlot != null) {
                 if (hoveringSlot.hasItem()) {
                     String query = "u:" + hoveringSlot.getItemStack().getDisplayName() + "!";
                     GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
@@ -132,10 +129,10 @@ public class RecipePageSmelting
     protected void renderBackground(TextureManager re, int x, int y) {
         super.renderBackground(re, x, y);
         re.bindTexture(re.loadTexture("/assets/minecraft/textures/gui/container/guidebook/guidebook.png"));
-        for (int i = 1; i <= recipes.size(); i++) {
-            RecipeEntryFurnace recipe = recipes.get(i-1);
-            List<SlotGuidebook> list = map.get(recipe);
-            drawTexturedModalRect(x + list.get(list.size()-1).x - 32, y +  list.get(list.size()-1).y, 234, 0, 22, 15);
+        for (int i = 1; i <= this.recipes.size(); i++) {
+            RecipeEntryFurnace recipe = this.recipes.get(i - 1);
+            List<SlotGuidebook> list = this.map.get(recipe);
+            drawTexturedModalRect(x + list.get(list.size() - 1).x - 32, y + list.get(list.size() - 1).y, 234, 0, 22, 15);
         }
     }
 
@@ -143,16 +140,14 @@ public class RecipePageSmelting
     protected void renderOverlay(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
         super.renderOverlay(re, sr, x, y, mouseX, mouseY, partialTicks);
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-            if (mouseOverSlot != null && mouseOverSlot.hasItem())
-            {
+        for (SlotGuidebook slot : this.slots) {
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            if (mouseOverSlot != null && mouseOverSlot.hasItem()) {
                 boolean showDescription = DescriptionPromptEnum.showDescription(mc);
-                String str = tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
-                if(!str.isEmpty())
-                {
-                    tooltipElement.render(str, mouseX, mouseY, 8, -8);
+                String str = this.tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
+                if (!str.isEmpty()) {
+                    this.tooltipElement.render(str, mouseX, mouseY, 8, -8);
                 }
             }
         }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/guidebook/trommeling/RecipePageTrommel.java b/game/client/src/main/java/net/minecraft/client/gui/guidebook/trommeling/RecipePageTrommel.java
index 0910282f2..e78e10646 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/guidebook/trommeling/RecipePageTrommel.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/guidebook/trommeling/RecipePageTrommel.java
@@ -12,19 +12,16 @@ import net.minecraft.client.gui.guidebook.search.GuidebookPageSearch;
 import net.minecraft.client.option.enums.DescriptionPromptEnum;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.WeightedRandomBag;
 import net.minecraft.core.WeightedRandomLootObject;
-import net.minecraft.core.achievement.Achievements;
 import net.minecraft.core.data.registry.recipe.RecipeSymbol;
 import net.minecraft.core.data.registry.recipe.SearchQuery;
 import net.minecraft.core.data.registry.recipe.entry.RecipeEntryTrommel;
-import net.minecraft.core.entity.player.Player;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.player.inventory.slot.Slot;
 import net.minecraft.client.gui.guidebook.SlotGuidebook;
-import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.HashMap;
@@ -35,7 +32,7 @@ public class RecipePageTrommel
     extends RecipePage<RecipeEntryTrommel> {
     public static final int RECIPES_PER_PAGE = 3;
     public List<SlotGuidebook> slots;
-    public Map<RecipeEntryTrommel,List<SlotGuidebook>> map;
+    public Map<RecipeEntryTrommel, List<SlotGuidebook>> map;
     private final TooltipElement tooltipElement;
     private final ItemElement itemElement;
     private static final Minecraft mc = Minecraft.getMinecraft();
@@ -47,29 +44,28 @@ public class RecipePageTrommel
         this.recipes = recipes;
         this.slots = new ArrayList<>();
         this.map = new HashMap<>();
-        tooltipElement = new TooltipElement(mc);
-        itemElement = new ItemElement(mc);
+        this.tooltipElement = new TooltipElement(mc);
+        this.itemElement = new ItemElement(mc);
         int recipeAmount = 0;
         int yOffset = 8;
         for (RecipeEntryTrommel recipe : recipes) {
             List<SlotGuidebook> recipeSlots = new ArrayList<>();
             int slotsAmount = 10;
 
-            for (int i = 0; i < slotsAmount - 1; i++)
-            {
-                if(recipe.getOutput().getEntries().size() > i){
+            for (int i = 0; i < slotsAmount - 1; i++) {
+                if (recipe.getOutput().getEntries().size() > i) {
                     ItemStack stack = recipe.getOutput().getEntries().get(i).getItemStack();
-                    recipeSlots.add(new SlotGuidebook(i, 81 + 20 * (i % 3), 1 + 20 * ((i / 3)+recipeAmount*3) + yOffset, new RecipeSymbol(stack), false,recipe).setAsOutput());
+                    recipeSlots.add(new SlotGuidebook(i, 81 + 20 * (i % 3), 1 + 20 * ((i / 3) + recipeAmount * 3) + yOffset, new RecipeSymbol(stack), false, recipe).setAsOutput());
                 } else {
-                    recipeSlots.add(new SlotGuidebook(i, 81 + 20 * (i % 3), 1 + 20 * ((i / 3)+recipeAmount*3) + yOffset, null, false,recipe).setAsOutput());
+                    recipeSlots.add(new SlotGuidebook(i, 81 + 20 * (i % 3), 1 + 20 * ((i / 3) + recipeAmount * 3) + yOffset, null, false, recipe).setAsOutput());
                 }
             }
 
-            int centerY = (recipeSlots.get(recipeSlots.size()-1).y + recipeSlots.get(recipeSlots.size()-8).y) / 2;
-            recipeSlots.add(new SlotGuidebook(slotsAmount - 1, 19, centerY,recipe.getInput(), false,recipe));
+            int centerY = (recipeSlots.get(recipeSlots.size() - 1).y + recipeSlots.get(recipeSlots.size() - 8).y) / 2;
+            recipeSlots.add(new SlotGuidebook(slotsAmount - 1, 19, centerY, recipe.getInput(), false, recipe));
 
-            map.put(recipe,recipeSlots);
-            slots.addAll(recipeSlots);
+            this.map.put(recipe, recipeSlots);
+            this.slots.addAll(recipeSlots);
             yOffset += 4;
             recipeAmount++;
         }
@@ -79,32 +75,32 @@ public class RecipePageTrommel
     @Override
     public void onTick() {
         ticks++;
-        for (SlotGuidebook slot : slots) {
-            if(ticks > 20) {
+        for (SlotGuidebook slot : this.slots) {
+            if (ticks > 20) {
                 slot.showRandomItem();
-                if(slots.get(slots.size()-1) == slot){
+                if (this.slots.get(this.slots.size() - 1) == slot) {
                     ticks = 0;
                 }
             }
         }
 
         ticks2++;
-        if(ticks2 > 25) {
+        if (ticks2 > 25) {
             ticks2 = 0;
-            for (SlotGuidebook slot : slots) {
+            for (SlotGuidebook slot : this.slots) {
                 if (slot.recipe instanceof RecipeEntryTrommel) {
                     RecipeSymbol input = (RecipeSymbol) slot.recipe.getInput();
                     if (!input.matches(slot.getItemStack())) {
-                        if(slot.recipeAmount > 8){
-                            int recipeIndexMax = Math.round((float) slot.recipeAmount /9);
-                            if(slot.recipeIndex >= recipeIndexMax){
+                        if (slot.recipeAmount > 8) {
+                            int recipeIndexMax = Math.round((float) slot.recipeAmount / 9);
+                            if (slot.recipeIndex >= recipeIndexMax) {
                                 slot.recipeIndex = 0;
                             } else {
                                 slot.recipeIndex++;
                             }
                             WeightedRandomBag<WeightedRandomLootObject> loot = (WeightedRandomBag<WeightedRandomLootObject>) slot.recipe.getOutput();
                             int index = slot.index + (9 * slot.recipeIndex);
-                            if(index > slot.recipeAmount){
+                            if (index > slot.recipeAmount) {
                                 slot.item = null;
                             } else {
                                 slot.item = loot.getEntries().get(index).getItemStack();
@@ -118,33 +114,32 @@ public class RecipePageTrommel
 
     @Override
     protected void renderForeground(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
-        if(recipes.isEmpty()){
-            drawStringCenteredNoShadow(sr, I18n.getInstance().translateKey("guidebook.section.search.error.no_recipes") ,x+width/2,y+height/2,0xFF808080);
+        if (this.recipes.isEmpty()) {
+            drawStringCenteredNoShadow(sr, I18n.getInstance().translateKey("guidebook.section.search.error.no_recipes"), x + this.width / 2, y + this.height / 2, 0xFF808080);
         }
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            drawSlot(x+slot.x -1,y+slot.y -1,0xFFFFFFFF);
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            itemElement.render(slot.getItemStack(),x+slot.x,y+slot.y,mouseOverSlot == slot,slot);
+        for (SlotGuidebook slot : this.slots) {
+            drawSlot(x + slot.x - 1, y + slot.y - 1, 0xFFFFFFFF);
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            this.itemElement.render(slot.getItemStack(), x + slot.x, y + slot.y, mouseOverSlot == slot, slot);
         }
     }
 
-    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY)
-    {
-        return mouseX >= x+slot.x - 1 && mouseX < x+slot.x + 16 + 1 && mouseY >= y+slot.y - 1 && mouseY < y+slot.y + 16 + 1;
+    public boolean getIsMouseOverSlot(final Slot slot, int x, int y, int mouseX, int mouseY) {
+        return mouseX >= x + slot.x - 1 && mouseX < x + slot.x + 16 + 1 && mouseY >= y + slot.y - 1 && mouseY < y + slot.y + 16 + 1;
     }
 
     @Override
     public boolean keyTyped(char c, int key, int x, int y, int mouseX, int mouseY) {
         super.keyTyped(c, key, x, y, mouseX, mouseY);
-        if(mc.gameSettings.keyShowRecipe.isKeyboardKey(key)){
-            SlotGuidebook hoveringSlot= null;
-            for (SlotGuidebook slot : slots) {
-                if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) hoveringSlot = slot;
+        if (mc.gameSettings.keyShowRecipe.isKeyboardKey(key)) {
+            SlotGuidebook hoveringSlot = null;
+            for (SlotGuidebook slot : this.slots) {
+                if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) hoveringSlot = slot;
             }
-            if(hoveringSlot != null){
-                if(hoveringSlot.hasItem()){
-                    String query = "r:"+hoveringSlot.getItemStack().getDisplayName()+"!";
+            if (hoveringSlot != null) {
+                if (hoveringSlot.hasItem()) {
+                    String query = "r:" + hoveringSlot.getItemStack().getDisplayName() + "!";
                     GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
                     GuidebookPageSearch.searchField.setText(query);
                     ScreenGuidebook.getPageManager().updatePages();
@@ -153,11 +148,11 @@ public class RecipePageTrommel
                 }
             }
         } else if (mc.gameSettings.keyShowUsage.isKeyboardKey(key)) {
-            SlotGuidebook hoveringSlot= null;
-            for (SlotGuidebook slot : slots) {
-                if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) hoveringSlot = slot;
+            SlotGuidebook hoveringSlot = null;
+            for (SlotGuidebook slot : this.slots) {
+                if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) hoveringSlot = slot;
             }
-            if(hoveringSlot != null) {
+            if (hoveringSlot != null) {
                 if (hoveringSlot.hasItem()) {
                     String query = "u:" + hoveringSlot.getItemStack().getDisplayName() + "!";
                     GuidebookPageManager.searchQuery = SearchQuery.resolve(query);
@@ -181,10 +176,10 @@ public class RecipePageTrommel
     protected void renderBackground(TextureManager re, int x, int y) {
         super.renderBackground(re, x, y);
         re.bindTexture(re.loadTexture("/assets/minecraft/textures/gui/container/guidebook/guidebook.png"));
-        for (int i = 1; i <= recipes.size(); i++) {
-            RecipeEntryTrommel recipe = recipes.get(i-1);
-            List<SlotGuidebook> list = map.get(recipe);
-            drawTexturedModalRect(x + list.get(list.size()-1).x + 25, y +  list.get(list.size()-1).y, 234, 0, 22, 15);
+        for (int i = 1; i <= this.recipes.size(); i++) {
+            RecipeEntryTrommel recipe = this.recipes.get(i - 1);
+            List<SlotGuidebook> list = this.map.get(recipe);
+            drawTexturedModalRect(x + list.get(list.size() - 1).x + 25, y + list.get(list.size() - 1).y, 234, 0, 22, 15);
         }
     }
 
@@ -192,16 +187,14 @@ public class RecipePageTrommel
     protected void renderOverlay(TextureManager re, FontRenderer sr, int x, int y, int mouseX, int mouseY, float partialTicks) {
         super.renderOverlay(re, sr, x, y, mouseX, mouseY, partialTicks);
         SlotGuidebook mouseOverSlot = null;
-        for (SlotGuidebook slot : slots) {
-            if(getIsMouseOverSlot(slot,x,y,mouseX,mouseY)) mouseOverSlot = slot;
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-            if (mouseOverSlot != null && mouseOverSlot.hasItem())
-            {
+        for (SlotGuidebook slot : this.slots) {
+            if (getIsMouseOverSlot(slot, x, y, mouseX, mouseY)) mouseOverSlot = slot;
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            if (mouseOverSlot != null && mouseOverSlot.hasItem()) {
                 boolean showDescription = DescriptionPromptEnum.showDescription(mc);
-                String str = tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
-                if(!str.isEmpty())
-                {
-                    tooltipElement.render(str, mouseX, mouseY, 8, -8);
+                String str = this.tooltipElement.getTooltipText(mouseOverSlot.getItemStack(), showDescription, mouseOverSlot);
+                if (!str.isEmpty()) {
+                    this.tooltipElement.render(str, mouseX, mouseY, 8, -8);
                 }
             }
         }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/HudIngame.java b/game/client/src/main/java/net/minecraft/client/gui/hud/HudIngame.java
index 6abad9248..c7c42233c 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/HudIngame.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/HudIngame.java
@@ -1,7 +1,6 @@
 package net.minecraft.client.gui.hud;
 
 import static net.minecraft.core.util.helper.Utils.*;
-import static org.lwjgl.opengl.GL11.*;
 
 import java.awt.Color;
 import java.util.ArrayList;
@@ -17,13 +16,16 @@ import net.minecraft.client.gui.HeldItemTooltipElement;
 import net.minecraft.client.gui.ScreenPhotoMode;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.block.BlockLogicPortal;
 import net.minecraft.core.enums.ChatVisibility;
 import net.minecraft.core.enums.HumanArmorShape;
 import net.minecraft.core.util.helper.Direction;
 import net.minecraft.core.util.phys.HitResult;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.hud.component.HudComponent;
@@ -35,7 +37,7 @@ import net.minecraft.client.render.terrain.RenderRegion;
 import net.minecraft.client.render.terrain.TerrainRendererMultiDraw;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.Global;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.Blocks;
@@ -55,10 +57,10 @@ import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.season.Season;
 import net.minecraft.core.world.weather.Weather;
 import net.minecraft.core.world.wind.WindProvider;
+import org.lwjgl.opengl.GL41;
 import org.slf4j.Logger;
 
-public class HudIngame extends Gui
-{
+public class HudIngame extends Gui {
     public static final float DEBUG_SCALE = 1f;
     public static final int MAX_CHAT_WIDTH = 320;
     private static final Logger LOGGER = LogUtils.getLogger();
@@ -77,15 +79,13 @@ public class HudIngame extends Gui
 
     public final HeldItemTooltipElement heldItemTooltipElement;
 
-    public HudIngame(Minecraft minecraft)
-    {
+    public HudIngame(Minecraft minecraft) {
         this.mc = minecraft;
         this.fontRenderer = this.mc.font;
         this.heldItemTooltipElement = new HeldItemTooltipElement(this.mc);
     }
 
-    public void renderGameOverlay(float partialTicks, boolean flag, int mouseX, int mouseY)
-    {
+    public void renderGameOverlay(float partialTicks, boolean flag, int mouseX, int mouseY) {
         if (this.mc.currentScreen instanceof ScreenPhotoMode) return;
 
         I18n stringtranslate = I18n.getInstance();
@@ -94,53 +94,51 @@ public class HudIngame extends Gui
         int sp = (int) ((this.mc.gameSettings.screenPadding.value * height) / 8);
         this.mc.worldRenderer.setupScaledResolution();
 
-        GL11.glEnable(3042 /* GL_BLEND */);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
 
         // Render vignette
-        if (this.mc.gameSettings.immersiveMode.drawVignette() && this.mc.gameSettings.vignette.value)
-        {
+        if (this.mc.gameSettings.immersiveMode.drawVignette() && this.mc.gameSettings.vignette.value) {
             renderVignette(this.mc.thePlayer.getBrightness(partialTicks), width, height);
         }
 
         // Render pumpkin overlay
         final ItemStack headSlotItem = this.mc.thePlayer.inventory.armorItemInSlot(HumanArmorShape.HEAD);
-        if (this.mc.gameSettings.thirdPersonView.value == 0 && headSlotItem != null && (headSlotItem.itemID == Blocks.PUMPKIN_CARVED_IDLE.id() || headSlotItem.itemID == Blocks.PUMPKIN_REDSTONE.id()))
-        {
+        if (this.mc.gameSettings.thirdPersonView.value == 0 && headSlotItem != null && (headSlotItem.itemID == Blocks.PUMPKIN_CARVED_IDLE.id() || headSlotItem.itemID == Blocks.PUMPKIN_REDSTONE.id())) {
             renderPumpkinBlur(width, height);
         }
 
         // Render portal overlay
         final float portalIntensity = MathHelper.lerp(this.mc.thePlayer.prevTimeInPortal, this.mc.thePlayer.timeInPortal, partialTicks);
-        if (portalIntensity > 0.0F)
-        {
+        if (portalIntensity > 0.0F) {
             renderPortalOverlay(portalIntensity, width, height);
         }
 
         for (final HudComponent component : HudComponents.INSTANCE.getComponents()) {
             if (component.isVisible()) {
+                GLRenderer.pushFrame();
                 component.render(this, width - sp * 2, height - sp * 2, partialTicks);
+                GLRenderer.popFrame();
             }
         }
 
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
 
         //Sleep Overlay
         Lighting.disable();
-        GL11.glDisable(32826 /* GL_RESCALE_NORMAL_EXT */);
-          if (this.mc.thePlayer.getSleepTimer() > 0) {
-            GL11.glDisable(2929 /* GL_DEPTH_TEST */);
-            GL11.glDisable(3008 /* GL_ALPHA_TEST */);
+//        GL11.glDisable(GL_RESCALE_NORMAL);
+        if (this.mc.thePlayer.getSleepTimer() > 0) {
+            GLRenderer.disableState(State.DEPTH_TEST);
+//            GL11.glDisable(GL_ALPHA_TEST);
             int i2 = this.mc.thePlayer.getSleepTimer();
             float f3 = (float) i2 / 100F;
-            if (f3 > 1.0F)
-            {
+            if (f3 > 1.0F) {
                 f3 = 1.0F - (float) (i2 - 100) / 10F;
             }
             int j4 = (int) (220F * f3) << 24 | 0x101020;
             drawRect(0, 0, width, height, j4);
-            GL11.glEnable(3008 /* GL_ALPHA_TEST */);
-            GL11.glEnable(2929 /* GL_DEPTH_TEST */);
+//            GL11.glEnable(GL_ALPHA_TEST);
+            GLRenderer.enableState(State.DEPTH_TEST);
         }
 
         //Text Overlays
@@ -176,10 +174,10 @@ public class HudIngame extends Gui
             if (!this.mc.gameSettings.showDebugScreen.value) drawPlayerList(width, height, sp);
 
             if (this.mc.gameSettings.showDebugScreen.value) {
-                glPushMatrix();
-                glEnable(GL_BLEND);
-                glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-                glScalef(DEBUG_SCALE, DEBUG_SCALE, 1);
+                GLRenderer.pushFrame();
+                GLRenderer.enableState(State.BLEND);
+                GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+                GLRenderer.modelM4f().scale(DEBUG_SCALE, DEBUG_SCALE, 1);
 
                 this.debugLine = 0;
                 this.debugLineRight = 0;
@@ -200,9 +198,10 @@ public class HudIngame extends Gui
 
                 this.debugOffsetRight += space;
 
-                drawDebugScreenLineRight(GL11.glGetString(GL11.GL_VENDOR));
-                drawDebugScreenLineRight(GL11.glGetString(GL11.GL_RENDERER));
-                drawDebugScreenLineRight(GL11.glGetString(GL11.GL_VERSION));
+                drawDebugScreenLineRight(GL41.glGetString(GL41.GL_VENDOR));
+                drawDebugScreenLineRight(GL41.glGetString(GL41.GL_RENDERER));
+                drawDebugScreenLineRight(GL41.glGetString(GL41.GL_VERSION));
+                drawDebugScreenLineRight(String.format("OpenGL %s.%s", GL41.glGetInteger(GL41.GL_MAJOR_VERSION), GL41.glGetInteger(GL41.GL_MINOR_VERSION)));
                 drawDebugScreenLineRight("Resolution: " + this.mc.gameWindow.getWidthPixels() + "x" + this.mc.gameWindow.getHeightPixels());
                 drawDebugScreenLineRight("Render Resolution: " + this.mc.renderer.getRenderWidth() + "x" + this.mc.renderer.getRenderHeight());
 
@@ -387,62 +386,39 @@ public class HudIngame extends Gui
                         }
                     }
                 }
-                glPopMatrix();
+                GLRenderer.popFrame();
             }
         }
 
-        if (this.mc.gameSettings.immersiveMode.drawChat())
-        {
-        	drawChat(width, height, sp);
+        if (this.mc.gameSettings.immersiveMode.drawChat()) {
+            drawChat(width, height, sp);
         }
-        
+
         // Adding this mostly to see if the stitcher and dynamic textures are working properly
         if (this.mc.gameSettings.keyToggleTextureAtlas.isPressed()) {
-            Tessellator tessellator = Tessellator.instance;
-
-            TextureRegistry.blockAtlas.bind();
-            
-            
-            int blockW = TextureRegistry.blockAtlas.getAtlasWidth();
-            int blockH = TextureRegistry.blockAtlas.getAtlasHeight();
-            float scaleBlock = (float) (width / 4) /blockW;
-            
-            tessellator.startDrawingQuads();
-            tessellator.addVertexWithUV(20,                        20 + blockH * scaleBlock, 0.0f, 0, 1);
-            tessellator.addVertexWithUV(20 + blockW * scaleBlock,  20 + blockH * scaleBlock, 0.0f, 1, 1);
-            tessellator.addVertexWithUV(20 + blockW * scaleBlock,  20, 0.0f, 1, 0);
-            tessellator.addVertexWithUV(20,                        20, 0.0f, 0, 0);
-            tessellator.draw();
+            GLRenderer.pushFrame();
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
 
-            int blockEndX = (int) (20 + blockW * scaleBlock + 10);
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
 
-            TextureRegistry.itemAtlas.bind();
-            
-            int itemW = TextureRegistry.itemAtlas.getAtlasWidth();
-            int itemH = TextureRegistry.itemAtlas.getAtlasHeight();
-            float scaleItem = (float) (width / 4) / itemW;
-            
-            tessellator.startDrawingQuads();
-            tessellator.addVertexWithUV(blockEndX,                    20 + itemH * scaleItem, 0.0f, 0, 1);
-            tessellator.addVertexWithUV(blockEndX + itemW * scaleItem,20 + itemH * scaleItem, 0.0f, 1, 1);
-            tessellator.addVertexWithUV(blockEndX + itemW * scaleItem,20, 0.0f, 1, 0);
-            tessellator.addVertexWithUV(blockEndX,                    20, 0.0f, 0, 0);
-            tessellator.draw();
+            TextureRegistry.worldAtlas.bind();
 
-            int itemEndX = (int) (blockEndX + itemW * scaleItem + 10);
 
-            TextureRegistry.particleAtlas.bind();
-
-            int particleW = TextureRegistry.particleAtlas.getAtlasWidth();
-            int particleH = TextureRegistry.particleAtlas.getAtlasHeight();
-            float scaleParticle = (float) (width / 4) /particleW;
+            int blockW = TextureRegistry.worldAtlas.getAtlasWidth();
+            int blockH = TextureRegistry.worldAtlas.getAtlasHeight();
+            float scaleBlock = (float) (width - 40) / blockW;
 
             tessellator.startDrawingQuads();
-            tessellator.addVertexWithUV(itemEndX,                            20 + particleH * scaleParticle, 0.0f, 0, 1);
-            tessellator.addVertexWithUV(itemEndX + particleW * scaleParticle,20 + particleH * scaleParticle, 0.0f, 1, 1);
-            tessellator.addVertexWithUV(itemEndX + particleW * scaleParticle,20, 0.0f, 1, 0);
-            tessellator.addVertexWithUV(itemEndX,                            20, 0.0f, 0, 0);
+            tessellator.addVertexWithUV(20, 20 + blockH * scaleBlock, 0.0f, 0, 1);
+            tessellator.addVertexWithUV(20 + blockW * scaleBlock, 20 + blockH * scaleBlock, 0.0f, 1, 1);
+            tessellator.addVertexWithUV(20 + blockW * scaleBlock, 20, 0.0f, 1, 0);
+            tessellator.addVertexWithUV(20, 20, 0.0f, 0, 0);
             tessellator.draw();
+
+            int blockEndX = (int) (20 + blockW * scaleBlock + 10);
+
+            GLRenderer.popFrame();
         }
     }
 
@@ -454,44 +430,39 @@ public class HudIngame extends Gui
 
     private final int debugLineHeight = 10;
 
-    private void drawDebugScreenLine(final CharSequence string, final boolean right, final int line, final int offset)
-    {
+    private void drawDebugScreenLine(final CharSequence string, final boolean right, final int line, final int offset) {
         int width = MathHelper.ceil(this.fontRenderer.stringWidthDouble(string));
         int height = this.debugLineHeight;
         int x = right ? (int) ((this.mc.resolution.getScaledWidthScreenCoords() / DEBUG_SCALE) - width - 2) : 2;
         int y = 3 + line * this.debugLineHeight + offset;
 
-        glDisable(GL_TEXTURE_2D);
-        glColor4d(0.2, 0.2, 0.2, 0.6);
-        final Tessellator t = Tessellator.instance;
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.setColor4f(0.2f, 0.2f, 0.2f, 0.6f);
+        final TessellatorGeneral t = GLRenderer.getTessellator();
 
         t.startDrawingQuads();
         t.drawRectangle(x - 1, y - 1, width + 2, height);
         t.draw();
-
-        glEnable(GL_TEXTURE_2D);
+        GLRenderer.popFrame();
 
 //		fontrenderer.drawStringWithShadow(string, x, y, 0xFFFFFF);
         drawStringNoShadow(this.fontRenderer, string, x, y, 0xFFFFFF);
     }
 
-    private void drawDebugScreenLine(final CharSequence string)
-    {
+    private void drawDebugScreenLine(final CharSequence string) {
         drawDebugScreenLine(string, false, this.debugLine++, this.debugOffset);
     }
 
-    private void drawDebugScreenLineRight(final CharSequence string)
-    {
+    private void drawDebugScreenLineRight(final CharSequence string) {
         drawDebugScreenLine(string, true, this.debugLineRight++, this.debugOffsetRight);
     }
 
     private final List<String> playerListScoreStrings = new ArrayList<>();
 
-    public void drawPlayerList(int screenWidth, int screenHeight, int screenPadding)
-    {
+    public void drawPlayerList(int screenWidth, int screenHeight, int screenPadding) {
         if (!this.mc.isMultiplayerWorld()) return;
-        if (this.mc.gameSettings.playerListPosition.value == 1)
-        {
+        if (this.mc.gameSettings.playerListPosition.value == 1) {
             this.mc.gameSettings.showPlayerList.value = this.mc.gameSettings.keyPlayerList.isPressed() && this.mc.currentScreen == null;
         }
         if (!this.mc.gameSettings.showPlayerList.value) return;
@@ -512,8 +483,7 @@ public class HudIngame extends Gui
 
         this.playerListScoreStrings.clear();
 
-        for (Map.Entry<String, String> a1 : players.entrySet())
-        {
+        for (Map.Entry<String, String> a1 : players.entrySet()) {
             longestNameWidth = Math.max(MathHelper.ceil(this.fontRenderer.stringWidthDouble(a1.getKey())), longestNameWidth);
 
             longestScoreWidth = Math.max(MathHelper.ceil(this.fontRenderer.stringWidthDouble(a1.getValue())), longestScoreWidth);
@@ -536,24 +506,20 @@ public class HudIngame extends Gui
         int listX = 0;
         int listY = screenPadding;
 
-        if (this.mc.gameSettings.playerListPosition.value == 0)
-        {
+        if (this.mc.gameSettings.playerListPosition.value == 0) {
             listX = (screenWidth - width) / 2;
         }
-        if (this.mc.gameSettings.playerListPosition.value == 1)
-        {
+        if (this.mc.gameSettings.playerListPosition.value == 1) {
             listX = (screenWidth - width) / 2;
             listY = screenHeight / 6 + screenPadding;
         }
-        if (this.mc.gameSettings.playerListPosition.value == 2)
-        {
+        if (this.mc.gameSettings.playerListPosition.value == 2) {
             listX = screenWidth - width - screenPadding;
         }
 
         drawRect(listX, listY, listX + width, listY + height, 0xA8080808);
         int i = 0;
-        for (Map.Entry<String, String> a2 : players.entrySet())
-        {
+        for (Map.Entry<String, String> a2 : players.entrySet()) {
             int x = i % columns;
             int y = (i / columns);
 
@@ -563,48 +529,41 @@ public class HudIngame extends Gui
             int scoreStringWidth = MathHelper.ceil(this.fontRenderer.stringWidthDouble(a2.getValue()));
             drawRect(posX - 2, posY - 2, posX + columnWidth + 2, posY + 10, 0xffa5a5a5);
             drawRect(posX - 1, posY - 1, posX + columnWidth + 1, posY + 9, 0xA8080808);
-            drawStringShadow(this.fontRenderer,a2.getKey(), posX, posY, 0xFFFFFF);
-            drawStringShadow(this.fontRenderer,TextFormatting.YELLOW + a2.getValue(), posX + columnWidth - scoreStringWidth, posY, 0xFFFFFF);
+            drawStringShadow(this.fontRenderer, a2.getKey(), posX, posY, 0xFFFFFF);
+            drawStringShadow(this.fontRenderer, TextFormatting.YELLOW + a2.getValue(), posX + columnWidth - scoreStringWidth, posY, 0xFFFFFF);
             i++;
         }
     }
 
-    public void drawRecordPlayingOverlay(int width, int height, float partialTicks)
-    {
-        if (this.recordPlayingUpFor > 0)
-        {
+    public void drawRecordPlayingOverlay(int width, int height, float partialTicks) {
+        if (this.recordPlayingUpFor > 0) {
             float f2 = (float) this.recordPlayingUpFor - partialTicks;
             int j3 = (int) ((f2 * 256F) / 20F);
-            if (j3 > 255)
-            {
+            if (j3 > 255) {
                 j3 = 255;
             }
-            if (j3 > 0)
-            {
-                GL11.glPushMatrix();
-                GL11.glTranslatef((float) width / 2, height - 48, 0.0F);
-                GL11.glEnable(3042 /* GL_BLEND */);
-                GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+            if (j3 > 0) {
+                GLRenderer.pushFrame();
+                GLRenderer.modelM4f().translate((float) width / 2, height - 48, 0.0F);
+                GLRenderer.enableState(State.BLEND);
+                GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
                 int k4 = 0xffffff;
-                if (this.colorString)
-                {
+                if (this.colorString) {
                     k4 = Color.HSBtoRGB(f2 / 50F, 0.7F, 0.6F) & 0xffffff;
                 }
                 drawStringNoShadow(this.fontRenderer, this.recordPlaying, MathHelper.ceil(-this.fontRenderer.stringWidthDouble(this.recordPlaying) / 2), -4, k4 + (j3 << 24));
-                GL11.glDisable(3042 /* GL_BLEND */);
-                GL11.glPopMatrix();
+                GLRenderer.disableState(State.BLEND);
+                GLRenderer.popFrame();
             }
         }
     }
 
-    public void drawChat(int width, int height, int sp)
-    {
+    public void drawChat(int width, int height, int sp) {
         if (this.mc.gameSettings.chatVisibility.value == ChatVisibility.NEVER_SHOW) return;
 //        if(mc.currentScreen instanceof ScreenChat && ((ScreenChat) mc.currentScreen).message.startsWith("/")) return;
         int linesToShow = 10;
         boolean ignoreFadeout = false;
-        if (this.mc.currentScreen instanceof ScreenChat)
-        {
+        if (this.mc.currentScreen instanceof ScreenChat) {
             int acceptableSize = height - 48 - 48;
             linesToShow = acceptableSize / 9;
             ignoreFadeout = true;
@@ -612,58 +571,53 @@ public class HudIngame extends Gui
             return;
         }
 
-        if (this.chatScroll > this.chatMessageList.size() - linesToShow) this.chatScroll = this.chatMessageList.size() - linesToShow;
+        if (this.chatScroll > this.chatMessageList.size() - linesToShow)
+            this.chatScroll = this.chatMessageList.size() - linesToShow;
         if (this.chatScroll < 0) this.chatScroll = 0;
 
-        GL11.glEnable(GL_BLEND);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glDisable(GL_ALPHA_TEST);
-        GL11.glPushMatrix();
-        GL11.glTranslatef(0.0F, height - 48, 0.0F);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+//        GL11.glDisable(GL_ALPHA_TEST);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate(0.0F, height - 48, 0.0F);
         int y = -12;
         for (int i = 0; i < linesToShow; i++) {
             if (this.chatScroll + i >= this.chatMessageList.size()) continue;
             final ChatLine line = this.chatMessageList.get(this.chatScroll + i);
-            if (line.updateCounter >= 190 && !ignoreFadeout)
-            {
+            if (line.updateCounter >= 190 && !ignoreFadeout) {
                 continue;
             }
             double fadeAmount = (double) line.updateCounter / 200D;
             fadeAmount = 1.0D - fadeAmount;
             fadeAmount *= 10D;
-            if (fadeAmount < 0.0D)
-            {
+            if (fadeAmount < 0.0D) {
                 fadeAmount = 0.0D;
             }
-            if (fadeAmount > 1.0D)
-            {
+            if (fadeAmount > 1.0D) {
                 fadeAmount = 1.0D;
             }
             fadeAmount *= fadeAmount;
             int alpha = (int) (255D * fadeAmount);
-            if (ignoreFadeout)
-            {
+            if (ignoreFadeout) {
                 alpha = 255;
             }
-            if (alpha > 0)
-            {
+            if (alpha > 0) {
                 final CharSequence message = line.message;
                 final byte xPad = 2;
-                final int h = MathHelper.ceil( this.fontRenderer.heightOfConstrainedChars(message, MAX_CHAT_WIDTH));
+                final int h = MathHelper.ceil(this.fontRenderer.heightOfConstrainedChars(message, MAX_CHAT_WIDTH));
                 y -= (h + 2);
                 drawRect(xPad + sp, y - sp - 1, xPad + MAX_CHAT_WIDTH, y + h - sp + 1, alpha / 2 << 24);
-                GL11.glEnable(GL_BLEND);
-                this.fontRenderer.renderWidthConstrained(Tessellator.instance, message, xPad + sp, y - sp, MAX_CHAT_WIDTH).setShadow().setColor(0xFFFFFF + (alpha << 24)).call();
+                GLRenderer.enableState(State.BLEND);
+                this.fontRenderer.renderWidthConstrained(message, xPad + sp, y - sp, MAX_CHAT_WIDTH).setShadow().setColor(0xFFFFFF + (alpha << 24)).call();
             }
         }
 
-        GL11.glPopMatrix();
-        GL11.glEnable(3008 /* GL_ALPHA_TEST */);
-        GL11.glDisable(3042 /* GL_BLEND */);
+        GLRenderer.popFrame();
+//        GL11.glEnable(GL_ALPHA_TEST);
+        GLRenderer.disableState(State.BLEND);
     }
 
-    public static String getTimeString(Minecraft mc)
-    {
+    public static String getTimeString(Minecraft mc) {
         long worldTime = mc.currentWorld.getWorldTime();
         int dayLength = Global.DAY_LENGTH_TICKS;
         int dayTime = (int) (worldTime % dayLength);
@@ -679,94 +633,86 @@ public class HudIngame extends Gui
         return hour + ":" + addZero(minute);
     }
 
-    public static String addZero(int i)
-    {
-        if (i < 10)
-        {
+    public static String addZero(int i) {
+        if (i < 10) {
             return "0" + i;
         }
         return String.valueOf(i);
     }
 
-    protected void renderPumpkinBlur(int xSize, int ySize)
-    {
-        GL11.glDisable(2929 /* GL_DEPTH_TEST */);
-        GL11.glDepthMask(false);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glDisable(3008 /* GL_ALPHA_TEST */);
+    protected void renderPumpkinBlur(int xSize, int ySize) {
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.setDepthMask(false);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+//        GL11.glDisable(GL_ALPHA_TEST);
         this.mc.textureManager.loadTexture("/assets/minecraft/textures/misc/pumpkinblur.png").bind();
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertexWithUV(0.0D, ySize, -90D, 0.0D, 1.0D);
         tessellator.addVertexWithUV(xSize, ySize, -90D, 1.0D, 1.0D);
         tessellator.addVertexWithUV(xSize, 0.0D, -90D, 1.0D, 0.0D);
         tessellator.addVertexWithUV(0.0D, 0.0D, -90D, 0.0D, 0.0D);
         tessellator.draw();
-        GL11.glDepthMask(true);
-        GL11.glEnable(2929 /* GL_DEPTH_TEST */);
-        GL11.glEnable(3008 /* GL_ALPHA_TEST */);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setDepthMask(true);
+        GLRenderer.enableState(State.DEPTH_TEST);
+//        GL11.glEnable(GL_ALPHA_TEST);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
     }
 
-    protected void renderVignette(float intensity, int xSize, int ySize)
-    {
+    protected void renderVignette(float intensity, int xSize, int ySize) {
         intensity = MathHelper.clamp(1.0f - intensity, 0.0f, 1.0f);
         this.prevVignetteBrightness += (double) (intensity - this.prevVignetteBrightness) * 0.01D;
-        GL11.glDisable(2929 /* GL_DEPTH_TEST */);
-        GL11.glDepthMask(false);
-        GL11.glBlendFunc(0, 769);
-        GL11.glColor4f(this.prevVignetteBrightness, this.prevVignetteBrightness, this.prevVignetteBrightness, 1.0F);
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.setDepthMask(false);
+        GLRenderer.setBlendFunc(BlendFactor.ZERO, BlendFactor.ONE_MINUS_SRC_COLOR);
+        GLRenderer.setColor4f(this.prevVignetteBrightness, this.prevVignetteBrightness, this.prevVignetteBrightness, 1.0F);
         this.mc.textureManager.loadTexture("/assets/minecraft/textures/misc/vignette.png").bind();
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertexWithUV(0.0D, ySize, -90D, 0.0D, 1.0D);
         tessellator.addVertexWithUV(xSize, ySize, -90D, 1.0D, 1.0D);
         tessellator.addVertexWithUV(xSize, 0.0D, -90D, 1.0D, 0.0D);
         tessellator.addVertexWithUV(0.0D, 0.0D, -90D, 0.0D, 0.0D);
         tessellator.draw();
-        GL11.glDepthMask(true);
-        GL11.glEnable(2929 /* GL_DEPTH_TEST */);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setDepthMask(true);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
     }
 
-    protected void renderPortalOverlay(float intensity, int xSize, int ySize)
-    {
-        if (intensity < 1.0F)
-        {
+    protected void renderPortalOverlay(float intensity, int xSize, int ySize) {
+        if (intensity < 1.0F) {
             intensity *= intensity;
             intensity *= intensity;
             intensity = intensity * 0.8F + 0.2F;
         }
-        GL11.glDisable(3008 /* GL_ALPHA_TEST */);
-        GL11.glDisable(2929 /* GL_DEPTH_TEST */);
-        GL11.glDepthMask(false);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, intensity);
+//        GL11.glDisable(GL_ALPHA_TEST);
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.setDepthMask(false);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, intensity);
         IconCoordinate portal = BlockModelDispatcher.getInstance().getDispatch(Blocks.getBlock(this.mc.thePlayer.portalID)).getOverlayTexture(this.mc.thePlayer.portalColor.blockMeta << 4 | BlockLogicPortal.MASK_COLOR_SET);
         portal.parentAtlas.bind();
         float f1 = (float) portal.getIconUMin();
         float f2 = (float) portal.getIconVMin();
         float f3 = (float) portal.getIconUMax();
         float f4 = (float) portal.getIconVMax();
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertexWithUV(0.0D, ySize, -90D, f1, f4);
         tessellator.addVertexWithUV(xSize, ySize, -90D, f3, f4);
         tessellator.addVertexWithUV(xSize, 0.0D, -90D, f3, f2);
         tessellator.addVertexWithUV(0.0D, 0.0D, -90D, f1, f2);
         tessellator.draw();
-        GL11.glDepthMask(true);
-        GL11.glEnable(2929 /* GL_DEPTH_TEST */);
-        GL11.glEnable(3008 /* GL_ALPHA_TEST */);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setDepthMask(true);
+        GLRenderer.enableState(State.DEPTH_TEST);
+//        GL11.glEnable(GL_ALPHA_TEST);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
     }
 
-    public void updateTick()
-    {
-        if (this.recordPlayingUpFor > 0)
-        {
+    public void updateTick() {
+        if (this.recordPlayingUpFor > 0) {
             this.recordPlayingUpFor--;
         }
         this.updateCounter++;
@@ -776,13 +722,11 @@ public class HudIngame extends Gui
 
     }
 
-    public void clearChatMessages()
-    {
+    public void clearChatMessages() {
         this.chatMessageList.clear();
     }
 
-    public void addChatMessage(final CharSequence s)
-    {
+    public void addChatMessage(final CharSequence s) {
         LOGGER.info("[CHAT] {}", s);
         this.chatMessageList.add(0, new ChatLine(s));
         while (this.chatMessageList.size() > 100) {
@@ -790,15 +734,13 @@ public class HudIngame extends Gui
         }
     }
 
-    public void setRecordPlayingMessage(String s)
-    {
+    public void setRecordPlayingMessage(String s) {
         this.recordPlaying = I18n.getInstance().translateKeyAndFormat("gui.ingame.label.now_playing", s);
         this.recordPlayingUpFor = 60;
         this.colorString = true;
     }
 
-    public static Direction getFacingDirection(Player player)
-    {
+    public static Direction getFacingDirection(Player player) {
         return directions[(MathHelper.floor((double) ((player.yRot * 4F) / 360F) + 0.5D) + 2) & 3];
     }
 }
\ No newline at end of file
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/HudIngameDoom.java b/game/client/src/main/java/net/minecraft/client/gui/hud/HudIngameDoom.java
index de700eb74..9293c965c 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/HudIngameDoom.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/HudIngameDoom.java
@@ -4,21 +4,22 @@ import it.unimi.dsi.fastutil.ints.IntArrayList;
 import it.unimi.dsi.fastutil.ints.IntList;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ScreenPhotoMode;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.enums.HumanArmorShape;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.net.command.TextFormatting;
-import org.lwjgl.opengl.GL11;
 
 public class HudIngameDoom
-    extends HudIngame
-{
+    extends HudIngame {
     private static final int[] NUMBER_WIDTHS = {
-            9, 7, 9, 9, 11, 9, 9, 9, 9, 9
+        9, 7, 9, 9, 11, 9, 9, 9, 9, 9
     };
     private static final int[] NUMBER_US = {
-            0, 9, 16, 25, 34, 45, 54, 63, 72, 81
+        0, 9, 16, 25, 34, 45, 54, 63, 72, 81
     };
 
     public HudIngameDoom(Minecraft minecraft) {
@@ -26,35 +27,31 @@ public class HudIngameDoom
     }
 
     @Override
-    public void renderGameOverlay(float partialTicks, boolean flag, int mouseX, int mouseY)
-    {
-        if (mc.currentScreen instanceof ScreenPhotoMode) return;
+    public void renderGameOverlay(float partialTicks, boolean flag, int mouseX, int mouseY) {
+        if (this.mc.currentScreen instanceof ScreenPhotoMode) return;
 
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
-        mc.worldRenderer.setupScaledResolution();
+        this.mc.worldRenderer.setupScaledResolution();
 
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
 
         // Render vignette
-        if (mc.gameSettings.immersiveMode.drawVignette() && mc.gameSettings.vignette.value)
-        {
-            renderVignette(mc.thePlayer.getBrightness(partialTicks), width, height);
+        if (this.mc.gameSettings.immersiveMode.drawVignette() && this.mc.gameSettings.vignette.value) {
+            renderVignette(this.mc.thePlayer.getBrightness(partialTicks), width, height);
         }
 
         // Render pumpkin overlay
-        ItemStack headSlotItem = mc.thePlayer.getItemInArmorSlot(HumanArmorShape.HEAD);
-        if (mc.gameSettings.thirdPersonView.value == 0 && headSlotItem != null && (headSlotItem.itemID == Blocks.PUMPKIN_CARVED_IDLE.id() || headSlotItem.itemID == Blocks.PUMPKIN_REDSTONE.id()))
-        {
+        ItemStack headSlotItem = this.mc.thePlayer.getItemInArmorSlot(HumanArmorShape.HEAD);
+        if (this.mc.gameSettings.thirdPersonView.value == 0 && headSlotItem != null && (headSlotItem.itemID == Blocks.PUMPKIN_CARVED_IDLE.id() || headSlotItem.itemID == Blocks.PUMPKIN_REDSTONE.id())) {
             renderPumpkinBlur(width, height);
         }
 
         // Render portal overlay
-        float portalIntensity = mc.thePlayer.prevTimeInPortal + (mc.thePlayer.timeInPortal - mc.thePlayer.prevTimeInPortal) * partialTicks;
-        if (portalIntensity > 0.0F)
-        {
+        float portalIntensity = this.mc.thePlayer.prevTimeInPortal + (this.mc.thePlayer.timeInPortal - this.mc.thePlayer.prevTimeInPortal) * partialTicks;
+        if (portalIntensity > 0.0F) {
             renderPortalOverlay(portalIntensity, width, height);
         }
 
@@ -67,103 +64,87 @@ public class HudIngameDoom
         drawHotbarIndicator();
         drawStacks();
 
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
 
-        if (mc.gameSettings.immersiveMode.drawCrosshair() && mc.gameSettings.thirdPersonView.value == 0)
-        {
+        if (this.mc.gameSettings.immersiveMode.drawCrosshair() && this.mc.gameSettings.thirdPersonView.value == 0) {
             // Render crosshair
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glBlendFunc(GL11.GL_ONE_MINUS_DST_COLOR, GL11.GL_ONE_MINUS_SRC_COLOR);
-            drawGuiIcon(width/2 - 7, height/2 - 7, 15, 15, TextureRegistry.getTexture("minecraft:gui/hud/crosshair"));
-            GL11.glDisable(GL11.GL_BLEND);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.ONE_MINUS_DST_COLOR, BlendFactor.ONE_MINUS_SRC_COLOR);
+            drawGuiIcon(width / 2 - 7, height / 2 - 7, 15, 15, TextureRegistry.getTexture("minecraft:gui/hud/crosshair"));
+            GLRenderer.disableState(State.BLEND);
         }
     }
 
-    private void drawBackground()
-    {
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+    private void drawBackground() {
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/hud/doom.png").bind();
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/hud/doom.png").bind();
 
         // Draw main hotbar
-        drawTexturedModalRectDouble(width / 2d - 197d, height - 43, 0, 0, 197, 43, 1/256d, 1/256d, 0);
-        drawTexturedModalRectDouble(width / 2d, height - 43, 0, 43, 197, 43, 1/256d, 1/256d, 0);
+        drawTexturedModalRectDouble(width / 2d - 197d, height - 43, 0, 0, 197, 43, 1 / 256d, 1 / 256d, 0);
+        drawTexturedModalRectDouble(width / 2d, height - 43, 0, 43, 197, 43, 1 / 256d, 1 / 256d, 0);
 
         // Draw sides
-        int loops = (int) Math.ceil((((width/2d) - 197)/128));
+        int loops = (int) Math.ceil((((width / 2d) - 197) / 128));
         for (int i = 0; i < loops; i++) {
-            drawTexturedModalRectDouble((width / 2d) - 197 - 128 * (i + 1), height - 43, 0, 86, 128, 43, 128, 43, 1/256f, 1/256f);
-            drawTexturedModalRectDouble((width / 2d) + 197d + 128 * i, height - 43, 0, 129 - 43, 128, 43, 128, 43, 1/256f, 1/256f);
+            drawTexturedModalRectDouble((width / 2d) - 197 - 128 * (i + 1), height - 43, 0, 86, 128, 43, 128, 43, 1 / 256f, 1 / 256f);
+            drawTexturedModalRectDouble((width / 2d) + 197d + 128 * i, height - 43, 0, 129 - 43, 128, 43, 128, 43, 1 / 256f, 1 / 256f);
         }
     }
 
-    private void drawFace()
-    {
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+    private void drawFace() {
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
         Face face = Face.NEUTRAL;
-        if (mc.thePlayer.getGamemode().isPlayerInvulnerable())
-        {
+        if (this.mc.thePlayer.getGamemode().isPlayerInvulnerable()) {
             face = Face.GOD;
-        }
-        else if (mc.thePlayer.getHealth() == 0)
-        {
+        } else if (this.mc.thePlayer.getHealth() == 0) {
             face = Face.DEAD;
-        }
-        else if (mc.thePlayer.hurtTime > 0)
-        {
+        } else if (this.mc.thePlayer.hurtTime > 0) {
             face = Face.PAIN;
-        }
-        else if (updateCounter % 200 > 175)
-        {
+        } else if (this.updateCounter % 200 > 175) {
             face = Face.LOOK_RIGHT;
-        }
-        else if (updateCounter % 200 > 150)
-        {
+        } else if (this.updateCounter % 200 > 150) {
             face = Face.LOOK_LEFT;
         }
 
         drawTexturedModalRect(width / 2 - 16, height - 36, face.u, face.v, 32, 32);
     }
 
-    private void drawAmmo()
-    {
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+    private void drawAmmo() {
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
-        ItemStack stack = mc.thePlayer.getHeldItem();
+        ItemStack stack = this.mc.thePlayer.getHeldItem();
         if (stack == null) return;
         int ammo = stack.stackSize;
 
         drawNumber(ammo, width / 2 - 160, height - 32);
     }
 
-    private void drawHealth()
-    {
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+    private void drawHealth() {
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
-        float healthPercentage = mc.thePlayer.getHealth() / (float)mc.thePlayer.getMaxHealth();
-        int health = (int)(healthPercentage * 100);
+        float healthPercentage = this.mc.thePlayer.getHealth() / (float) this.mc.thePlayer.getMaxHealth();
+        int health = (int) (healthPercentage * 100);
         if (health < 0) health = 0;
 
         drawNumber(health, width / 2 - 116, height - 32);
     }
 
-    private void drawNumber(int i, int x, int y)
-    {
-        GL11.glColor4f(1f, 1f, 1f, 1f);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/hud/doom.png").bind();
+    private void drawNumber(int i, int x, int y) {
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/hud/doom.png").bind();
 
         IntList parts = new IntArrayList();
 
         int prev = 0;
         int mult = 1;
-        while (i / mult != 0)
-        {
+        while (i / mult != 0) {
             int lowerDigits = i % (mult * 10);
             int digit = lowerDigits - prev;
             prev += digit;
@@ -182,17 +163,14 @@ public class HudIngameDoom
         }
     }
 
-    private void drawArmsButtons()
-    {
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+    private void drawArmsButtons() {
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
         int i = 1;
-        int activeSlot = mc.thePlayer.inventory.getCurrentItemIndex() % 9;
-        for (int y = 0; y < 2; y++)
-        {
-            for (int x = 0; x < 5; x++)
-            {
+        int activeSlot = this.mc.thePlayer.inventory.getCurrentItemIndex() % 9;
+        for (int y = 0; y < 2; y++) {
+            for (int x = 0; x < 5; x++) {
                 if (i >= 10) continue;
 
                 int px = width / 2 - 90 + 14 * x;
@@ -205,70 +183,63 @@ public class HudIngameDoom
         }
     }
 
-    private void drawArmsButton(int x, int y, int number, boolean active)
-    {
-        GL11.glColor4f(1f, 1f, 1f, 1f);
-        mc.textureManager.loadTexture("/assets/minecraft/textures/gui/hud/doom.png").bind();
+    private void drawArmsButton(int x, int y, int number, boolean active) {
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+        this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/hud/doom.png").bind();
 
         int u = 13;
         int v = 196;
         int textColor = 0xFFFFFFFF;
 
-        if (active)
-        {
+        if (active) {
             u = 0;
             textColor = 0xFFA0A0A0;
         }
 
         drawTexturedModalRect(x, y, u, v, 13, 13);
-        drawStringShadow(fontRenderer, Integer.toString(number % 10), x + 4, y + 3, textColor);
+        drawStringShadow(this.fontRenderer, Integer.toString(number % 10), x + 4, y + 3, textColor);
     }
 
-    private void drawArmor()
-    {
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+    private void drawArmor() {
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
-        float armorPercentage = mc.thePlayer.getPlayerProtectionAmount() / 20f;
-        int armor = (int)(armorPercentage * 100);
+        float armorPercentage = this.mc.thePlayer.getPlayerProtectionAmount() / 20f;
+        int armor = (int) (armorPercentage * 100);
 
         drawNumber(armor, width / 2 + 48, height - 32);
     }
 
-    private void drawHotbarIndicator()
-    {
-//        GL11.glColor4f(1f, 1f, 1f, 1f);
+    private void drawHotbarIndicator() {
+//        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
 //        GL11.glBindTexture(GL11.GL_TEXTURE_2D, mc.renderEngine.getTexture("/assets/minecraft/textures/gui/doom.png"));
 
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
         int x = width / 2 + 76;
         int y = height - 36;
 
-        int selectedHotbar = ((mc.thePlayer.inventory.getHotbarOffset() + 27) % 36) / 9;
+        int selectedHotbar = ((this.mc.thePlayer.inventory.getHotbarOffset() + 27) % 36) / 9;
 
         drawTexturedModalRect(x, y + 9 * selectedHotbar, 0, 129, 6, 6);
     }
 
-    private void drawStacks()
-    {
-        int width = mc.resolution.getScaledWidthScreenCoords();
-        int height = mc.resolution.getScaledHeightScreenCoords();
+    private void drawStacks() {
+        int width = this.mc.resolution.getScaledWidthScreenCoords();
+        int height = this.mc.resolution.getScaledHeightScreenCoords();
 
-        int currentItem = mc.thePlayer.inventory.getCurrentItemIndex();
-        int wrappedCurrentItem = mc.thePlayer.inventory.getCurrentItemIndex() % 9;
+        int currentItem = this.mc.thePlayer.inventory.getCurrentItemIndex();
+        int wrappedCurrentItem = this.mc.thePlayer.inventory.getCurrentItemIndex() % 9;
 
         int offset = 0;
-        if (wrappedCurrentItem >= 5)
-        {
+        if (wrappedCurrentItem >= 5) {
             offset = 3 - (8 - wrappedCurrentItem);
         }
 
         int q = 0;
-        for (int i = currentItem - offset; i < currentItem - offset + 4; i++)
-        {
-            ItemStack stack = mc.thePlayer.inventory.getItem(i);
+        for (int i = currentItem - offset; i < currentItem - offset + 4; i++) {
+            ItemStack stack = this.mc.thePlayer.inventory.getItem(i);
             int x = width / 2 + 94;
             int y = height - 37 + q * 9;
 
@@ -278,48 +249,37 @@ public class HudIngameDoom
         }
     }
 
-    private void drawItemStack(ItemStack stack, int x, int y, boolean selected)
-    {
+    private void drawItemStack(ItemStack stack, int x, int y, boolean selected) {
         if (stack == null) return;
         String name = stack.getDisplayName();
-        
+
         if (name.length() >= 10) name = name.substring(0, 10);
         name = name.toUpperCase();
-        if (selected)
-        {
-            drawStringShadow(fontRenderer, TextFormatting.get(stack.getDisplayColor()) + name, x, y, 0xFFFFFFFF);
-        }
-        else
-        {
-            drawStringNoShadow(fontRenderer, name, x, y, 0xFF404040);
+        if (selected) {
+            drawStringShadow(this.fontRenderer, TextFormatting.get(stack.getDisplayColor()) + name, x, y, 0xFFFFFFFF);
+        } else {
+            drawStringNoShadow(this.fontRenderer, name, x, y, 0xFF404040);
         }
 
         int maxStackSize = stack.getMaxStackSize();
         int stackSize = stack.stackSize;
 
         // Draw stack size
-        if (stackSize < 10)
-        {
-            drawStringShadow(fontRenderer, Integer.toString(stackSize), x + 70, y, 0xFFFFFFA0);
-        }
-        else
-        {
-            drawStringShadow(fontRenderer, Integer.toString(stackSize), x + 64, y, 0xFFFFFFA0);
+        if (stackSize < 10) {
+            drawStringShadow(this.fontRenderer, Integer.toString(stackSize), x + 70, y, 0xFFFFFFA0);
+        } else {
+            drawStringShadow(this.fontRenderer, Integer.toString(stackSize), x + 64, y, 0xFFFFFFA0);
         }
 
         // Draw max stack size
-        if (maxStackSize < 10)
-        {
-            drawStringShadow(fontRenderer, Integer.toString(maxStackSize), x + 88, y, 0xFFFFFFA0);
-        }
-        else
-        {
-            drawStringShadow(fontRenderer, Integer.toString(maxStackSize), x + 82, y, 0xFFFFFFA0);
+        if (maxStackSize < 10) {
+            drawStringShadow(this.fontRenderer, Integer.toString(maxStackSize), x + 88, y, 0xFFFFFFA0);
+        } else {
+            drawStringShadow(this.fontRenderer, Integer.toString(maxStackSize), x + 82, y, 0xFFFFFFA0);
         }
     }
 
-    private enum Face
-    {
+    private enum Face {
         NEUTRAL(0, 224),
         LOOK_RIGHT(32, 224),
         LOOK_LEFT(64, 224),
@@ -332,8 +292,7 @@ public class HudIngameDoom
         public final int u;
         public final int v;
 
-        Face(int u, int v)
-        {
+        Face(int u, int v) {
             this.u = u;
             this.v = v;
         }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentArmorBar.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentArmorBar.java
index 43db58db0..0f1359e05 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentArmorBar.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentArmorBar.java
@@ -1,23 +1,24 @@
 package net.minecraft.client.gui.hud.component;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import org.lwjgl.opengl.GL11;
 
 public class HudComponentArmorBar
     extends HudComponentMovable {
     private final IconCoordinate armor_empty;
     private final IconCoordinate armor_half;
     private final IconCoordinate armor_full;
+
     public HudComponentArmorBar(String key, Layout layout) {
         super(key, 81, 10, layout);
-        armor_empty = TextureRegistry.getTexture("minecraft:gui/hud/armor_empty");
-        armor_half = TextureRegistry.getTexture("minecraft:gui/hud/armor_half");
-        armor_full = TextureRegistry.getTexture("minecraft:gui/hud/armor_full");
+        this.armor_empty = TextureRegistry.getTexture("minecraft:gui/hud/armor_empty");
+        this.armor_half = TextureRegistry.getTexture("minecraft:gui/hud/armor_half");
+        this.armor_full = TextureRegistry.getTexture("minecraft:gui/hud/armor_full");
     }
 
     @Override
@@ -31,28 +32,24 @@ public class HudComponentArmorBar
         int y = this.getLayout().getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.disableState(State.BLEND);
 
         int armorValue = mc.thePlayer.getPlayerProtectionAmount();
         for (int i = 0; i < 10; i++) {
-            if (armorValue > 0)
-            {
+            if (armorValue > 0) {
                 int xArmor = x + getXSize() - i * 8 - 9;
-                if (i * 2 + 1 < armorValue)
-                {
+                if (i * 2 + 1 < armorValue) {
                     // Full armor icon
-                    hud.drawGuiIcon(xArmor, y, 9, 9, armor_full);
+                    hud.drawGuiIcon(xArmor, y, 9, 9, this.armor_full);
                 }
-                if (i * 2 + 1 == armorValue)
-                {
+                if (i * 2 + 1 == armorValue) {
                     // Half armor icon
-                    hud.drawGuiIcon(xArmor, y, 9, 9, armor_half);
+                    hud.drawGuiIcon(xArmor, y, 9, 9, this.armor_half);
                 }
-                if (i * 2 + 1 > armorValue)
-                {
+                if (i * 2 + 1 > armorValue) {
                     // Empty armor icon
-                    hud.drawGuiIcon(xArmor, y, 9, 9, armor_empty);
+                    hud.drawGuiIcon(xArmor, y, 9, 9, this.armor_empty);
                 }
             }
         }
@@ -64,26 +61,23 @@ public class HudComponentArmorBar
         int y = layout.getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.disableState(State.BLEND);
 
         int armorValue = 11;
         for (int i = 0; i < 10; i++) {
             int xArmor = x + getXSize() - i * 8 - 9;
-            if (i * 2 + 1 < armorValue)
-            {
+            if (i * 2 + 1 < armorValue) {
                 // Full armor icon
-                gui.drawGuiIcon(xArmor, y, 9, 9, armor_full);
+                gui.drawGuiIcon(xArmor, y, 9, 9, this.armor_full);
             }
-            if (i * 2 + 1 == armorValue)
-            {
+            if (i * 2 + 1 == armorValue) {
                 // Half armor icon
-                gui.drawGuiIcon(xArmor, y, 9, 9, armor_half);
+                gui.drawGuiIcon(xArmor, y, 9, 9, this.armor_half);
             }
-            if (i * 2 + 1 > armorValue)
-            {
+            if (i * 2 + 1 > armorValue) {
                 // Empty armor icon
-                gui.drawGuiIcon(xArmor, y, 9, 9, armor_empty);
+                gui.drawGuiIcon(xArmor, y, 9, 9, this.armor_empty);
             }
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentArmorDurability.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentArmorDurability.java
index ac445def4..306b6607d 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentArmorDurability.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentArmorDurability.java
@@ -1,21 +1,18 @@
 package net.minecraft.client.gui.hud.component;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.enums.HumanArmorShape;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.item.Items;
 
-import static org.lwjgl.opengl.GL11.*;
-
 public class HudComponentArmorDurability
-    extends HudComponentMovable
-{
-    private static final ItemStack[] PREVIEW_STACKS = new ItemStack[] {
+    extends HudComponentMovable {
+    private static final ItemStack[] PREVIEW_STACKS = new ItemStack[]{
         Items.ARMOR_BOOTS_DIAMOND.getDefaultStack(),
         Items.ARMOR_LEGGINGS_DIAMOND.getDefaultStack(),
         Items.ARMOR_CHESTPLATE_DIAMOND.getDefaultStack(),
@@ -41,25 +38,22 @@ public class HudComponentArmorDurability
         int x = this.getLayout().getComponentX(this, xSizeScreen);
         int y = this.getLayout().getComponentY(this, ySizeScreen);
 
-        for (int i = 0; i < mc.thePlayer.getNumArmorSlots(); i++)
-        {
+        for (int i = 0; i < mc.thePlayer.getNumArmorSlots(); i++) {
             ItemStack stack = mc.thePlayer.getItemInArmorSlot(HumanArmorShape.values()[i]);
 
-            if (stack != null)
-            {
+            if (stack != null) {
                 int xx = x + 2;
                 int yy = y + 48 - i * 16;
-                ItemModelDispatcher.getInstance().getDispatch(stack).renderGui(Tessellator.instance, null, stack, xx, yy, 1f, 1.0f, partialTick);
-                glDisable(GL_LIGHTING);
+                ItemModelDispatcher.getInstance().getDispatch(stack).renderGui(GLRenderer.getTessellator(), null, stack, xx, yy, LightmapHelper.getLightmapCoord(15, 15), partialTick);
+//                glDisable(GL_LIGHTING);
 
-                if (stack.isItemStackDamageable())
-                {
+                if (stack.isItemStackDamageable()) {
                     float durability = (stack.getMaxDamage() - stack.getMetadata()) / (float) stack.getMaxDamage();
 
                     int l = (int) (durability * 255);
                     final int i1 = 255 - l << 16 | l << 8;
 
-                    mc.font.render(Tessellator.instance, String.valueOf((stack.getMaxDamage() - stack.getMetadata()) + 1), xx + 20, yy + 4).setShadow().setColor(i1).call();
+                    mc.font.render(String.valueOf((stack.getMaxDamage() - stack.getMetadata()) + 1), xx + 20, yy + 4).setShadow().setColor(i1).call();
                 }
             }
         }
@@ -70,23 +64,21 @@ public class HudComponentArmorDurability
         int x = this.getLayout().getComponentX(this, xSizeScreen);
         int y = this.getLayout().getComponentY(this, ySizeScreen);
 
-        for (int i = 0; i < PREVIEW_STACKS.length; i++)
-        {
+        for (int i = 0; i < PREVIEW_STACKS.length; i++) {
             ItemStack stack = PREVIEW_STACKS[i];
 
             int xx = x + 2;
             int yy = y + 48 - i * 16;
-            ItemModelDispatcher.getInstance().getDispatch(stack).renderGui(Tessellator.instance, null, stack, xx, yy, 1f, 1.0f, 0.0f);
-            glDisable(GL_LIGHTING);
+            ItemModelDispatcher.getInstance().getDispatch(stack).renderGui(GLRenderer.getTessellator(), null, stack, xx, yy, LightmapHelper.getLightmapCoord(15, 15), 0.0f);
+//            glDisable(GL_LIGHTING);
 
-            if (stack.isItemStackDamageable())
-            {
+            if (stack.isItemStackDamageable()) {
                 float durability = (stack.getMaxDamage() - stack.getMetadata()) / (float) stack.getMaxDamage();
 
                 int l = (int) (durability * 255);
                 final int i1 = 255 - l << 16 | l << 8;
 
-                mc.font.render(Tessellator.instance, String.valueOf((stack.getMaxDamage() - stack.getMetadata()) + 1), xx + 20, yy + 4).setShadow().setColor(i1).call();
+                mc.font.render(String.valueOf((stack.getMaxDamage() - stack.getMetadata()) + 1), xx + 20, yy + 4).setShadow().setColor(i1).call();
             }
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentCrosshair.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentCrosshair.java
index 12d145ef3..080de3209 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentCrosshair.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentCrosshair.java
@@ -1,9 +1,11 @@
 package net.minecraft.client.gui.hud.component;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import org.lwjgl.opengl.GL11;
 
@@ -24,13 +26,13 @@ public class HudComponentCrosshair
         int y = this.getLayout().getComponentY(this, ySizeScreen);
 
         // Setup crosshair texture
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
 
         // Render crosshair
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_ONE_MINUS_DST_COLOR, GL11.GL_ONE_MINUS_SRC_COLOR);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.ONE_MINUS_DST_COLOR, BlendFactor.ONE_MINUS_SRC_COLOR);
         hud.drawGuiIcon(x, y, 15, 15, TextureRegistry.getTexture("minecraft:gui/hud/crosshair"));
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.disableState(State.BLEND);
     }
 
     @Override
@@ -39,7 +41,7 @@ public class HudComponentCrosshair
         int y = layout.getComponentY(this, ySizeScreen);
 
         // Setup crosshair texture
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
 
         // Render crosshair
         gui.drawGuiIcon(x, y, 15, 15, TextureRegistry.getTexture("minecraft:gui/hud/crosshair"));
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentFireBar.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentFireBar.java
index 89ea81875..d1c35f580 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentFireBar.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentFireBar.java
@@ -1,11 +1,11 @@
 package net.minecraft.client.gui.hud.component;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import org.lwjgl.opengl.GL11;
 
 public class HudComponentFireBar
     extends HudComponentMovable {
@@ -24,11 +24,11 @@ public class HudComponentFireBar
         int y = this.getLayout().getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         float fire = (float) mc.thePlayer.remainingFireTicks / (float) mc.thePlayer.maxFireTicks;
-        int fireBar = (int) Math.min(fire * 20,20);
+        int fireBar = (int) Math.min(fire * 20, 20);
 
         for (int i = 0; i < fireBar / 2; i++) {
             hud.drawGuiIcon(x + i * 8, y, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/fire"));
@@ -41,8 +41,8 @@ public class HudComponentFireBar
         int y = layout.getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         int fireBar = 11;
         for (int i = 0; i < fireBar / 2; i++) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHealthBar.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHealthBar.java
index 312cf9a30..fced9f1d9 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHealthBar.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHealthBar.java
@@ -3,6 +3,8 @@ package net.minecraft.client.gui.hud.component;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicEdible;
@@ -11,7 +13,6 @@ import net.minecraft.core.item.ItemFood;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.player.gamemode.Gamemode;
 import net.minecraft.core.util.phys.HitResult;
-import org.lwjgl.opengl.GL11;
 
 import java.util.Random;
 
@@ -34,8 +35,8 @@ public class HudComponentHealthBar
         int y = this.getLayout().getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         boolean heartsFlash = (mc.thePlayer.heartsFlashTime / 3) % 2 == 1;
         if (mc.thePlayer.heartsFlashTime < 10) {
@@ -113,8 +114,8 @@ public class HudComponentHealthBar
         int y = layout.getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         int health = 11;
         for (int i = 0; i < 10; i++) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHeldItemCount.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHeldItemCount.java
index ad85cf818..8ead0c6b7 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHeldItemCount.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHeldItemCount.java
@@ -1,22 +1,20 @@
 package net.minecraft.client.gui.hud.component;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
 import net.minecraft.client.render.Lighting;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.item.ItemStack;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 
-import java.awt.*;
+import java.awt.Color;
 
 public class HudComponentHeldItemCount
-    extends HudComponentMovable
-{
+    extends HudComponentMovable {
     private static final ItemStack PREVIEW_ITEM = new ItemStack(Blocks.COBBLE_BASALT, 53);
 
     public HudComponentHeldItemCount(String key, Layout layout) {
@@ -42,47 +40,39 @@ public class HudComponentHeldItemCount
         int yy = y + 3;
 
         ItemStack heldItemStack = mc.thePlayer.inventory.getCurrentItem();
-        if (heldItemStack != null)
-        {
+        if (heldItemStack != null) {
             boolean renderItem;
 
-            if (heldItemStack.isItemStackDamageable())
-            {
+            if (heldItemStack.isItemStackDamageable()) {
                 renderItem = true;
                 float durability = (heldItemStack.getMaxDamage() - heldItemStack.getMetadata()) / (float) heldItemStack.getMaxDamage();
 
-                final int color = 0xFF000000 + Color.HSBtoRGB(durability/3F, 1f, 1f);
+                final int color = 0xFF000000 + Color.HSBtoRGB(durability / 3F, 1f, 1f);
                 int remainingDurability = (heldItemStack.getMaxDamage() - heldItemStack.getMetadata()) + 1;
-                mc.font.render(Tessellator.instance, remainingDurability, xx + 18, yy + 4).setShadow().setColor(color).call();
-            }
-            else
-            {
+                mc.font.render(remainingDurability, xx + 18, yy + 4).setShadow().setColor(color).call();
+            } else {
                 int itemCount = 0;
                 int stackCount = 0;
-                for (int i = 0; i < mc.thePlayer.inventory.getContainerSize(); i++)
-                {
+                for (int i = 0; i < mc.thePlayer.inventory.getContainerSize(); i++) {
                     ItemStack itemStack = mc.thePlayer.inventory.getItem(i);
-                    if (itemStack != null && itemStack.itemID == heldItemStack.itemID && itemStack.getMetadata() == heldItemStack.getMetadata())
-                    {
+                    if (itemStack != null && itemStack.itemID == heldItemStack.itemID && itemStack.getMetadata() == heldItemStack.getMetadata()) {
                         itemCount += itemStack.stackSize;
                         stackCount++;
                     }
                 }
                 renderItem = stackCount >= 1;
 
-                if (renderItem)
-                {
-                    mc.font.render(Tessellator.instance, itemCount, xx + 18, yy + 4).setShadow().setColor(0xFFFFFFFF).call();
+                if (renderItem) {
+                    mc.font.render(itemCount, xx + 18, yy + 4).setShadow().setColor(0xFFFFFFFF).call();
                 }
             }
 
-            if (renderItem)
-            {
-                GL11.glEnable(GL11.GL_DEPTH_TEST);
-                GL11.glDisable(GL11.GL_BLEND);
-                GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+            if (renderItem) {
+                GLRenderer.enableState(State.DEPTH_TEST);
+                GLRenderer.disableState(State.BLEND);
+//                GL11.glEnable(GL12.GL_RESCALE_NORMAL);
                 Lighting.enableInventoryLight();
-                ItemModelDispatcher.getInstance().getDispatch(heldItemStack).renderGui(Tessellator.instance, null, heldItemStack, xx, yy, 1f, 1f, partialTick);
+                ItemModelDispatcher.getInstance().getDispatch(heldItemStack).renderGui(GLRenderer.getTessellator(), null, heldItemStack, xx, yy, LightmapHelper.getLightmapCoord(15, 15), partialTick);
                 Lighting.disable();
             }
         }
@@ -99,13 +89,13 @@ public class HudComponentHeldItemCount
         ItemStack heldItemStack = PREVIEW_ITEM;
         int itemCount = heldItemStack.stackSize;
 
-        mc.font.render(Tessellator.instance, itemCount, xx + 18, yy + 4).setShadow().setColor(0xFFFFFFFF).call();
+        mc.font.render(itemCount, xx + 18, yy + 4).setShadow().setColor(0xFFFFFFFF).call();
 
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.disableState(State.BLEND);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
         Lighting.enableInventoryLight();
-        ItemModelDispatcher.getInstance().getDispatch(heldItemStack).renderGui(Tessellator.instance, null, heldItemStack, xx, yy, 1f, 1f, 0.0f);
+        ItemModelDispatcher.getInstance().getDispatch(heldItemStack).renderGui(GLRenderer.getTessellator(), null, heldItemStack, xx, yy, LightmapHelper.getLightmapCoord(15, 15), 0.0f);
         Lighting.disable();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHotbar.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHotbar.java
index 6f86881da..a57d71a1e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHotbar.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentHotbar.java
@@ -5,23 +5,23 @@ import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
 import net.minecraft.client.render.Lighting;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.Scissor;
 import net.minecraft.client.render.item.model.ItemModel;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.player.inventory.container.ContainerInventory;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 
 import static net.minecraft.client.Minecraft.HOTBAR_SWAP_ANIMATION_LENGTH_TICKS;
 
 public class HudComponentHotbar
     extends HudComponentMovable {
-    private static final ItemStack[] PREVIEW_ITEMS = new ItemStack[] {
+    private static final ItemStack[] PREVIEW_ITEMS = new ItemStack[]{
         new ItemStack(Blocks.STONE),
         new ItemStack(Blocks.COBBLE_STONE),
         new ItemStack(Blocks.BRICK_CLAY),
@@ -61,7 +61,7 @@ public class HudComponentHotbar
         ContainerInventory inv = mc.thePlayer.inventory;
 
         // Setup hotbar texture
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
 
         // Render hotbar
         hud.drawGuiIcon(x + 5, y, 182, 22, TextureRegistry.getTexture("minecraft:gui/hud/hotbar"));
@@ -72,9 +72,9 @@ public class HudComponentHotbar
         hud.drawGuiIcon(x, y, 6, 22, coordinate);
 
         // Setup items
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.enableState(State.BLEND);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
         Lighting.enableInventoryLight();
         int lastHotbarStart = (mc.thePlayer.inventory.getHotbarOffset() + 27) % 36;
         int nextHotbarStart = (mc.thePlayer.inventory.getHotbarOffset() + 9) % 36;
@@ -88,30 +88,30 @@ public class HudComponentHotbar
                 // Draw last hotbar
                 for (int itemIndex = 0; itemIndex < 9; itemIndex++) {
                     int itemX = x + 8 + itemIndex * 20;
-                    int itemY = y + 3 - 22 + (int) (22 * (mc.hotbarSwapAnimationProgress - partialTick)/ HOTBAR_SWAP_ANIMATION_LENGTH_TICKS);
+                    int itemY = y + 3 - 22 + (int) (22 * (mc.hotbarSwapAnimationProgress - partialTick) / HOTBAR_SWAP_ANIMATION_LENGTH_TICKS);
                     renderInventorySlot(mc, itemIndex + lastHotbarStart, itemX, itemY, partialTick);
                 }
 
                 // Render hotbar items
-                GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+                GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
                 for (int itemIndex = 0; itemIndex < 9; itemIndex++) {
                     int itemX = x + 8 + itemIndex * 20;
-                    int itemY = y + 3 + (int) (22 * (mc.hotbarSwapAnimationProgress - partialTick)/ HOTBAR_SWAP_ANIMATION_LENGTH_TICKS);
+                    int itemY = y + 3 + (int) (22 * (mc.hotbarSwapAnimationProgress - partialTick) / HOTBAR_SWAP_ANIMATION_LENGTH_TICKS);
                     renderInventorySlot(mc, itemIndex + mc.thePlayer.inventory.getHotbarOffset(), itemX, itemY, partialTick);
                 }
             } else {
                 // Draw next hotbar
                 for (int itemIndex = 0; itemIndex < 9; itemIndex++) {
                     int itemX = x + 8 + itemIndex * 20;
-                    int itemY = y + 3 + 22 + (int) (22 * (mc.hotbarSwapAnimationProgress + partialTick)/ HOTBAR_SWAP_ANIMATION_LENGTH_TICKS);
+                    int itemY = y + 3 + 22 + (int) (22 * (mc.hotbarSwapAnimationProgress + partialTick) / HOTBAR_SWAP_ANIMATION_LENGTH_TICKS);
                     renderInventorySlot(mc, itemIndex + nextHotbarStart, itemX, itemY, partialTick);
                 }
 
                 // Render hotbar items
-                GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+                GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
                 for (int itemIndex = 0; itemIndex < 9; itemIndex++) {
                     int itemX = x + 8 + itemIndex * 20;
-                    int itemY = y + 3 + (int) (22 * (mc.hotbarSwapAnimationProgress + partialTick)/ HOTBAR_SWAP_ANIMATION_LENGTH_TICKS);
+                    int itemY = y + 3 + (int) (22 * (mc.hotbarSwapAnimationProgress + partialTick) / HOTBAR_SWAP_ANIMATION_LENGTH_TICKS);
                     renderInventorySlot(mc, itemIndex + mc.thePlayer.inventory.getHotbarOffset(), itemX, itemY, partialTick);
                 }
             }
@@ -119,7 +119,7 @@ public class HudComponentHotbar
 
         } else {
             // Render hotbar items
-            GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+            GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
             for (int itemIndex = 0; itemIndex < 9; itemIndex++) {
                 int itemX = x + 8 + itemIndex * 20;
                 int itemY = y + 3;
@@ -128,20 +128,19 @@ public class HudComponentHotbar
         }
 
 
-
         Scissor.disable();
         Lighting.disable();
 
         // Setup hotbar texture
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
 
         // Render selector
         hud.drawGuiIcon((x + 4) + (inv.getCurrentItemIndex() % 9) * 20, y - 1, 24, 24, TextureRegistry.getTexture(mc.thePlayer.getHeldObject() == null ? "minecraft:gui/hud/hotbar_selection" : "minecraft:gui/hud/hotbar_selection_locked"));
 
-        GL11.glPushMatrix();
-        GL11.glTranslatef(0, 0, 1f);
-        hud.heldItemTooltipElement.updateAndRender(mc, x + 5 + 182/2, y - 29);
-        GL11.glPopMatrix();
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate(0, 0, 1f);
+        hud.heldItemTooltipElement.updateAndRender(mc, x + 5 + 182 / 2, y - 29);
+        GLRenderer.popFrame();
     }
 
     @Override
@@ -150,7 +149,7 @@ public class HudComponentHotbar
         int y = layout.getComponentY(this, ySizeScreen);
 
         // Setup hotbar texture
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
 
         // Render hotbar
         gui.drawGuiIcon(x + 5, y, 182, 22, TextureRegistry.getTexture("minecraft:gui/hud/hotbar"));
@@ -165,13 +164,13 @@ public class HudComponentHotbar
 
 
         // Setup items
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.enableState(State.BLEND);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
         Lighting.enableInventoryLight();
 
         // Render hotbar items
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
         for (int itemIndex = 0; itemIndex < 9; itemIndex++) {
             int itemX = x + 8 + itemIndex * 20;
             int itemY = y + 3;
@@ -181,36 +180,32 @@ public class HudComponentHotbar
         Lighting.disable();
     }
 
-    private void renderInventorySlot(Minecraft mc, int itemIndex, int x, int y, float partialTick)
-    {
+    private void renderInventorySlot(Minecraft mc, int itemIndex, int x, int y, float partialTick) {
         ItemStack itemstack = mc.thePlayer.inventory.mainInventory[itemIndex];
-        if (itemstack == null)
-        {
+        if (itemstack == null) {
             return;
         }
         ItemModel itemModel = ItemModelDispatcher.getInstance().getDispatch(itemstack.getItem());
         float animProgress = (float) itemstack.animationsToGo - partialTick;
-        if (animProgress > 0.0F)
-        {
-            GL11.glPushMatrix();
+        if (animProgress > 0.0F) {
+            GLRenderer.pushFrame();
             float f2 = 1.0F + animProgress / 5F;
-            GL11.glTranslatef(x + 8, y + 12, 0.0F);
-            GL11.glScalef(1.0F / f2, (f2 + 1.0F) / 2.0F, 1.0F);
-            GL11.glTranslatef(-(x + 8), -(y + 12), 0.0F);
+            GLRenderer.modelM4f().translate(x + 8, y + 12, 0.0F);
+            GLRenderer.modelM4f().scale(1.0F / f2, (f2 + 1.0F) / 2.0F, 1.0F);
+            GLRenderer.modelM4f().translate(-(x + 8), -(y + 12), 0.0F);
         }
-//        itemModel.renderItemIntoGui(Tessellator.instance, mc.font, mc.textureManager, itemstack, x, y, 1.0f);
-        itemModel.renderGui(Tessellator.instance, null, itemstack, x, y, 1, 1, partialTick);
-        if (animProgress > 0.0F)
-        {
-            GL11.glPopMatrix();
+//        itemModel.renderItemIntoGui(GLRenderer.getTessellator(), mc.font, mc.textureManager, itemstack, x, y, 1.0f);
+        itemModel.renderGui(GLRenderer.getTessellator(), null, itemstack, x, y, LightmapHelper.getLightmapCoord(15, 15), partialTick);
+        if (animProgress > 0.0F) {
+            GLRenderer.popFrame();
         }
-        itemModel.renderItemOverlayIntoGUI(Tessellator.instance, mc.font, mc.textureManager, itemstack, x, y, null, 1.0f);
+        itemModel.renderItemOverlayIntoGUI(GLRenderer.getTessellator(), mc.font, mc.textureManager, itemstack, x, y, null, 1.0f);
     }
 
     private void renderItem(Minecraft mc, ItemStack itemStack, int x, int y) {
         ItemModel itemModel = ItemModelDispatcher.getInstance().getDispatch(itemStack.getItem());
-//        itemModel.renderItemIntoGui(Tessellator.instance, mc.font, mc.textureManager, itemStack, x, y, 1.0f);
-        itemModel.renderGui(Tessellator.instance, null, itemStack, x, y, 1.0f, 1f, 1f);
-        itemModel.renderItemOverlayIntoGUI(Tessellator.instance, mc.font, mc.textureManager, itemStack, x, y, null, 1.0f);
+//        itemModel.renderItemIntoGui(GLRenderer.getTessellator(), mc.font, mc.textureManager, itemStack, x, y, 1.0f);
+        itemModel.renderGui(GLRenderer.getTessellator(), null, itemStack, x, y, LightmapHelper.getLightmapCoord(15, 15), 1f);
+        itemModel.renderItemOverlayIntoGUI(GLRenderer.getTessellator(), mc.font, mc.textureManager, itemStack, x, y, null, 1.0f);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentInfoOverlay.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentInfoOverlay.java
index eaad85361..8e0adcd7f 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentInfoOverlay.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentInfoOverlay.java
@@ -5,7 +5,6 @@ import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
 import net.minecraft.client.gui.hud.component.layout.LayoutAbsolute;
 import net.minecraft.client.gui.hud.component.layout.LayoutSnap;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.Global;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.item.Items;
@@ -23,8 +22,7 @@ import net.minecraft.core.world.weather.Weathers;
 import static net.minecraft.core.util.helper.Utils.floor10;
 
 public class HudComponentInfoOverlay
-    extends HudComponentMovable
-{
+    extends HudComponentMovable {
     public HudComponentInfoOverlay(String key, Layout layout) {
         super(key, 130, 112, layout);
     }
@@ -40,7 +38,7 @@ public class HudComponentInfoOverlay
             xOffset = mc.font.stringWidth(string) + 2 - this.getXSize();
         }
 
-        mc.font.render(Tessellator.instance, string, x - xOffset, y).setShadow().setColor(argb).call();
+        mc.font.render(string, x - xOffset, y).setShadow().setColor(argb).call();
     }
 
     @Override
@@ -49,8 +47,7 @@ public class HudComponentInfoOverlay
         int y = this.getLayout().getComponentY(this, ySizeScreen);
 
         boolean rightAligned = false;
-        if (this.getLayout() instanceof LayoutAbsolute) {
-            final LayoutAbsolute layout = (LayoutAbsolute) this.getLayout();
+        if (this.getLayout() instanceof LayoutAbsolute layout) {
             final ComponentAnchor anchor = layout.getAnchor();
             if (anchor == ComponentAnchor.TOP_RIGHT || anchor == ComponentAnchor.CENTER_RIGHT || anchor == ComponentAnchor.BOTTOM_RIGHT) {
                 rightAligned = true;
@@ -67,29 +64,21 @@ public class HudComponentInfoOverlay
         boolean compass = false;
         boolean rotaryCalendar = false;
 
-        if (mc.thePlayer.getGamemode() == Gamemode.creative)
-        {
+        if (mc.thePlayer.getGamemode() == Gamemode.creative) {
             clock = true;
             compass = true;
             rotaryCalendar = true;
-        }
-        else
-        {
-            for (int iinv = 0; iinv < mc.thePlayer.inventory.getContainerSize(); iinv++)
-            {
+        } else {
+            for (int iinv = 0; iinv < mc.thePlayer.inventory.getContainerSize(); iinv++) {
                 ItemStack item = mc.thePlayer.inventory.getItem(iinv);
-                if (item != null)
-                {
-                    if (item.itemID == Items.TOOL_CLOCK.id)
-                    {
+                if (item != null) {
+                    if (item.itemID == Items.TOOL_CLOCK.id) {
                         clock = true;
                     }
-                    if (item.itemID == Items.TOOL_COMPASS.id)
-                    {
+                    if (item.itemID == Items.TOOL_COMPASS.id) {
                         compass = true;
                     }
-                    if (item.itemID == Items.TOOL_CALENDAR.id)
-                    {
+                    if (item.itemID == Items.TOOL_CALENDAR.id) {
                         rotaryCalendar = true;
                     }
                 }
@@ -102,79 +91,61 @@ public class HudComponentInfoOverlay
 
         if (mc.gameSettings.versionInOverlay.value) {
             int color;
-            if (mc.gameSettings.overlayMode.value == 2)
-            {
+            if (mc.gameSettings.overlayMode.value == 2) {
                 color = 0xFFFFFF60;
             } else {
                 color = 0xFFFFFFFF;
             }
             drawString("Better than Adventure! " + TextFormatting.WHITE + Global.VERSION, x, y + tsp + lineHeight * line++, color, rightAligned);
         }
-        if (mc.gameSettings.fpsInOverlay.value)
-        {
+        if (mc.gameSettings.fpsInOverlay.value) {
             drawString(mc.lingDebugFPS, x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
         }
-        if (compass)
-        {
-            if (mc.gameSettings.overlayShowCoords.value)
-            {
-                if (mc.gameSettings.overlayMode.value == 0)
-                {
+        if (compass) {
+            if (mc.gameSettings.overlayShowCoords.value) {
+                if (mc.gameSettings.overlayMode.value == 0) {
                     drawString("x: " + floor10(mc.thePlayer.x) + " y: " + floor10(mc.thePlayer.y) + " z: " + floor10(mc.thePlayer.z), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
                 }
-                if (mc.gameSettings.overlayMode.value == 1)
-                {
-                    drawString( "x: " + floor10(mc.thePlayer.x), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
-                    drawString( "y: " + floor10(mc.thePlayer.y), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
-                    drawString( "z: " + floor10(mc.thePlayer.z), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
+                if (mc.gameSettings.overlayMode.value == 1) {
+                    drawString("x: " + floor10(mc.thePlayer.x), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
+                    drawString("y: " + floor10(mc.thePlayer.y), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
+                    drawString("z: " + floor10(mc.thePlayer.z), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
                 }
-                if (mc.gameSettings.overlayMode.value == 2)
-                {
+                if (mc.gameSettings.overlayMode.value == 2) {
                     drawString("x: " + floor10(mc.thePlayer.x), x, y + tsp + lineHeight * line++, 0xFFFF8080, rightAligned);
                     drawString("y: " + floor10(mc.thePlayer.y), x, y + tsp + lineHeight * line++, 0xFF80FF80, rightAligned);
                     drawString("z: " + floor10(mc.thePlayer.z), x, y + tsp + lineHeight * line++, 0xFF8080FF, rightAligned);
                 }
             }
-            if (mc.gameSettings.overlayShowDirection.value)
-            {
+            if (mc.gameSettings.overlayShowDirection.value) {
                 drawString(I18n.getInstance().translateKey(HudIngame.getFacingDirection(mc.thePlayer).getTranslationKey()), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
             }
         }
-        if (clock)
-        {
-            if (mc.gameSettings.overlayShowTime.value)
-            {
-                if (mc.gameSettings.overlayMode.value == 0)
-                {
-                    drawString(String.format("%s %s %d", HudIngame.getTimeString(mc), I18n.getInstance().translateKey("unit.day"),mc.currentWorld.getWorldTime() / Global.DAY_LENGTH_TICKS), x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFFFFFF80 : 0xFFFFFFFF, rightAligned);
+        if (clock) {
+            if (mc.gameSettings.overlayShowTime.value) {
+                if (mc.gameSettings.overlayMode.value == 0) {
+                    drawString(String.format("%s %s %d", HudIngame.getTimeString(mc), I18n.getInstance().translateKey("unit.day"), mc.currentWorld.getWorldTime() / Global.DAY_LENGTH_TICKS), x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFFFFFF80 : 0xFFFFFFFF, rightAligned);
                 }
-                if (mc.gameSettings.overlayMode.value > 0)
-                {
+                if (mc.gameSettings.overlayMode.value > 0) {
                     drawString(HudIngame.getTimeString(mc), x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFFFFFF80 : 0xFFFFFFFF, rightAligned);
                     drawString(String.format("%s %d", I18n.getInstance().translateKey("unit.day"), mc.currentWorld.getWorldTime() / Global.DAY_LENGTH_TICKS), x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFFFFFF80 : 0xFFFFFFFF, rightAligned);
                 }
             }
         }
-        if (rotaryCalendar)
-        {
-            if (mc.gameSettings.overlayShowSeason.value)
-            {
+        if (rotaryCalendar) {
+            if (mc.gameSettings.overlayShowSeason.value) {
                 Season season = mc.currentWorld.getSeasonManager().getCurrentSeason();
-                if (season != null)
-                {
+                if (season != null) {
                     drawString(season.getTranslatedName(), x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFF80FFFF : 0xFFFFFFFF, rightAligned);
                 }
             }
-            if (mc.gameSettings.overlayShowWeather.value)
-            {
+            if (mc.gameSettings.overlayShowWeather.value) {
                 Weather weather = mc.currentWorld.getCurrentWeather();
-                if (weather != null && weather != mc.currentWorld.worldType.getDefaultWeather())
-                {
+                if (weather != null && weather != mc.currentWorld.worldType.getDefaultWeather()) {
                     drawString(I18n.getInstance().translateKey(weather.getNameLanguageKey()), x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFFFF80FF : 0xFFFFFFFF, rightAligned);
                 }
             }
-            if(mc.gameSettings.overlayShowBiome.value)
-            {
+            if (mc.gameSettings.overlayShowBiome.value) {
                 int blockX = MathHelper.floor(mc.thePlayer.x);
                 int blockY = MathHelper.floor(mc.thePlayer.y);
                 int blockZ = MathHelper.floor(mc.thePlayer.z);
@@ -217,18 +188,15 @@ public class HudComponentInfoOverlay
                 final double py = 64.355;
                 final double pz = 38472.333;
 
-                if (mc.gameSettings.overlayMode.value == 0)
-                {
+                if (mc.gameSettings.overlayMode.value == 0) {
                     drawString("x: " + floor10(px) + " y: " + floor10(py) + " z: " + floor10(pz), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
                 }
-                if (mc.gameSettings.overlayMode.value == 1)
-                {
+                if (mc.gameSettings.overlayMode.value == 1) {
                     drawString("x: " + floor10(px), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
                     drawString("y: " + floor10(py), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
                     drawString("z: " + floor10(pz), x, y + tsp + lineHeight * line++, 0xFFFFFFFF, rightAligned);
                 }
-                if (mc.gameSettings.overlayMode.value == 2)
-                {
+                if (mc.gameSettings.overlayMode.value == 2) {
                     drawString("x: " + floor10(px), x, y + tsp + lineHeight * line++, 0xFFFF8080, rightAligned);
                     drawString("y: " + floor10(py), x, y + tsp + lineHeight * line++, 0xFF80FF80, rightAligned);
                     drawString("z: " + floor10(pz), x, y + tsp + lineHeight * line++, 0xFF8080FF, rightAligned);
@@ -240,12 +208,10 @@ public class HudComponentInfoOverlay
         }
         {
             {
-                if (mc.gameSettings.overlayMode.value == 0)
-                {
+                if (mc.gameSettings.overlayMode.value == 0) {
                     drawString(String.format("%s %s %d", "8:32", I18n.getInstance().translateKey("unit.day"), 500), x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFFFFFF80 : 0xFFFFFFFF, rightAligned);
                 }
-                if (mc.gameSettings.overlayMode.value > 0)
-                {
+                if (mc.gameSettings.overlayMode.value > 0) {
                     drawString("8:32", x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFFFFFF80 : 0xFFFFFFFF, rightAligned);
                     drawString(String.format("%s %d", I18n.getInstance().translateKey("unit.day"), 500), x, y + tsp + lineHeight * line++, mc.gameSettings.overlayMode.value == 2 ? 0xFFFFFF80 : 0xFFFFFFFF, rightAligned);
                 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentLog.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentLog.java
index d25b23c9f..fe82a2ace 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentLog.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentLog.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.gui.hud.component;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.console.LogMessage;
 import net.minecraft.client.console.LogMessageReceiver;
 import net.minecraft.client.gui.Gui;
@@ -9,11 +8,12 @@ import net.minecraft.client.gui.hud.component.layout.Layout;
 import net.minecraft.client.gui.hud.component.layout.LayoutAbsolute;
 import net.minecraft.client.gui.hud.component.layout.LayoutSnap;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.net.command.TextFormatting;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.HashMap;
@@ -105,7 +105,7 @@ public class HudComponentLog extends HudComponentMovable {
                     this.logEntries.add(new LogEntry(line));
                 }
             });
-            callbackAdded = true;
+            this.callbackAdded = true;
         }
 
         int x = this.getLayout().getComponentX(this, xSizeScreen);
@@ -119,18 +119,18 @@ public class HudComponentLog extends HudComponentMovable {
             }
         }
 
-        final @NotNull String @NotNull[] messages = new String[this.logEntries.size()];
-        final float @NotNull[] opacities = new float[this.logEntries.size()];
+        final @NotNull String @NotNull [] messages = new String[this.logEntries.size()];
+        final float @NotNull [] opacities = new float[this.logEntries.size()];
         for (int i = 0; i < this.logEntries.size(); i++) {
             messages[i] = this.logEntries.get(i).message;
             opacities[i] = this.logEntries.get(i).getOpacity();
         }
 
         @Nullable ComponentAnchor anchor = null;
-        if (layout instanceof LayoutAbsolute) {
-            anchor = ((LayoutAbsolute) layout).getAnchor();
-        } else if (layout instanceof LayoutSnap) {
-            anchor = ((LayoutSnap) layout).getAnchor();
+        if (this.layout instanceof LayoutAbsolute layoutAbsolute) {
+            anchor = layoutAbsolute.getAnchor();
+        } else if (this.layout instanceof LayoutSnap layoutSnap) {
+            anchor = layoutSnap.getAnchor();
         }
 
         render(mc.font, x, y, messages, opacities, anchor);
@@ -141,7 +141,7 @@ public class HudComponentLog extends HudComponentMovable {
         int x = layout.getComponentX(this, xSizeScreen);
         int y = layout.getComponentY(this, ySizeScreen);
 
-        final @NotNull String @NotNull[] lines = {
+        final @NotNull String @NotNull [] lines = {
             this.preludes.get(LogMessage.Level.DEBUG) + "This is a debug line!",
             this.preludes.get(LogMessage.Level.INFO) + "This is an info line!",
             this.preludes.get(LogMessage.Level.WARN) + "This is a warning line!",
@@ -149,30 +149,30 @@ public class HudComponentLog extends HudComponentMovable {
         };
 
         @Nullable ComponentAnchor anchor = null;
-        if (layout instanceof LayoutAbsolute) {
-            anchor = ((LayoutAbsolute) layout).getAnchor();
-        } else if (layout instanceof LayoutSnap) {
-            anchor = ((LayoutSnap) layout).getAnchor();
+        if (layout instanceof LayoutAbsolute layoutAbsolute) {
+            anchor = layoutAbsolute.getAnchor();
+        } else if (layout instanceof LayoutSnap layoutSnap) {
+            anchor = layoutSnap.getAnchor();
         }
 
-        render(mc.font, x, y, lines, new float[] { 1.0f, 1.0f, 1.0f, 1.0f }, anchor);
+        render(mc.font, x, y, lines, new float[]{1.0f, 1.0f, 1.0f, 1.0f}, anchor);
     }
 
-    private void render(final @NotNull FontRenderer sr, final int x, final int y, final @NotNull String @NotNull[] lines, final float @NotNull[] opacities, final @Nullable ComponentAnchor anchor) {
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+    private void render(final @NotNull FontRenderer sr, final int x, final int y, final @NotNull String @NotNull [] lines, final float @NotNull [] opacities, final @Nullable ComponentAnchor anchor) {
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         for (int i = 0; i < lines.length; i++) {
             @NotNull String line = lines[i];
 
             final int lineWidth = sr.stringWidth(line);
             if (anchor == null || anchor == ComponentAnchor.TOP_LEFT || anchor == ComponentAnchor.CENTER_LEFT || anchor == ComponentAnchor.BOTTOM_LEFT) {
-                sr.render(Tessellator.instance, line, x + PADDING, y + PADDING + i * LINE_HEIGHT).setShadow().setColor(0x00_FF_FF_FF + ((int)(opacities[i] * 0xFF) << 24)).call();
+                sr.render(line, x + PADDING, y + PADDING + i * LINE_HEIGHT).setShadow().setColor(0x00_FF_FF_FF + ((int) (opacities[i] * 0xFF) << 24)).call();
             } else if (anchor == ComponentAnchor.TOP_CENTER || anchor == ComponentAnchor.CENTER || anchor == ComponentAnchor.BOTTOM_CENTER) {
-                sr.render(Tessellator.instance, line, x + PADDING + WIDTH / 2 - lineWidth / 2, y + PADDING + i * LINE_HEIGHT).setShadow().setColor(0x00_FF_FF_FF + ((int)(opacities[i] * 0xFF) << 24)).call();
+                sr.render(line, x + PADDING + WIDTH / 2 - lineWidth / 2, y + PADDING + i * LINE_HEIGHT).setShadow().setColor(0x00_FF_FF_FF + ((int) (opacities[i] * 0xFF) << 24)).call();
             } else {
-                sr.render(Tessellator.instance, line, x + PADDING + WIDTH - lineWidth, y + PADDING + i * LINE_HEIGHT).setShadow().setColor(0x00_FF_FF_FF + ((int)(opacities[i] * 0xFF) << 24)).call();
+                sr.render(line, x + PADDING + WIDTH - lineWidth, y + PADDING + i * LINE_HEIGHT).setShadow().setColor(0x00_FF_FF_FF + ((int) (opacities[i] * 0xFF) << 24)).call();
             }
         }
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.disableState(State.BLEND);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentOxygenBar.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentOxygenBar.java
index 368d59643..88f4f4a44 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentOxygenBar.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentOxygenBar.java
@@ -3,19 +3,22 @@ package net.minecraft.client.gui.hud.component;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.material.Materials;
-import org.lwjgl.opengl.GL11;
+
 
 public class HudComponentOxygenBar
     extends HudComponentMovable {
     private final IconCoordinate air;
     private final IconCoordinate air_pop;
+
     public HudComponentOxygenBar(String key, Layout layout) {
         super(key, 81, 10, layout);
-        air = TextureRegistry.getTexture("minecraft:gui/hud/air");
-        air_pop = TextureRegistry.getTexture("minecraft:gui/hud/air_pop");
+        this.air = TextureRegistry.getTexture("minecraft:gui/hud/air");
+        this.air_pop = TextureRegistry.getTexture("minecraft:gui/hud/air_pop");
     }
 
     @Override
@@ -29,20 +32,16 @@ public class HudComponentOxygenBar
         int y = this.getLayout().getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         int numBubbles = (int) Math.ceil(((double) (mc.thePlayer.airSupply - 2) * 10D) / 300D);
         int numPops = (int) Math.ceil(((double) mc.thePlayer.airSupply * 10D) / 300D) - numBubbles;
-        for (int i = 0; i < numBubbles + numPops; i++)
-        {
-            if (i < numBubbles)
-            {
-                hud.drawGuiIcon(x + i * 8, y, 9, 9, air);
-            }
-            else
-            {
-                hud.drawGuiIcon(x + i * 8, y, 9, 9, air_pop);
+        for (int i = 0; i < numBubbles + numPops; i++) {
+            if (i < numBubbles) {
+                hud.drawGuiIcon(x + i * 8, y, 9, 9, this.air);
+            } else {
+                hud.drawGuiIcon(x + i * 8, y, 9, 9, this.air_pop);
             }
         }
     }
@@ -53,20 +52,16 @@ public class HudComponentOxygenBar
         int y = layout.getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         int numBubbles = 5;
         int numPops = 6 - numBubbles;
-        for (int i = 0; i < numBubbles + numPops; i++)
-        {
-            if (i < numBubbles)
-            {
-                gui.drawGuiIcon(x + i * 8, y, 9, 9, air);
-            }
-            else
-            {
-                gui.drawGuiIcon(x + i * 8, y, 9, 9, air_pop);
+        for (int i = 0; i < numBubbles + numPops; i++) {
+            if (i < numBubbles) {
+                gui.drawGuiIcon(x + i * 8, y, 9, 9, this.air);
+            } else {
+                gui.drawGuiIcon(x + i * 8, y, 9, 9, this.air_pop);
             }
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentRotationLock.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentRotationLock.java
index a34afcf59..764d3468e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentRotationLock.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentRotationLock.java
@@ -1,13 +1,13 @@
 package net.minecraft.client.gui.hud.component;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.entity.player.Player;
 import net.minecraft.core.util.helper.Direction;
-import org.lwjgl.opengl.GL11;
 
 public class HudComponentRotationLock
     extends HudComponentMovable {
@@ -23,8 +23,8 @@ public class HudComponentRotationLock
     @Override
     public void render(HudIngame hud, int xSizeScreen, int ySizeScreen, float partialTick) {
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         int x = this.getLayout().getComponentX(this, xSizeScreen);
         int y = this.getLayout().getComponentY(this, ySizeScreen);
@@ -38,42 +38,29 @@ public class HudComponentRotationLock
 
         Direction dir = Direction.getDirection(player);
 
-        if (dir.isHorizontal())
-        {
+        if (dir.isHorizontal()) {
             dir = dir.rotate(-Direction.getHorizontalDirection(player.yRot).rotate(2).index);
 
-            if (facingUp)
-            {
+            if (facingUp) {
                 if (dir == Direction.SOUTH) dir = Direction.UP;
                 if (dir == Direction.NORTH) dir = Direction.DOWN;
             }
-            if (facingDown)
-            {
+            if (facingDown) {
                 if (dir == Direction.SOUTH) dir = Direction.DOWN;
                 if (dir == Direction.NORTH) dir = Direction.UP;
             }
-        }
-        else if (dir == Direction.UP)
-        {
+        } else if (dir == Direction.UP) {
             dir = Direction.DOWN;
-            if (facingUp)
-            {
+            if (facingUp) {
                 dir = Direction.SOUTH;
-            }
-            else if (facingDown)
-            {
+            } else if (facingDown) {
                 dir = Direction.NORTH;
             }
-        }
-        else if (dir == Direction.DOWN)
-        {
+        } else if (dir == Direction.DOWN) {
             dir = Direction.UP;
-            if (facingDown)
-            {
+            if (facingDown) {
                 dir = Direction.SOUTH;
-            }
-            else if (facingUp)
-            {
+            } else if (facingUp) {
                 dir = Direction.NORTH;
             }
         }
@@ -91,8 +78,8 @@ public class HudComponentRotationLock
         int y = layout.getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         String prefix = mc.gameSettings.rotationOverlayMode.value % 2 == 1 ? "arrow" : "cube";
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentSubtitles.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentSubtitles.java
index b9dbb41fd..04ff0a8bd 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentSubtitles.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentSubtitles.java
@@ -1,22 +1,17 @@
 package net.minecraft.client.gui.hud.component;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
 import net.minecraft.client.gui.subtitles.SubtitleTracker;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.sound.SoundRepository;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.List;
 
-import static org.lwjgl.opengl.GL11.GL_ALPHA_TEST;
-import static org.lwjgl.opengl.GL11.GL_BLEND;
-import static org.lwjgl.opengl.GL11.GL_ONE_MINUS_SRC_ALPHA;
-import static org.lwjgl.opengl.GL11.GL_SRC_ALPHA;
-
 public class HudComponentSubtitles extends HudComponentMovable {
     public HudComponentSubtitles(String key, int xSize, int ySize, Layout layout) {
         super(key, xSize, ySize, layout);
@@ -71,9 +66,9 @@ public class HudComponentSubtitles extends HudComponentMovable {
         }
         maxMessageWidth += mc.font.stringWidth("<") + mc.font.stringWidth(">");
 
-        GL11.glEnable(GL_BLEND);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glDisable(GL_ALPHA_TEST);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+//        GL11.glDisable(GL_ALPHA_TEST);
         for (int i = 0; i < subtitleEntries.size() && i < messagesToShow; i++)
         {
             SubtitleTracker.SubtitleEntry entry = subtitleEntries.get(i);
@@ -105,20 +100,20 @@ public class HudComponentSubtitles extends HudComponentMovable {
                 final String subtitle = entry.soundEvent.getSubtitleTranslated();
                 if (subtitle != null) {
                     gui.drawRect(xRight - maxMessageWidth - xPad * 2, yBottom + y2 - 1, xRight, yBottom + y2 + 8, alpha / 2 << 24);
-                    GL11.glEnable(GL_BLEND);
-                    mc.font.renderCentered(Tessellator.instance, subtitle, xRight - (maxMessageWidth) / 2 - xPad, yBottom + y2).setShadow().setColor(0xFFFFFF + (alpha << 24)).call();
+                    GLRenderer.enableState(State.BLEND);
+                    mc.font.renderCentered(subtitle, xRight - (maxMessageWidth) / 2 - xPad, yBottom + y2).setShadow().setColor(0xFFFFFF + (alpha << 24)).call();
                     if (mc.thePlayer != null) {
                         final double sin = Math.sin(entry.getRelativeAngle(mc.thePlayer) + Math.PI/2);
                         if (sin > 0.7) {
-                            mc.font.render(Tessellator.instance, "<", xRight - maxMessageWidth - xPad, yBottom + y2).setColor(0xFFFFFF + (alpha << 24)).call();
+                            mc.font.render("<", xRight - maxMessageWidth - xPad, yBottom + y2).setColor(0xFFFFFF + (alpha << 24)).call();
                         } else if (sin < -0.7) {
-                            mc.font.render(Tessellator.instance, ">", xRight - mc.font.stringWidth(">") - xPad/2, yBottom + y2).setColor(0xFFFFFF + (alpha << 24)).call();
+                            mc.font.render(">", xRight - mc.font.stringWidth(">") - xPad/2, yBottom + y2).setColor(0xFFFFFF + (alpha << 24)).call();
                         }
                     }
                 }
             }
         }
-        GL11.glEnable(GL_ALPHA_TEST);
-        GL11.glDisable(GL_BLEND);
+//        GL11.glEnable(GL_ALPHA_TEST);
+        GLRenderer.disableState(State.BLEND);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentVehicleHealthBar.java b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentVehicleHealthBar.java
index 61d7b9701..1d9fb6105 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentVehicleHealthBar.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/hud/component/HudComponentVehicleHealthBar.java
@@ -3,6 +3,8 @@ package net.minecraft.client.gui.hud.component;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.hud.HudIngame;
 import net.minecraft.client.gui.hud.component.layout.Layout;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.entity.Mob;
 import net.minecraft.core.util.helper.MathHelper;
@@ -30,53 +32,45 @@ public class HudComponentVehicleHealthBar
             int y = this.getLayout().getComponentY(this, ySizeScreen);
 
             // Setup rendering
-            GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-            GL11.glDisable(GL11.GL_BLEND);
+            GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+            GLRenderer.enableState(State.BLEND);
 
             boolean heartsFlash = (mobVehicle.heartsFlashTime / 3) % 2 == 1;
-            if (mobVehicle.heartsFlashTime < 10)
-            {
+            if (mobVehicle.heartsFlashTime < 10) {
                 heartsFlash = false;
             }
             int health = mobVehicle.getHealth();
             int prevHealth = mobVehicle.prevHealth;
-            random.setSeed(hud.updateCounter * 0x4c627L);
+            this.random.setSeed(hud.updateCounter * 0x4c627L);
 
-            int hearts = MathHelper.ceil(mobVehicle.getMaxHealth()/2f);
+            int hearts = MathHelper.ceil(mobVehicle.getMaxHealth() / 2f);
             for (int i = 0; i < hearts; i++) {
                 int heartOffset = 0;
-                if (heartsFlash)
-                {
+                if (heartsFlash) {
                     heartOffset = 1;
                 }
                 int xHeart = (x + 9 * 8) - i * 8;
                 int yHeart = y;
-                if (health <= 4)
-                {
-                    yHeart += random.nextInt(2);
+                if (health <= 4) {
+                    yHeart += this.random.nextInt(2);
                 }
 
                 hud.drawGuiIcon(xHeart, yHeart, 9, 9, heartOffset == 0 ? TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/container") : TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/container_blinking"));
-                if (heartsFlash)
-                {
-                    if (i * 2 + 1 < prevHealth)
-                    {
+                if (heartsFlash) {
+                    if (i * 2 + 1 < prevHealth) {
                         // Half flash heart icon
                         hud.drawGuiIcon(xHeart, yHeart, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/full_blinking"));
                     }
-                    if (i * 2 + 1 == prevHealth)
-                    {
+                    if (i * 2 + 1 == prevHealth) {
                         // Full flash heart icon
                         hud.drawGuiIcon(xHeart, yHeart, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/half_blinking"));
                     }
                 }
-                if (i * 2 + 1 < health)
-                {
+                if (i * 2 + 1 < health) {
                     // Full heart icon
                     hud.drawGuiIcon(xHeart, yHeart, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/full"));
                 }
-                if (i * 2 + 1 == health)
-                {
+                if (i * 2 + 1 == health) {
                     // Half heart icon
                     hud.drawGuiIcon(xHeart, yHeart, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/half"));
                 }
@@ -90,20 +84,18 @@ public class HudComponentVehicleHealthBar
         int y = layout.getComponentY(this, ySizeScreen);
 
         // Setup rendering
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f); // Reset color
+        GLRenderer.enableState(State.BLEND);
 
         int health = 11;
         for (int i = 0; i < 10; i++) {
             int xHeart = (x + 9 * 8) - i * 8;
             gui.drawGuiIcon(xHeart, y, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/container"));
-            if (i * 2 + 1 < health)
-            {
+            if (i * 2 + 1 < health) {
                 // Full heart icon
                 gui.drawGuiIcon(xHeart, y, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/full"));
             }
-            if (i * 2 + 1 == health)
-            {
+            if (i * 2 + 1 == health) {
                 // Half heart icon
                 gui.drawGuiIcon(xHeart, y, 9, 9, TextureRegistry.getTexture("minecraft:gui/hud/heart/pig/half"));
             }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/keyboard/ScreenKeyboard.java b/game/client/src/main/java/net/minecraft/client/gui/keyboard/ScreenKeyboard.java
index 982ac2a5b..6eefe9f74 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/keyboard/ScreenKeyboard.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/keyboard/ScreenKeyboard.java
@@ -6,6 +6,7 @@ import net.minecraft.client.gui.keyboard.keys.Key;
 import net.minecraft.client.gui.text.ITextField;
 import net.minecraft.client.gui.text.TextFieldEditor;
 import net.minecraft.client.input.controller.ControllerInput;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.sound.SoundCategory;
 import net.minecraft.core.util.helper.ChatAllowedCharacters;
@@ -52,34 +53,34 @@ public class ScreenKeyboard extends Screen implements ITextField {
 
 
         this.keyboardLayout = KeyboardLayout.defaultLayout;
-        Arrays.stream(keyboardLayout.getKeys()).forEach(key -> key.onOpen(mc, this));
+        Arrays.stream(this.keyboardLayout.getKeys()).forEach(key -> key.onOpen(this.mc, this));
     }
 
     @Override
     public void opened(int width, int height) {
         Keyboard.enableRepeatEvents(true);
-        if (parent != null) {
-            parent.fontRenderer = mc.font;
-            parent.width = width;
-            parent.height = height;
+        if (this.parent != null) {
+            this.parent.fontRenderer = this.mc.font;
+            this.parent.width = width;
+            this.parent.height = height;
         }
-        this.glyphRenderer = new ControllerGlyphElement(mc);
+        this.glyphRenderer = new ControllerGlyphElement(this.mc);
         super.opened(width, height);
     }
 
     @Override
     public boolean isPauseScreen() {
-        if (parent != null) {
-            return parent.isPauseScreen();
+        if (this.parent != null) {
+            return this.parent.isPauseScreen();
         }
         return super.isPauseScreen();
     }
 
     @Override
     public void tick() {
-        cursorCounter++;
-        if (parent != null) {
-            parent.tick();
+        this.cursorCounter++;
+        if (this.parent != null) {
+            this.parent.tick();
         }
     }
 
@@ -93,12 +94,12 @@ public class ScreenKeyboard extends Screen implements ITextField {
     }
 
     public void typeChar(int key, char chr) {
-        if (editor.handleInput(key, chr)) {
-            if (keyAction != null) {
-                keyAction.apply(chr, key, editor.getText());
+        if (this.editor.handleInput(key, chr)) {
+            if (this.keyAction != null) {
+                this.keyAction.apply(chr, key, this.editor.getText());
             }
 
-            for (String id : activeModifiers.keySet()) {
+            for (String id : this.activeModifiers.keySet()) {
                 if (!isModifierLocked(id)) {
                     setModifierState(id, false);
                 }
@@ -107,50 +108,49 @@ public class ScreenKeyboard extends Screen implements ITextField {
     }
 
     public void backspace() {
-        editor.deleteCharsBeforeCursor(1);
-        if (backspaceAction != null) {
-            backspaceAction.apply(editor.getText());
+        this.editor.deleteCharsBeforeCursor(1);
+        if (this.backspaceAction != null) {
+            this.backspaceAction.apply(this.editor.getText());
         }
     }
 
     public void setModifierState(String id, boolean flag) {
-        activeModifiers.put(id, flag);
-        activeLocks.putIfAbsent(id, false);
+        this.activeModifiers.put(id, flag);
+        this.activeLocks.putIfAbsent(id, false);
     }
 
     public void setModifierLock(String id, boolean flag) {
-        activeModifiers.putIfAbsent(id, false);
-        activeLocks.put(id, flag);
+        this.activeModifiers.putIfAbsent(id, false);
+        this.activeLocks.put(id, flag);
     }
 
     public boolean isModifierActive(String id) {
-        return activeModifiers.getOrDefault(id, false) || isModifierLocked(id);
+        return this.activeModifiers.getOrDefault(id, false) || isModifierLocked(id);
     }
 
     public boolean isModifierLocked(String id) {
-        return activeLocks.getOrDefault(id, false);
+        return this.activeLocks.getOrDefault(id, false);
     }
 
     @Override
     public void removed() {
-        if (mc.controllerInput != null) {
-            mc.controllerInput.lockCursor = false;
-            mc.controllerInput.hideCursor = false;
+        if (this.mc.controllerInput != null) {
+            this.mc.controllerInput.lockCursor = false;
+            this.mc.controllerInput.hideCursor = false;
         }
-        if (resultStringAction != null) {
-            resultStringAction.apply(editor.getText());
+        if (this.resultStringAction != null) {
+            this.resultStringAction.apply(this.editor.getText());
         }
-        Keyboard.enableRepeatEvents(wasRepeating);
+        Keyboard.enableRepeatEvents(this.wasRepeating);
     }
 
-    public void close()
-    {
+    public void close() {
         this.removed();
-        mc.currentScreen = parent;
+        this.mc.currentScreen = this.parent;
     }
 
     public void setGroup(int group) {
-        group = MathHelper.clamp(group, 0, keyboardLayout.getHighestGroup());
+        group = MathHelper.clamp(group, 0, this.keyboardLayout.getHighestGroup());
         this.group = group;
     }
 
@@ -160,11 +160,11 @@ public class ScreenKeyboard extends Screen implements ITextField {
 
     public int getShiftedGroup(int amount) {
         int group = this.group + amount;
-        return (group + keyboardLayout.getHighestGroup() + 1) % (keyboardLayout.getHighestGroup() + 1);
+        return (group + this.keyboardLayout.getHighestGroup() + 1) % (this.keyboardLayout.getHighestGroup() + 1);
     }
 
     public int getGroup() {
-        return group;
+        return this.group;
     }
 
     @Override
@@ -173,45 +173,45 @@ public class ScreenKeyboard extends Screen implements ITextField {
             close();
             return;
         }
-        int _x = ((width - keyboardLayout.getWidth()) / 2);
-        int _y = height - keyboardLayout.getHeight() - 5;
-        Arrays.stream(keyboardLayout.getKeys()).forEach(key -> key.onClick(mc, this, _x, _y, mx, my, buttonNum));
+        int _x = ((this.width - this.keyboardLayout.getWidth()) / 2);
+        int _y = this.height - this.keyboardLayout.getHeight() - 5;
+        Arrays.stream(this.keyboardLayout.getKeys()).forEach(key -> key.onClick(this.mc, this, _x, _y, mx, my, buttonNum));
     }
 
     @Override
     public void mouseReleased(int mx, int my, int buttonNum) {
-        int _x = ((width - keyboardLayout.getWidth()) / 2);
-        int _y = height - keyboardLayout.getHeight() - 5;
-        Arrays.stream(keyboardLayout.getKeys()).forEach(key -> key.onRelease(mc, this, _x, _y, mx, my, buttonNum));
+        int _x = ((this.width - this.keyboardLayout.getWidth()) / 2);
+        int _y = this.height - this.keyboardLayout.getHeight() - 5;
+        Arrays.stream(this.keyboardLayout.getKeys()).forEach(key -> key.onRelease(this.mc, this, _x, _y, mx, my, buttonNum));
     }
 
     public boolean mouseOnKeyboard(int mx, int my) {
-        int keyboardWidth = keyboardLayout.getWidth();
-        int keyboardHeight = keyboardLayout.getHeight();
+        int keyboardWidth = this.keyboardLayout.getWidth();
+        int keyboardHeight = this.keyboardLayout.getHeight();
 
-        int _x = ((width - keyboardWidth) / 2) - HORIZONTAL_BUFFER;
-        int _y = height - keyboardHeight - 5 - 34;
+        int _x = ((this.width - keyboardWidth) / 2) - HORIZONTAL_BUFFER;
+        int _y = this.height - keyboardHeight - 5 - 34;
         return
             _x <= mx && mx < _x + (keyboardWidth + HORIZONTAL_BUFFER * 2) &&
-            _y <= my && my < _y + (keyboardHeight + 34 + 5);
+                _y <= my && my < _y + (keyboardHeight + 34 + 5);
     }
 
     @Override
     public void render(int mx, int my, float partialTick) {
-        if (parent != null) {
-            GL11.glPushMatrix();
-            GL11.glTranslatef(0, 0, -100);
-            parent.render(mx, my, partialTick);
-            GL11.glPopMatrix();
+        if (this.parent != null) {
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().translate(0, 0, -100);
+            this.parent.render(mx, my, partialTick);
+            GLRenderer.popFrame();
         }
-        drawRect(0, 0, width, height, 0x90_00_00_00);
-        GL11.glColor4f(1f, 1f, 1f, 1f);
+        drawRect(0, 0, this.width, this.height, 0x90_00_00_00);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
 
-        int keyboardWidth = keyboardLayout.getWidth();
-        int keyboardHeight = keyboardLayout.getHeight();
+        int keyboardWidth = this.keyboardLayout.getWidth();
+        int keyboardHeight = this.keyboardLayout.getHeight();
 
-        int _x = ((width - keyboardWidth) / 2);
-        int _y = height - keyboardHeight - 5;
+        int _x = ((this.width - keyboardWidth) / 2);
+        int _y = this.height - keyboardHeight - 5;
 
         drawGuiIcon(
             _x - 5 - HORIZONTAL_BUFFER,
@@ -227,19 +227,17 @@ public class ScreenKeyboard extends Screen implements ITextField {
             keyboardHeight + 8,
             TextureRegistry.getTexture("minecraft:gui/screen/keyboard/keyboard_background"));
 
-        Arrays.stream(keyboardLayout.getKeys()).forEach(key -> key.render(mc, this, _x, _y, mx, my));
+        Arrays.stream(this.keyboardLayout.getKeys()).forEach(key -> key.render(this.mc, this, _x, _y, mx, my));
 
-        drawStringCenteredShadow(mc.font, editor.getText(), _x + keyboardWidth/2, _y - 20, 0xFFFFFF);
+        drawStringCenteredShadow(this.mc.font, this.editor.getText(), _x + keyboardWidth / 2, _y - 20, 0xFFFFFF);
 
-        boolean drawCursor = (cursorCounter / 6) % 2 == 0;
-        if (drawCursor)
-        {
-            int width = MathHelper.ceil(fontRenderer.stringWidthDouble(editor.getText()));
-            if (editor.getCursor() < editor.getText().length())
-            {
-                width = MathHelper.ceil(fontRenderer.stringWidthDouble(editor.getText().substring(0, editor.getCursor())));
+        boolean drawCursor = (this.cursorCounter / 6) % 2 == 0;
+        if (drawCursor) {
+            int width = MathHelper.ceil(this.fontRenderer.stringWidthDouble(this.editor.getText()));
+            if (this.editor.getCursor() < this.editor.getText().length()) {
+                width = MathHelper.ceil(this.fontRenderer.stringWidthDouble(this.editor.getText().substring(0, this.editor.getCursor())));
             }
-            drawStringShadow(fontRenderer, "_", _x + keyboardWidth/2 - MathHelper.ceil(fontRenderer.stringWidthDouble(editor.getText())/2) + width, _y - 20 + 1, 0xE0E0E0);
+            drawStringShadow(this.fontRenderer, "_", _x + keyboardWidth / 2 - MathHelper.ceil(this.fontRenderer.stringWidthDouble(this.editor.getText()) / 2) + width, _y - 20 + 1, 0xE0E0E0);
         }
 
 
@@ -248,71 +246,71 @@ public class ScreenKeyboard extends Screen implements ITextField {
 
     @Override
     public void guiSpecificControllerInput(@NotNull ControllerInput controller) {
-        int keyboardWidth = keyboardLayout.getWidth();
-        int keyboardHeight = keyboardLayout.getHeight();
+        int keyboardWidth = this.keyboardLayout.getWidth();
+        int keyboardHeight = this.keyboardLayout.getHeight();
 
-        int _x = ((width - keyboardWidth) / 2);
-        int _y = height - keyboardHeight - 5;
+        int _x = ((this.width - keyboardWidth) / 2);
+        int _y = this.height - keyboardHeight - 5;
 
-        if(controller.buttonA.pressedThisFrame()) {
-            this.mouseClicked((int)controller.cursorX, (int)controller.cursorY, 0);
+        if (controller.buttonA.pressedThisFrame()) {
+            this.mouseClicked((int) controller.cursorX, (int) controller.cursorY, 0);
         }
-        if(controller.buttonA.releasedThisFrame()) {
-            this.mouseReleased((int)controller.cursorX, (int)controller.cursorY, 0);
+        if (controller.buttonA.releasedThisFrame()) {
+            this.mouseReleased((int) controller.cursorX, (int) controller.cursorY, 0);
         }
 
         if (!controller.lockCursor) {
             if (controller.digitalPad.up.pressedThisFrame()) {
-                Key hovered = getHoveredKey((int)controller.cursorX, (int)controller.cursorY);
+                Key hovered = getHoveredKey((int) controller.cursorX, (int) controller.cursorY);
 
                 final int stepSize = 9;
-                int x = hovered != null ? (_x + hovered.getX() + hovered.getWidth()/2): MathHelper.clamp((int) controller.cursorX, keyboardLayout.getMinX() + _x, keyboardLayout.getMaxX() + _x);
-                int y = hovered != null ? (_y + hovered.getY() + hovered.getHeight()/2) : MathHelper.clamp((int) controller.cursorY, keyboardLayout.getMinY() + _y, keyboardLayout.getMaxY() + _y);
-                for (int i = 0; i < keyboardHeight/9; i++) {
+                int x = hovered != null ? (_x + hovered.getX() + hovered.getWidth() / 2) : MathHelper.clamp((int) controller.cursorX, this.keyboardLayout.getMinX() + _x, this.keyboardLayout.getMaxX() + _x);
+                int y = hovered != null ? (_y + hovered.getY() + hovered.getHeight() / 2) : MathHelper.clamp((int) controller.cursorY, this.keyboardLayout.getMinY() + _y, this.keyboardLayout.getMaxY() + _y);
+                for (int i = 0; i < keyboardHeight / 9; i++) {
                     int newY = y - stepSize * i;
                     while (newY < _y) {
                         newY += keyboardHeight;
                     }
-                    while (newY > height - 5) {
+                    while (newY > this.height - 5) {
                         newY -= keyboardHeight;
                     }
                     Key newHover = getHoveredKey(x, newY);
                     if (newHover != null && newHover != hovered) {
-                        controller.cursorX = _x + newHover.getX() + newHover.getWidth()/2f;
-                        controller.cursorY = _y + newHover.getY() + newHover.getHeight()/2f;
+                        controller.cursorX = _x + newHover.getX() + newHover.getWidth() / 2f;
+                        controller.cursorY = _y + newHover.getY() + newHover.getHeight() / 2f;
                         break;
                     }
                 }
             }
             if (controller.digitalPad.down.pressedThisFrame()) {
-                Key hovered = getHoveredKey((int)controller.cursorX, (int)controller.cursorY);
+                Key hovered = getHoveredKey((int) controller.cursorX, (int) controller.cursorY);
 
                 final int stepSize = 9;
-                int x = hovered != null ? (_x + hovered.getX() + hovered.getWidth()/2): MathHelper.clamp((int) controller.cursorX, keyboardLayout.getMinX() + _x, keyboardLayout.getMaxX() + _x);
-                int y = hovered != null ? (_y + hovered.getY() + hovered.getHeight()/2) : MathHelper.clamp((int) controller.cursorY, keyboardLayout.getMinY() + _y, keyboardLayout.getMaxY() + _y);
-                for (int i = 0; i < keyboardHeight/9; i++) {
+                int x = hovered != null ? (_x + hovered.getX() + hovered.getWidth() / 2) : MathHelper.clamp((int) controller.cursorX, this.keyboardLayout.getMinX() + _x, this.keyboardLayout.getMaxX() + _x);
+                int y = hovered != null ? (_y + hovered.getY() + hovered.getHeight() / 2) : MathHelper.clamp((int) controller.cursorY, this.keyboardLayout.getMinY() + _y, this.keyboardLayout.getMaxY() + _y);
+                for (int i = 0; i < keyboardHeight / 9; i++) {
                     int newY = y + stepSize * i;
                     while (newY < _y) {
                         newY += keyboardHeight;
                     }
-                    while (newY > height - 5) {
+                    while (newY > this.height - 5) {
                         newY -= keyboardHeight;
                     }
                     Key newHover = getHoveredKey(x, newY);
                     if (newHover != null && newHover != hovered) {
-                        controller.cursorX = _x + newHover.getX() + newHover.getWidth()/2f;
-                        controller.cursorY = _y + newHover.getY() + newHover.getHeight()/2f;
+                        controller.cursorX = _x + newHover.getX() + newHover.getWidth() / 2f;
+                        controller.cursorY = _y + newHover.getY() + newHover.getHeight() / 2f;
                         break;
                     }
                 }
             }
             if (controller.digitalPad.left.pressedThisFrame()) {
-                Key hovered = getHoveredKey((int)controller.cursorX, (int)controller.cursorY);
+                Key hovered = getHoveredKey((int) controller.cursorX, (int) controller.cursorY);
 
                 final int stepSize = 9;
-                int x = hovered != null ? (_x + hovered.getX() + hovered.getWidth()/2): MathHelper.clamp((int) controller.cursorX, keyboardLayout.getMinX() + _x, keyboardLayout.getMaxX() + _x);
-                int y = hovered != null ? (_y + hovered.getY() + hovered.getHeight()/2) : MathHelper.clamp((int) controller.cursorY, keyboardLayout.getMinY() + _y, keyboardLayout.getMaxY() + _y);
-                for (int i = 0; i < keyboardWidth/9; i++) {
+                int x = hovered != null ? (_x + hovered.getX() + hovered.getWidth() / 2) : MathHelper.clamp((int) controller.cursorX, this.keyboardLayout.getMinX() + _x, this.keyboardLayout.getMaxX() + _x);
+                int y = hovered != null ? (_y + hovered.getY() + hovered.getHeight() / 2) : MathHelper.clamp((int) controller.cursorY, this.keyboardLayout.getMinY() + _y, this.keyboardLayout.getMaxY() + _y);
+                for (int i = 0; i < keyboardWidth / 9; i++) {
                     int newX = x - stepSize * i;
                     while (newX < _x) {
                         newX += keyboardWidth;
@@ -322,19 +320,19 @@ public class ScreenKeyboard extends Screen implements ITextField {
                     }
                     Key newHover = getHoveredKey(newX, y);
                     if (newHover != null && newHover != hovered) {
-                        controller.cursorX = _x + newHover.getX() + newHover.getWidth()/2f;
-                        controller.cursorY = _y + newHover.getY() + newHover.getHeight()/2f;
+                        controller.cursorX = _x + newHover.getX() + newHover.getWidth() / 2f;
+                        controller.cursorY = _y + newHover.getY() + newHover.getHeight() / 2f;
                         break;
                     }
                 }
             }
             if (controller.digitalPad.right.pressedThisFrame()) {
-                Key hovered = getHoveredKey((int)controller.cursorX, (int)controller.cursorY);
+                Key hovered = getHoveredKey((int) controller.cursorX, (int) controller.cursorY);
 
                 final int stepSize = 9;
-                int x = hovered != null ? (_x + hovered.getX() + hovered.getWidth()/2): MathHelper.clamp((int) controller.cursorX, keyboardLayout.getMinX() + _x, keyboardLayout.getMaxX() + _x);
-                int y = hovered != null ? (_y + hovered.getY() + hovered.getHeight()/2) : MathHelper.clamp((int) controller.cursorY, keyboardLayout.getMinY() + _y, keyboardLayout.getMaxY() + _y);
-                for (int i = 0; i < keyboardWidth/9; i++) {
+                int x = hovered != null ? (_x + hovered.getX() + hovered.getWidth() / 2) : MathHelper.clamp((int) controller.cursorX, this.keyboardLayout.getMinX() + _x, this.keyboardLayout.getMaxX() + _x);
+                int y = hovered != null ? (_y + hovered.getY() + hovered.getHeight() / 2) : MathHelper.clamp((int) controller.cursorY, this.keyboardLayout.getMinY() + _y, this.keyboardLayout.getMaxY() + _y);
+                for (int i = 0; i < keyboardWidth / 9; i++) {
                     int newX = x + stepSize * i;
                     while (newX < _x) {
                         newX += keyboardWidth;
@@ -344,34 +342,34 @@ public class ScreenKeyboard extends Screen implements ITextField {
                     }
                     Key newHover = getHoveredKey(newX, y);
                     if (newHover != null && newHover != hovered) {
-                        controller.cursorX = _x + newHover.getX() + newHover.getWidth()/2f;
-                        controller.cursorY = _y + newHover.getY() + newHover.getHeight()/2f;
+                        controller.cursorX = _x + newHover.getX() + newHover.getWidth() / 2f;
+                        controller.cursorY = _y + newHover.getY() + newHover.getHeight() / 2f;
                         break;
                     }
                 }
             }
         }
 
-        Arrays.stream(keyboardLayout.getKeys()).forEach(key -> key.onButtonUse(mc, this, _x, _y));
+        Arrays.stream(this.keyboardLayout.getKeys()).forEach(key -> key.onButtonUse(this.mc, this, _x, _y));
     }
 
     @Override
     public void playControllerButtonSound(@NotNull ControllerInput controller) {
         if (controller.buttonStart.pressedThisFrame()) {
-            mc.sndManager.playSound("ui.ui_click", SoundCategory.GUI_SOUNDS, 1.0f, 1.0f);
+            this.mc.sndManager.playSound("ui.ui_click", SoundCategory.GUI_SOUNDS, 1.0f, 1.0f);
         }
         if (controller.buttonB.pressedThisFrame()) {
-            mc.sndManager.playSound("ui.ui_back", SoundCategory.GUI_SOUNDS, 1.0f, 1.0f);
+            this.mc.sndManager.playSound("ui.ui_back", SoundCategory.GUI_SOUNDS, 1.0f, 1.0f);
         }
     }
 
     public @Nullable Key getHoveredKey(int mx, int my) {
-        int keyboardWidth = keyboardLayout.getWidth();
-        int keyboardHeight = keyboardLayout.getHeight();
+        int keyboardWidth = this.keyboardLayout.getWidth();
+        int keyboardHeight = this.keyboardLayout.getHeight();
 
-        int _x = ((width - keyboardWidth) / 2);
-        int _y = height - keyboardHeight - 5;
-        for (Key key : keyboardLayout.getKeys()) {
+        int _x = ((this.width - keyboardWidth) / 2);
+        int _y = this.height - keyboardHeight - 5;
+        for (Key key : this.keyboardLayout.getKeys()) {
             if (key.isHovered(_x, _y, mx, my)) return key;
         }
         return null;
@@ -384,7 +382,7 @@ public class ScreenKeyboard extends Screen implements ITextField {
 
     @Override
     public String getText() {
-        return workingString;
+        return this.workingString;
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/BackspaceKey.java b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/BackspaceKey.java
index 97163a2b3..b0212a963 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/BackspaceKey.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/BackspaceKey.java
@@ -78,16 +78,16 @@ public class BackspaceKey extends Key{
             if (src.height != DEFAULT_HEIGHT) object.addProperty("height", src.height);
             if (src.controllerButton != null) object.addProperty("button", src.controllerButton.name().toLowerCase(Locale.ROOT));
 
-            boolean ku = !src.keyUp.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_UP);
-            boolean kd = !src.keyDown.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_DOWN);
-            boolean kuh = !src.keyUpHovered.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_UP_HOVERED);
-            boolean kdh = !src.keyDownHovered.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_DOWN_HOVERED);
+            boolean ku = !src.keyUp.namespaceId.toString().equals(DEFAULT_TEXTURE_UP);
+            boolean kd = !src.keyDown.namespaceId.toString().equals(DEFAULT_TEXTURE_DOWN);
+            boolean kuh = !src.keyUpHovered.namespaceId.toString().equals(DEFAULT_TEXTURE_UP_HOVERED);
+            boolean kdh = !src.keyDownHovered.namespaceId.toString().equals(DEFAULT_TEXTURE_DOWN_HOVERED);
             if (ku || kd || kuh || kdh) {
                 JsonObject textureObject = new JsonObject();
-                if (ku) textureObject.addProperty("up", src.keyUp.sourceNamespaceId.toString());
-                if (kd) textureObject.addProperty("down", src.keyDown.sourceNamespaceId.toString());
-                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.sourceNamespaceId.toString());
-                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.sourceNamespaceId.toString());
+                if (ku) textureObject.addProperty("up", src.keyUp.namespaceId.toString());
+                if (kd) textureObject.addProperty("down", src.keyDown.namespaceId.toString());
+                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.namespaceId.toString());
+                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.namespaceId.toString());
                 object.add("textures", textureObject);
             }
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/CharKey.java b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/CharKey.java
index 0256cad4a..f8f5a5f80 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/CharKey.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/CharKey.java
@@ -11,6 +11,8 @@ import com.google.gson.JsonSerializer;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.keyboard.ScreenKeyboard;
 import net.minecraft.client.input.InputType;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
@@ -23,8 +25,8 @@ import java.util.ArrayList;
 import java.util.List;
 import java.util.Locale;
 
-public class CharKey extends Key{
-    private static int EXTRAS_HOLD_LENGTH = 300;
+public class CharKey extends Key {
+    private static final int EXTRAS_HOLD_LENGTH = 300;
     protected boolean renderChar = true;
     protected int lastRadial = 0;
     protected final CharGroup @NotNull [] groups;
@@ -38,7 +40,7 @@ public class CharKey extends Key{
     @Override
     public void render(Minecraft mc, ScreenKeyboard keyboard, int originX, int originY, int mouseX, int mouseY) {
         super.render(mc, keyboard, originX, originY, mouseX, mouseY);
-        if (!renderChar) return;
+        if (!this.renderChar) return;
         boolean hovered = isHovered(originX, originY, mouseX, mouseY);
         int texColor = hovered ? 0xFFFFA0 : 0xE0E0E0;
 
@@ -48,42 +50,42 @@ public class CharKey extends Key{
             CharGroup lastGroup = getGroup(keyboard.getShiftedGroup(-1));
 
             if (lastGroup != currentGroup && lastGroup != nextGroup) {
-                GL11.glPushMatrix();
-                GL11.glColor4f(0.75f, 0.75f, 0.75f, 1f);
-                GL11.glTranslatef(x + originX + 4, y + originY + 2, 0);
-                GL11.glScalef(0.75f, 0.75f, 1);
+                GLRenderer.pushFrame();
+                GLRenderer.setColor4f(0.75f, 0.75f, 0.75f, 1f);
+                GLRenderer.modelM4f().translate(this.x + originX + 4, this.y + originY + 2, 0);
+                GLRenderer.modelM4f().scale(0.75f, 0.75f, 1);
                 drawStringCenteredShadow(mc.font, String.valueOf(keyboard.isModifierActive(ModifierKey.ID_MODIFIER_SHIFT) ? lastGroup.collections[0].upper : lastGroup.collections[0].lower), 0, 0, 0xE0E0E0);
-                GL11.glPopMatrix();
+                GLRenderer.popFrame();
             }
 
             if (nextGroup != currentGroup) {
-                GL11.glPushMatrix();
-                GL11.glColor4f(0.75f, 0.75f, 0.75f, 1f);
-                GL11.glTranslatef(x + width + originX - 4, y + originY + 2, 0);
-                GL11.glScalef(0.75f, 0.75f, 1);
+                GLRenderer.pushFrame();
+                GLRenderer.setColor4f(0.75f, 0.75f, 0.75f, 1f);
+                GLRenderer.modelM4f().translate(this.x + this.width + originX - 4, this.y + originY + 2, 0);
+                GLRenderer.modelM4f().scale(0.75f, 0.75f, 1);
                 drawStringCenteredShadow(mc.font, String.valueOf(keyboard.isModifierActive(ModifierKey.ID_MODIFIER_SHIFT) ? nextGroup.collections[0].upper : nextGroup.collections[0].lower), 0, 0, 0xE0E0E0);
-                GL11.glPopMatrix();
+                GLRenderer.popFrame();
             }
         }
 //        if (isHovered) {
 //            drawStringCentered(mc.font, String.valueOf(getHoldTime()), x + width/2 + originX, y + mc.font.fontHeight/2 + 4 + originY - 10, texColor);
 //        }
         if (getHoldTime() > EXTRAS_HOLD_LENGTH) {
-            double animProgress = MathHelper.clamp((getHoldTime() - EXTRAS_HOLD_LENGTH)/100d, 0, 1);
-            GL11.glPushMatrix();
-            GL11.glEnable(GL11.GL_BLEND);
+            double animProgress = MathHelper.clamp((getHoldTime() - EXTRAS_HOLD_LENGTH) / 100d, 0, 1);
+            GLRenderer.pushFrame();
+            GLRenderer.enableState(State.BLEND);
             GL11.glEnable(GL11.GL_DEPTH_TEST);
-            GL11.glTranslatef(0, 0, 10);
+            GLRenderer.modelM4f().translate(0, 0, 10);
 
             final int size = (int) (64 * animProgress);
             drawTexturedIcon(
-                x + (width - size)/2 + originX,
-                y + (height - size)/2  + originY + 2,
+                this.x + (this.width - size) / 2 + originX,
+                this.y + (this.height - size) / 2 + originY + 2,
                 size,
                 size,
                 TextureRegistry.getTexture("minecraft:gui/screen/keyboard/radial_background"));
 
-            drawStringCenteredShadow(mc.font, String.valueOf(getActiveChar(mc, keyboard, originX, originY, mouseX, mouseY)), x + width/2 + originX, y + mc.font.getFont().fontHeight()/2 + 4 + originY, texColor);
+            drawStringCenteredShadow(mc.font, String.valueOf(getActiveChar(mc, keyboard, originX, originY, mouseX, mouseY)), this.x + this.width / 2 + originX, this.y + mc.font.getFont().fontHeight() / 2 + 4 + originY, texColor);
 
             final double dx;
             final double dy;
@@ -91,8 +93,8 @@ public class CharKey extends Key{
                 dx = mc.controllerInput.joyLeft.getX() * 20;
                 dy = mc.controllerInput.joyLeft.getY() * 20;
             } else {
-                dx = mouseX - (x + width/2d + originX);
-                dy = mouseY - (y + height/2d + originY);
+                dx = mouseX - (this.x + this.width / 2d + originX);
+                dy = mouseY - (this.y + this.height / 2d + originY);
             }
 
             int rIndex = getRadialIndex(mc, keyboard, dx, dy);
@@ -101,8 +103,8 @@ public class CharKey extends Key{
             for (int i = 0; i < currentGroup.collections.length; i++) {
                 CharCollection collection = currentGroup.collections[i];
 
-                int charX = MathHelper.floor(x + originX + width/2d + Math.cos(r * i - Math.PI/2) * 20 * animProgress);
-                int charY = MathHelper.floor(y + originY + height/2d + Math.sin(r * i - Math.PI/2) * 20 * animProgress) - 3;
+                int charX = MathHelper.floor(this.x + originX + this.width / 2d + Math.cos(r * i - Math.PI / 2) * 20 * animProgress);
+                int charY = MathHelper.floor(this.y + originY + this.height / 2d + Math.sin(r * i - Math.PI / 2) * 20 * animProgress) - 3;
 
                 drawStringCenteredShadow(
                     mc.font,
@@ -111,33 +113,33 @@ public class CharKey extends Key{
                     charY,
                     i == rIndex ? 0xFFFFA0 : 0xE0E0E0);
             }
-            GL11.glDisable(GL11.GL_BLEND);
-            GL11.glPopMatrix();
+            GLRenderer.disableState(State.BLEND);
+            GLRenderer.popFrame();
         } else {
-            drawStringCenteredShadow(mc.font, String.valueOf(getActiveChar(mc, keyboard, originX, originY, mouseX, mouseY)), x + width/2 + originX, y + mc.font.getFont().fontHeight()/2 + 4 + originY, texColor);
+            drawStringCenteredShadow(mc.font, String.valueOf(getActiveChar(mc, keyboard, originX, originY, mouseX, mouseY)), this.x + this.width / 2 + originX, this.y + mc.font.getFont().fontHeight() / 2 + 4 + originY, texColor);
         }
-        GL11.glColor4f(1f, 1f, 1f, 1f);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
     }
 
     protected int getRadialIndex(Minecraft mc, ScreenKeyboard keyboard, double dx, double dy) {
         if (getHoldTime() < EXTRAS_HOLD_LENGTH) {
-            lastRadial = 0;
+            this.lastRadial = 0;
             return 0;
         }
 
         final int deadzone = 7;
         if (Math.hypot(dx, dy) < deadzone) {
-            return lastRadial;
+            return this.lastRadial;
         }
 
         CharGroup currentGroup = getGroup(keyboard.getGroup());
         double r = (Math.PI * 2) / currentGroup.collections.length;
 
-        double mouseR = Math.atan2(dy, dx) + Math.PI/2 + r/2;
+        double mouseR = Math.atan2(dy, dx) + Math.PI / 2 + r / 2;
         if (mouseR < 0) mouseR += Math.PI * 2;
 
         int radial = MathHelper.floor(mouseR / r) % currentGroup.collections.length;
-        lastRadial = radial;
+        this.lastRadial = radial;
         return radial;
     }
 
@@ -161,8 +163,8 @@ public class CharKey extends Key{
             dx = mc.controllerInput.joyLeft.getX() * 20;
             dy = mc.controllerInput.joyLeft.getY() * 20;
         } else {
-            dx = mouseX - (x + width/2d + originX);
-            dy = mouseY - (y + height/2d + originY);
+            dx = mouseX - (this.x + this.width / 2d + originX);
+            dy = mouseY - (this.y + this.height / 2d + originY);
         }
 
         int rI = getRadialIndex(mc, keyboard, dx, dy);
@@ -170,7 +172,7 @@ public class CharKey extends Key{
     }
 
     protected CharGroup getGroup(int group) {
-        return group < groups.length ? groups[group] : groups[0];
+        return group < this.groups.length ? this.groups[group] : this.groups[0];
     }
 
     @Override
@@ -180,7 +182,7 @@ public class CharKey extends Key{
 
     @Override
     public int highestGroup() {
-        return groups.length - 1;
+        return this.groups.length - 1;
     }
 
     protected static class CharGroup {
@@ -194,6 +196,7 @@ public class CharKey extends Key{
     protected static class CharCollection {
         public char lower;
         public char upper;
+
         public CharCollection(char lower, char upper) {
             this.lower = lower;
             this.upper = upper;
@@ -264,19 +267,20 @@ public class CharKey extends Key{
             object.addProperty("y", src.y);
             if (src.width != DEFAULT_WIDTH) object.addProperty("width", src.width);
             if (src.height != DEFAULT_HEIGHT) object.addProperty("height", src.height);
-            if (src.controllerButton != null) object.addProperty("button", src.controllerButton.name().toLowerCase(Locale.ROOT));
+            if (src.controllerButton != null)
+                object.addProperty("button", src.controllerButton.name().toLowerCase(Locale.ROOT));
             if (src.renderChar != DEFAULT_RENDER_CHAR) object.addProperty("renderChar", src.renderChar);
 
-            boolean ku = !src.keyUp.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_UP);
-            boolean kd = !src.keyDown.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_DOWN);
-            boolean kuh = !src.keyUpHovered.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_UP_HOVERED);
-            boolean kdh = !src.keyDownHovered.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_DOWN_HOVERED);
+            boolean ku = !src.keyUp.namespaceId.toString().equals(DEFAULT_TEXTURE_UP);
+            boolean kd = !src.keyDown.namespaceId.toString().equals(DEFAULT_TEXTURE_DOWN);
+            boolean kuh = !src.keyUpHovered.namespaceId.toString().equals(DEFAULT_TEXTURE_UP_HOVERED);
+            boolean kdh = !src.keyDownHovered.namespaceId.toString().equals(DEFAULT_TEXTURE_DOWN_HOVERED);
             if (ku || kd || kuh || kdh) {
                 JsonObject textureObject = new JsonObject();
-                if (ku) textureObject.addProperty("up", src.keyUp.sourceNamespaceId.toString());
-                if (kd) textureObject.addProperty("down", src.keyDown.sourceNamespaceId.toString());
-                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.sourceNamespaceId.toString());
-                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.sourceNamespaceId.toString());
+                if (ku) textureObject.addProperty("up", src.keyUp.namespaceId.toString());
+                if (kd) textureObject.addProperty("down", src.keyDown.namespaceId.toString());
+                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.namespaceId.toString());
+                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.namespaceId.toString());
                 object.add("textures", textureObject);
             }
 
@@ -285,8 +289,8 @@ public class CharKey extends Key{
                 JsonArray collections = new JsonArray(group.collections.length);
                 for (CharCollection collection : group.collections) {
                     JsonObject o = new JsonObject();
-                    o.addProperty("lower", (int)collection.lower);
-                    o.addProperty("upper", (int)collection.upper);
+                    o.addProperty("lower", (int) collection.lower);
+                    o.addProperty("upper", (int) collection.upper);
                     collections.add(o);
                 }
                 groups.add(collections);
@@ -347,17 +351,17 @@ public class CharKey extends Key{
 
         public CharKeyBuilder addGroup(char c) {
             CharCollection collection = new CharCollection(c, Character.toUpperCase(c));
-            groups.add(new CharGroup(new CharCollection[]{collection}));
+            this.groups.add(new CharGroup(new CharCollection[]{collection}));
             return this;
         }
 
         public CharKeyBuilder addGroup(char lower, char upper) {
             CharCollection collection = new CharCollection(lower, upper);
-            groups.add(new CharGroup(new CharCollection[]{collection}));
+            this.groups.add(new CharGroup(new CharCollection[]{collection}));
             return this;
         }
 
-        public CharKeyBuilder addGroup(char[] ... group) {
+        public CharKeyBuilder addGroup(char[]... group) {
             CharCollection[] collections = new CharCollection[group.length];
             for (int i = 0; i < group.length; i++) {
                 char[] arr = group[i];
@@ -367,19 +371,19 @@ public class CharKey extends Key{
                     collections[i] = new CharCollection(arr[0], Character.toUpperCase(arr[0]));
                 }
             }
-            groups.add(new CharGroup(collections));
+            this.groups.add(new CharGroup(collections));
             return this;
         }
 
         protected CharKeyBuilder addGroup(CharGroup group) {
-            groups.add(group);
+            this.groups.add(group);
             return this;
         }
 
         public CharKey build() {
-            CharGroup[] compiledGroups = groups.toArray(new CharGroup[0]);
-            CharKey key = new CharKey(x, y, width, height, renderChar, compiledGroups);
-            key.setControllerButton(controllerButton).setTextures(texUp, texDown, texUpHovered, texDownHovered);
+            CharGroup[] compiledGroups = this.groups.toArray(new CharGroup[0]);
+            CharKey key = new CharKey(this.x, this.y, this.width, this.height, this.renderChar, compiledGroups);
+            key.setControllerButton(this.controllerButton).setTextures(this.texUp, this.texDown, this.texUpHovered, this.texDownHovered);
             return key;
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/CursorKey.java b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/CursorKey.java
index e889ac411..feaca62eb 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/CursorKey.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/CursorKey.java
@@ -86,10 +86,10 @@ public class CursorKey extends Key{
             boolean kdh = true;
             if (ku || kd || kuh || kdh) {
                 JsonObject textureObject = new JsonObject();
-                if (ku) textureObject.addProperty("up", src.keyUp.sourceNamespaceId.toString());
-                if (kd) textureObject.addProperty("down", src.keyDown.sourceNamespaceId.toString());
-                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.sourceNamespaceId.toString());
-                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.sourceNamespaceId.toString());
+                if (ku) textureObject.addProperty("up", src.keyUp.namespaceId.toString());
+                if (kd) textureObject.addProperty("down", src.keyDown.namespaceId.toString());
+                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.namespaceId.toString());
+                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.namespaceId.toString());
                 object.add("textures", textureObject);
             }
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/EnterKey.java b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/EnterKey.java
index db15ae8e6..bab04b012 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/EnterKey.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/EnterKey.java
@@ -77,16 +77,16 @@ public class EnterKey extends Key{
             if (src.height != DEFAULT_HEIGHT) object.addProperty("height", src.height);
             if (src.controllerButton != null) object.addProperty("button", src.controllerButton.name().toLowerCase(Locale.ROOT));
 
-            boolean ku = !src.keyUp.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_UP);
-            boolean kd = !src.keyDown.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_DOWN);
-            boolean kuh = !src.keyUpHovered.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_UP_HOVERED);
-            boolean kdh = !src.keyDownHovered.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_DOWN_HOVERED);
+            boolean ku = !src.keyUp.namespaceId.toString().equals(DEFAULT_TEXTURE_UP);
+            boolean kd = !src.keyDown.namespaceId.toString().equals(DEFAULT_TEXTURE_DOWN);
+            boolean kuh = !src.keyUpHovered.namespaceId.toString().equals(DEFAULT_TEXTURE_UP_HOVERED);
+            boolean kdh = !src.keyDownHovered.namespaceId.toString().equals(DEFAULT_TEXTURE_DOWN_HOVERED);
             if (ku || kd || kuh || kdh) {
                 JsonObject textureObject = new JsonObject();
-                if (ku) textureObject.addProperty("up", src.keyUp.sourceNamespaceId.toString());
-                if (kd) textureObject.addProperty("down", src.keyDown.sourceNamespaceId.toString());
-                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.sourceNamespaceId.toString());
-                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.sourceNamespaceId.toString());
+                if (ku) textureObject.addProperty("up", src.keyUp.namespaceId.toString());
+                if (kd) textureObject.addProperty("down", src.keyDown.namespaceId.toString());
+                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.namespaceId.toString());
+                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.namespaceId.toString());
                 object.add("textures", textureObject);
             }
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/GroupKey.java b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/GroupKey.java
index 982f43015..7c88466bb 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/GroupKey.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/GroupKey.java
@@ -126,10 +126,10 @@ public class GroupKey extends Key{
             boolean kdh = true;
             if (ku || kd || kuh || kdh) {
                 JsonObject textureObject = new JsonObject();
-                if (ku) textureObject.addProperty("up", src.keyUp.sourceNamespaceId.toString());
-                if (kd) textureObject.addProperty("down", src.keyDown.sourceNamespaceId.toString());
-                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.sourceNamespaceId.toString());
-                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.sourceNamespaceId.toString());
+                if (ku) textureObject.addProperty("up", src.keyUp.namespaceId.toString());
+                if (kd) textureObject.addProperty("down", src.keyDown.namespaceId.toString());
+                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.namespaceId.toString());
+                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.namespaceId.toString());
                 object.add("textures", textureObject);
             }
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/Key.java b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/Key.java
index 671b6cca5..94942e0d9 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/Key.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/Key.java
@@ -14,6 +14,8 @@ import net.minecraft.client.gui.keyboard.ScreenKeyboard;
 import net.minecraft.client.input.InputType;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.input.controller.IButton;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.sound.SoundCategory;
@@ -51,39 +53,40 @@ public abstract class Key extends Gui implements GuiElement {
     }
 
     public void onOpen(Minecraft mc, ScreenKeyboard keyboard) {
-        isDown = false;
-        isHovered = false;
+        this.isDown = false;
+        this.isHovered = false;
     }
+
     public void render(Minecraft mc, ScreenKeyboard keyboard, int originX, int originY, int mouseX, int mouseY) {
         boolean hovered = isHovered(originX, originY, mouseX, mouseY);
-        if (!isHovered && hovered) {
+        if (!this.isHovered && hovered) {
             onFocus(mc, keyboard, originX, originY, mouseX, mouseY);
         }
-        isHovered = hovered;
+        this.isHovered = hovered;
 
         boolean down = isDown(mc, keyboard);
         if (down) {
             if (hovered) {
-                drawGuiIcon(x + originX, y + originY, width, height, keyDownHovered);
+                drawGuiIcon(this.x + originX, this.y + originY, this.width, this.height, this.keyDownHovered);
             } else {
-                drawGuiIcon(x + originX, y + originY, width, height, keyDown);
+                drawGuiIcon(this.x + originX, this.y + originY, this.width, this.height, this.keyDown);
             }
         } else {
             if (hovered) {
-                drawGuiIcon(x + originX, y + originY, width, height, keyUpHovered);
+                drawGuiIcon(this.x + originX, this.y + originY, this.width, this.height, this.keyUpHovered);
             } else {
-                drawGuiIcon(x + originX, y + originY, width, height, keyUp);
+                drawGuiIcon(this.x + originX, this.y + originY, this.width, this.height, this.keyUp);
             }
         }
-        if (mc.inputType == InputType.CONTROLLER && controllerButton != null) {
-            GL11.glPushMatrix();
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glTranslatef(x + originX + width - 8, y + originY + 1, 0);
-            GL11.glColor4f(1, 1, 1, 0.5f);
-            GL11.glScalef(0.5f, 0.5f, 1);
-            keyboard.glyphRenderer.drawGlyph(mc.controllerInput, controllerButton.glyph, 0, 0);
-            GL11.glDisable(GL11.GL_BLEND);
-            GL11.glPopMatrix();
+        if (mc.inputType == InputType.CONTROLLER && this.controllerButton != null) {
+            GLRenderer.pushFrame();
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.modelM4f().translate(this.x + originX + this.width - 8, this.y + originY + 1, 0);
+            GLRenderer.setColor4f(1, 1, 1, 0.5f);
+            GLRenderer.modelM4f().scale(0.5f, 0.5f, 1);
+            keyboard.glyphRenderer.drawGlyph(mc.controllerInput, this.controllerButton.glyph, 0, 0);
+            GLRenderer.disableState(State.BLEND);
+            GLRenderer.popFrame();
         }
     }
 
@@ -94,8 +97,8 @@ public abstract class Key extends Gui implements GuiElement {
     public void onClick(Minecraft mc, ScreenKeyboard keyboard, int originX, int originY, int mouseX, int mouseY, int mouseButton) {
         if (mouseButton == 0 && isHovered(originX, originY, mouseX, mouseY)) {
             pressAction(mc, keyboard, originX, originY, mouseX, mouseY);
-            holdStart = System.currentTimeMillis();
-            isDown = true;
+            this.holdStart = System.currentTimeMillis();
+            this.isDown = true;
         }
     }
 
@@ -115,23 +118,23 @@ public abstract class Key extends Gui implements GuiElement {
     }
 
     public void onRelease(Minecraft mc, ScreenKeyboard keyboard, int originX, int originY, int mouseX, int mouseY, int mouseButton) {
-        if (isDown && mouseButton == 0) {
+        if (this.isDown && mouseButton == 0) {
             releaseAction(mc, keyboard, originX, originY, mouseX, mouseY);
-            isDown = false;
+            this.isDown = false;
         }
     }
 
     public void onButtonUse(Minecraft mc, ScreenKeyboard keyboard, int originX, int originY) {
-        if (mc.inputType == InputType.CONTROLLER && mc.controllerInput != null && controllerButton != null) {
-            IButton button = controllerButton.getButton(mc.controllerInput);
+        if (mc.inputType == InputType.CONTROLLER && mc.controllerInput != null && this.controllerButton != null) {
+            IButton button = this.controllerButton.getButton(mc.controllerInput);
             if (button.pressedThisFrame()) {
                 pressAction(mc, keyboard, originX, originY, (int) mc.controllerInput.cursorX, (int) mc.controllerInput.cursorY);
-                holdStart = System.currentTimeMillis();
-                isDown = true;
+                this.holdStart = System.currentTimeMillis();
+                this.isDown = true;
             }
             if (button.releasedThisFrame()) {
                 releaseAction(mc, keyboard, originX, originY, (int) mc.controllerInput.cursorX, (int) mc.controllerInput.cursorY);
-                isDown = false;
+                this.isDown = false;
             }
         }
     }
@@ -150,7 +153,7 @@ public abstract class Key extends Gui implements GuiElement {
     }
 
     public long getHoldTime() {
-        return isDown ? System.currentTimeMillis() - holdStart : 0;
+        return this.isDown ? System.currentTimeMillis() - this.holdStart : 0;
     }
 
     @Override
@@ -175,38 +178,38 @@ public abstract class Key extends Gui implements GuiElement {
 
     @Override
     public int getX() {
-        return x;
+        return this.x;
     }
 
     @Override
     public int getY() {
-        return y;
+        return this.y;
     }
 
     @Override
     public int getWidth() {
-        return width;
+        return this.width;
     }
 
     @Override
     public int getHeight() {
-        return height;
+        return this.height;
     }
 
     public boolean isHovered(int originX, int originY, int mx, int my) {
         mx -= originX;
         my -= originY;
         return
-            x <= mx && mx < x + width &&
-            y <= my && my < y + height;
+            this.x <= mx && mx < this.x + this.width &&
+                this.y <= my && my < this.y + this.height;
     }
 
     public boolean isDown(Minecraft mc, ScreenKeyboard keyboard) {
-        return isDown || isButtonPressed(mc, keyboard);
+        return this.isDown || isButtonPressed(mc, keyboard);
     }
 
     public boolean isButtonPressed(Minecraft mc, ScreenKeyboard keyboard) {
-        return mc.inputType == InputType.CONTROLLER && controllerButton != null && mc.controllerInput != null && controllerButton.getButton(mc.controllerInput).isPressed();
+        return mc.inputType == InputType.CONTROLLER && this.controllerButton != null && mc.controllerInput != null && this.controllerButton.getButton(mc.controllerInput).isPressed();
     }
 
     public int highestGroup() {
@@ -216,6 +219,7 @@ public abstract class Key extends Gui implements GuiElement {
     public static class Serializer implements JsonSerializer<Key>, JsonDeserializer<Key> {
         public static final Map<String, Class<? extends Key>> ID_TO_KEY_CLASS = new HashMap<>();
         public static final Map<Class<? extends Key>, String> KEY_CLASS_TO_ID = new HashMap<>();
+
         static {
             registerKeyClass("key_char", CharKey.class);
             registerKeyClass("key_back", BackspaceKey.class);
@@ -254,21 +258,21 @@ public abstract class Key extends Gui implements GuiElement {
         BUTTON_X(ControllerGlyphElement.Glyph.BUTTON_X, c -> c.buttonX),
         BUTTON_Y(ControllerGlyphElement.Glyph.BUTTON_Y, c -> c.buttonY),
 
-        BUTTON_DPAD_UP(ControllerGlyphElement.Glyph.D_PAD_UP,c -> c.digitalPad.up),
-        BUTTON_DPAD_LEFT(ControllerGlyphElement.Glyph.D_PAD_LEFT,c -> c.digitalPad.left),
-        BUTTON_DPAD_DOWN(ControllerGlyphElement.Glyph.D_PAD_DOWN,c -> c.digitalPad.down),
-        BUTTON_DPAD_RIGHT(ControllerGlyphElement.Glyph.D_PAD_RIGHT,c -> c.digitalPad.right),
+        BUTTON_DPAD_UP(ControllerGlyphElement.Glyph.D_PAD_UP, c -> c.digitalPad.up),
+        BUTTON_DPAD_LEFT(ControllerGlyphElement.Glyph.D_PAD_LEFT, c -> c.digitalPad.left),
+        BUTTON_DPAD_DOWN(ControllerGlyphElement.Glyph.D_PAD_DOWN, c -> c.digitalPad.down),
+        BUTTON_DPAD_RIGHT(ControllerGlyphElement.Glyph.D_PAD_RIGHT, c -> c.digitalPad.right),
 
-        BUTTON_SHOULDER_LEFT(ControllerGlyphElement.Glyph.SHOULDER_LEFT,c -> c.buttonLeftShoulder),
-        BUTTON_SHOULDER_RIGHT(ControllerGlyphElement.Glyph.SHOULDER_RIGHT,c -> c.buttonRightShoulder),
+        BUTTON_SHOULDER_LEFT(ControllerGlyphElement.Glyph.SHOULDER_LEFT, c -> c.buttonLeftShoulder),
+        BUTTON_SHOULDER_RIGHT(ControllerGlyphElement.Glyph.SHOULDER_RIGHT, c -> c.buttonRightShoulder),
 
-        BUTTON_STICK_LEFT(ControllerGlyphElement.Glyph.STICK_LEFT_PRESS,c -> c.joyLeft.button),
-        BUTTON_STICK_RIGHT(ControllerGlyphElement.Glyph.STICK_RIGHT_PRESS,c -> c.joyRight.button),
+        BUTTON_STICK_LEFT(ControllerGlyphElement.Glyph.STICK_LEFT_PRESS, c -> c.joyLeft.button),
+        BUTTON_STICK_RIGHT(ControllerGlyphElement.Glyph.STICK_RIGHT_PRESS, c -> c.joyRight.button),
 
-        BUTTON_TRIGGER_LEFT(ControllerGlyphElement.Glyph.TRIGGER_LEFT,c -> c.buttonLeftTrigger),
-        BUTTON_TRIGGER_RIGHT(ControllerGlyphElement.Glyph.TRIGGER_RIGHT,c -> c.buttonRightTrigger),
+        BUTTON_TRIGGER_LEFT(ControllerGlyphElement.Glyph.TRIGGER_LEFT, c -> c.buttonLeftTrigger),
+        BUTTON_TRIGGER_RIGHT(ControllerGlyphElement.Glyph.TRIGGER_RIGHT, c -> c.buttonRightTrigger),
 
-        BUTTON_START(ControllerGlyphElement.Glyph.BUTTON_START,c -> c.buttonStart),
+        BUTTON_START(ControllerGlyphElement.Glyph.BUTTON_START, c -> c.buttonStart),
         BUTTON_BACK(ControllerGlyphElement.Glyph.BUTTON_BACK, c -> c.buttonBack);
 
         public final @NotNull ControllerGlyphElement.Glyph glyph;
@@ -280,7 +284,7 @@ public abstract class Key extends Gui implements GuiElement {
         }
 
         public @NotNull IButton getButton(ControllerInput controller) {
-            return buttonGetter.apply(controller);
+            return this.buttonGetter.apply(controller);
         }
 
         private interface ButtonGetter {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/ModifierKey.java b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/ModifierKey.java
index 758ea48f0..e7ebac4b8 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/ModifierKey.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/keyboard/keys/ModifierKey.java
@@ -97,16 +97,16 @@ public class ModifierKey extends Key{
             if (src.height != DEFAULT_HEIGHT) object.addProperty("height", src.height);
             if (src.controllerButton != null) object.addProperty("button", src.controllerButton.name().toLowerCase(Locale.ROOT));
 
-            boolean ku = !src.keyUp.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_UP);
-            boolean kd = !src.keyDown.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_DOWN);
-            boolean kuh = !src.keyUpHovered.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_UP_HOVERED);
-            boolean kdh = !src.keyDownHovered.sourceNamespaceId.toString().equals(DEFAULT_TEXTURE_DOWN_HOVERED);
+            boolean ku = !src.keyUp.namespaceId.toString().equals(DEFAULT_TEXTURE_UP);
+            boolean kd = !src.keyDown.namespaceId.toString().equals(DEFAULT_TEXTURE_DOWN);
+            boolean kuh = !src.keyUpHovered.namespaceId.toString().equals(DEFAULT_TEXTURE_UP_HOVERED);
+            boolean kdh = !src.keyDownHovered.namespaceId.toString().equals(DEFAULT_TEXTURE_DOWN_HOVERED);
             if (ku || kd || kuh || kdh) {
                 JsonObject textureObject = new JsonObject();
-                if (ku) textureObject.addProperty("up", src.keyUp.sourceNamespaceId.toString());
-                if (kd) textureObject.addProperty("down", src.keyDown.sourceNamespaceId.toString());
-                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.sourceNamespaceId.toString());
-                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.sourceNamespaceId.toString());
+                if (ku) textureObject.addProperty("up", src.keyUp.namespaceId.toString());
+                if (kd) textureObject.addProperty("down", src.keyDown.namespaceId.toString());
+                if (kuh) textureObject.addProperty("up_hovered", src.keyUpHovered.namespaceId.toString());
+                if (kdh) textureObject.addProperty("down_hovered", src.keyDownHovered.namespaceId.toString());
                 object.add("textures", textureObject);
             }
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/modelviewer/ScreenModelViewer.java b/game/client/src/main/java/net/minecraft/client/gui/modelviewer/ScreenModelViewer.java
index 9c57be8e3..8927e5511 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/modelviewer/ScreenModelViewer.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/modelviewer/ScreenModelViewer.java
@@ -15,8 +15,8 @@ import net.minecraft.client.gui.modelviewer.elements.ListenerTextFieldElement;
 import net.minecraft.client.gui.modelviewer.elements.IListenerElement;
 import net.minecraft.client.gui.options.ScreenOptions;
 import net.minecraft.client.gui.options.data.OptionsPages;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.shader.PhotoModeRenderer;
-import net.minecraft.client.render.shader.Shaders;
 import net.minecraft.client.render.shader.ShadersRenderer;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.client.util.helper.FileOpener;
@@ -30,7 +30,7 @@ import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
+import org.lwjgl.opengl.GL41;
 import org.slf4j.Logger;
 
 import java.io.File;
@@ -76,411 +76,401 @@ public class ScreenModelViewer extends ScreenPhotoMode implements ListenerTextFi
     protected final int defaultRed = (int) (255 * 0.25f);
     protected final int defaultGreen = (int) (255 * 0.25f);
     protected final int defaultBlue = (int) (255 * 0.35f);
-    protected int bgRed = defaultRed;
-    protected int bgGreen = defaultGreen;
-    protected int bgBlue = defaultBlue;
+    protected int bgRed = this.defaultRed;
+    protected int bgGreen = this.defaultGreen;
+    protected int bgBlue = this.defaultBlue;
 
     protected boolean tickProgress = true;
     protected boolean rotateToCamera = true;
-    public ScreenModelViewer(){
+
+    public ScreenModelViewer() {
         DisplayChunk.displayBlockId = 0;
         DisplayChunk.displayBlockMeta = 0;
-        mc.currentWorld.entities.clear();
-        mc.currentWorld.tileEntityList.clear();
-        mc.thePlayer.absMoveTo(0.5, 64.5, 0.5, 180, 0);
-        mc.thePlayer.noPhysics = true;
-        mc.textureManager.refreshTexturesAndDisplayErrors();
-        mc.textureManager.updateDynamicTextures(false);
-
-        if(Shaders.enableShaders) {
-            photoModeRenderer = new PhotoModeRenderer(mc, this);
-        }
+        this.mc.currentWorld.entities.clear();
+        this.mc.currentWorld.tileEntityList.clear();
+        this.mc.thePlayer.absMoveTo(0.5, 64.5, 0.5, 180, 0);
+        this.mc.thePlayer.noPhysics = true;
+        this.mc.textureManager.refreshTexturesAndDisplayErrors();
+        this.mc.textureManager.updateDynamicTextures(false);
+
+        this.photoModeRenderer = new PhotoModeRenderer(this.mc, this);
 
-        this.previousRenderer = mc.renderer;
-        showPlayer = false;
-        showHelpText = false;
-        lastIZoom = iZoom = iZoomGoal = 8.5f;
+        this.previousRenderer = this.mc.renderer;
+        this.showPlayer = false;
+        this.showHelpText = false;
+        this.lastIZoom = this.iZoom = this.iZoomGoal = 8.5f;
 
-        mc.ppm.reset();
+        this.mc.ppm.reset();
 
-        iRotationGoal = iRotation = -2;
+        this.iRotationGoal = this.iRotation = -2;
 
-        categories.add(blockCategory);
-        categories.add(entityCategory);
-        categories.add(particleCategory);
-        setCategory(entityCategory);
+        this.categories.add(this.blockCategory);
+        this.categories.add(this.entityCategory);
+        this.categories.add(this.particleCategory);
+        setCategory(this.entityCategory);
     }
+
     @Override
-    public void init()
-    {
-        buttons.clear();
+    public void init() {
+        this.buttons.clear();
         I18n i18n = I18n.getInstance();
 
         List<ButtonElement> leftSideButtons = new ArrayList<>();
 
-        buttonExit = new ListenerButtonElement(5, 0, height - 20, 20, 20, "X");
-        buttonExit.setActionListener(this::exitToMenu);
+        this.buttonExit = new ListenerButtonElement(5, 0, this.height - 20, 20, 20, "X");
+        this.buttonExit.setActionListener(this::exitToMenu);
 
-        buttonRotateLeft = new ListenerButtonElement(0, width / 2 - 49 - 2 - 20, height - 20, 20, 20, "<");
-        buttonRotateLeft.setActionListener(() -> {
-            iRotationGoal += 1;
-            iRotationGoal = (int) iRotationGoal;
+        this.buttonRotateLeft = new ListenerButtonElement(0, this.width / 2 - 49 - 2 - 20, this.height - 20, 20, 20, "<");
+        this.buttonRotateLeft.setActionListener(() -> {
+            this.iRotationGoal += 1;
+            this.iRotationGoal = (int) this.iRotationGoal;
         });
-        buttonRotateRight = new ListenerButtonElement(1, width / 2 + 49 + 2, height - 20, 20, 20, ">");
-        buttonRotateRight.setActionListener(() -> {
-            iRotationGoal -= 1;
-            iRotationGoal = (int) iRotationGoal;
+        this.buttonRotateRight = new ListenerButtonElement(1, this.width / 2 + 49 + 2, this.height - 20, 20, 20, ">");
+        this.buttonRotateRight.setActionListener(() -> {
+            this.iRotationGoal -= 1;
+            this.iRotationGoal = (int) this.iRotationGoal;
         });
-        buttonTakeScreenshot = new ListenerButtonElement(4, width / 2 - 49, height - 20, 98, 20, i18n.translateKey("gui.photo_mode.button.take_screenshot"));
-        buttonTakeScreenshot.setActionListener(this::screenShot);
-
-        ButtonElement bulkRender = new ListenerButtonElement(4, width - 100, height - 20, 98, 20, i18n.translateKey("gui.model_viewer.button.bulk_render")).setActionListener(this::bulkRender);
-
-        buttonPrevEntry = new ListenerButtonElement(10, width / 2 - 49 - 2 - 20, height - 40 - 2, 20, 20, "<");
-        buttonPrevEntry.setActionListener(() -> currentCategory.cycleCategoryEntry(-1));
-        buttonNextEntry = new ListenerButtonElement(11, width / 2 + 49 + 2, height - 40 - 2, 20, 20, ">");
-        buttonNextEntry.setActionListener(() -> currentCategory.cycleCategoryEntry(1));
-        buttonCategory = new ListenerButtonElement(12, width / 2 - 49, height - 40 - 2, 98, 20, i18n.translateKey(currentCategory.getCategoryNameKey()));
-        buttonCategory.setActionListener(() -> setCategory(categories.get((categories.indexOf(currentCategory) + 1) % categories.size())));
-        buttonCategory.setOnValueChanged(() -> buttonCategory.displayString = i18n.translateKey(currentCategory.getCategoryNameKey()));
-
-        buttonReloadTextures = new ListenerButtonElement(12, 21, height - 20, 98, 20, i18n.translateKey("gui.model_viewer.button.reload_textures"));
-        buttonReloadTextures.setActionListener(() -> mc.texturePackList.refresh());
-        buttonOpenScreenshotFolder = (ListenerButtonElement) new ListenerButtonElement(30, buttonReloadTextures.getWidth() + buttonReloadTextures.getX() + 1, buttonReloadTextures.getY(), 20, 20, "")
+        this.buttonTakeScreenshot = new ListenerButtonElement(4, this.width / 2 - 49, this.height - 20, 98, 20, i18n.translateKey("gui.photo_mode.button.take_screenshot"));
+        this.buttonTakeScreenshot.setActionListener(this::screenShot);
+
+        ButtonElement bulkRender = new ListenerButtonElement(4, this.width - 100, this.height - 20, 98, 20, i18n.translateKey("gui.model_viewer.button.bulk_render")).setActionListener(this::bulkRender);
+
+        this.buttonPrevEntry = new ListenerButtonElement(10, this.width / 2 - 49 - 2 - 20, this.height - 40 - 2, 20, 20, "<");
+        this.buttonPrevEntry.setActionListener(() -> this.currentCategory.cycleCategoryEntry(-1));
+        this.buttonNextEntry = new ListenerButtonElement(11, this.width / 2 + 49 + 2, this.height - 40 - 2, 20, 20, ">");
+        this.buttonNextEntry.setActionListener(() -> this.currentCategory.cycleCategoryEntry(1));
+        this.buttonCategory = new ListenerButtonElement(12, this.width / 2 - 49, this.height - 40 - 2, 98, 20, i18n.translateKey(this.currentCategory.getCategoryNameKey()));
+        this.buttonCategory.setActionListener(() -> setCategory(this.categories.get((this.categories.indexOf(this.currentCategory) + 1) % this.categories.size())));
+        this.buttonCategory.setOnValueChanged(() -> this.buttonCategory.displayString = i18n.translateKey(this.currentCategory.getCategoryNameKey()));
+
+        this.buttonReloadTextures = new ListenerButtonElement(12, 21, this.height - 20, 98, 20, i18n.translateKey("gui.model_viewer.button.reload_textures"));
+        this.buttonReloadTextures.setActionListener(() -> this.mc.texturePackList.refresh());
+        this.buttonOpenScreenshotFolder = (ListenerButtonElement) new ListenerButtonElement(30, this.buttonReloadTextures.getWidth() + this.buttonReloadTextures.getX() + 1, this.buttonReloadTextures.getY(), 20, 20, "")
             .setTextures("minecraft:gui/misc/button_folder", "minecraft:gui/misc/button_folder_highlighted", "minecraft:gui/misc/button_folder");
-        buttonOpenScreenshotFolder.setActionListener(() -> FileOpener.open(new File(mc.getMinecraftDir(), "")));
+        this.buttonOpenScreenshotFolder.setActionListener(() -> FileOpener.open(new File(this.mc.getMinecraftDir(), "")));
 
-        buttonCenterScreen = new ListenerButtonElement(10, 0, 0, 120, 20, i18n.translateKey("gui.photo_mode.button.center_camera"));
-        buttonCenterScreen.setActionListener(() -> {
-            iPanXGoal = 0;
-            iPanYGoal = 0;
+        this.buttonCenterScreen = new ListenerButtonElement(10, 0, 0, 120, 20, i18n.translateKey("gui.photo_mode.button.center_camera"));
+        this.buttonCenterScreen.setActionListener(() -> {
+            this.iPanXGoal = 0;
+            this.iPanYGoal = 0;
         });
 
-        buttonTickToggle = new ListenerButtonElement(13, width - 120, 0, 99, 20, i18n.translateKeyAndFormat("gui.model_viewer.button.tickprogress", tickProgress));
-        buttonTickToggle.setActionListener(() -> tickProgress = !tickProgress);
-        buttonTickToggle.setOnValueChanged(() -> buttonTickToggle.displayString = i18n.translateKeyAndFormat("gui.model_viewer.button.tickprogress", tickProgress));
+        this.buttonTickToggle = new ListenerButtonElement(13, this.width - 120, 0, 99, 20, i18n.translateKeyAndFormat("gui.model_viewer.button.tickprogress", this.tickProgress));
+        this.buttonTickToggle.setActionListener(() -> this.tickProgress = !this.tickProgress);
+        this.buttonTickToggle.setOnValueChanged(() -> this.buttonTickToggle.displayString = i18n.translateKeyAndFormat("gui.model_viewer.button.tickprogress", this.tickProgress));
 
-        ListenerButtonElement cameraRotateButton = new ListenerButtonElement(-1, width - 120, 0, 120, 20, i18n.translateKeyAndFormat("gui.model_viewer.button.rotate", rotateToCamera));
+        ListenerButtonElement cameraRotateButton = new ListenerButtonElement(-1, this.width - 120, 0, 120, 20, i18n.translateKeyAndFormat("gui.model_viewer.button.rotate", this.rotateToCamera));
         cameraRotateButton.setActionListener(() -> {
-            rotateToCamera = !rotateToCamera;
-            cameraRotateButton.displayString = i18n.translateKeyAndFormat("gui.model_viewer.button.rotate", rotateToCamera);
+            this.rotateToCamera = !this.rotateToCamera;
+            cameraRotateButton.displayString = i18n.translateKeyAndFormat("gui.model_viewer.button.rotate", this.rotateToCamera);
         });
 
-        ListenerButtonElement buttonManualTick = new ListenerButtonElement(14, width - 21, 0, 20, 20, "+");
+        ListenerButtonElement buttonManualTick = new ListenerButtonElement(14, this.width - 21, 0, 20, 20, "+");
         buttonManualTick.setActionListener(this::entryTick);
 
-        sliderTilt = new ListenerSliderElement(7, 0, 0, 120, 20, i18n.translateKey("gui.photo_mode.button.tilt.default"), iTiltGoal / 90f);
-        sliderTilt.setOnValueChanged(() ->{
+        this.sliderTilt = new ListenerSliderElement(7, 0, 0, 120, 20, i18n.translateKey("gui.photo_mode.button.tilt.default"), this.iTiltGoal / 90f);
+        this.sliderTilt.setOnValueChanged(() -> {
             // Update tilt slider
             String tilt = i18n.translateKey("gui.photo_mode.button.tilt.default");
-            if ((int)(sliderTilt.sliderValue * 90.0f) != 30)
-            {
-                tilt = (int)(sliderTilt.sliderValue * 90.0f) + " degrees";
+            if ((int) (this.sliderTilt.sliderValue * 90.0f) != 30) {
+                tilt = (int) (this.sliderTilt.sliderValue * 90.0f) + " degrees";
             }
-            sliderTilt.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.tilt", tilt);
-            if (sliderTilt.dragging)
-            {
-                iTiltGoal = (float) (int)(sliderTilt.sliderValue * 90.0f);
+            this.sliderTilt.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.tilt", tilt);
+            if (this.sliderTilt.dragging) {
+                this.iTiltGoal = (float) (int) (this.sliderTilt.sliderValue * 90.0f);
             }
         });
-        if(Shaders.enableShaders) {
-            buttonShaders = new ListenerButtonElement(8, 0, 0, 120, 20, i18n.translateKeyAndFormat("gui.photo_mode.button.shader", i18n.translateKey("gui.photo_mode.button.shader.none")));
-            buttonShaders.setActionListener(() -> {
-                boolean ctrl = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
-                if (ctrl)
-                {
-                    photoModeRenderer.first();
-                }
-                else
-                {
-                    photoModeRenderer.next();
-                }
-                sliderIntensity.enabled = photoModeRenderer.getActiveShader() != null;
-            });
-            buttonShaders.setOnValueChanged(() -> {
-                String activeShader = photoModeRenderer.getActiveShader();
-                if (activeShader == null) activeShader = i18n.translateKey("gui.photo_mode.button.shader.none");
-                activeShader = activeShader.toUpperCase(Locale.ROOT);
-                buttonShaders.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.shader", activeShader);
-            });
-            sliderIntensity = new ListenerSliderElement(9, 0, 0, 120, 20, i18n.translateKeyAndFormat("gui.photo_mode.button.intensity", (int)(intensityValue * 100) + "%"), intensityValue);
-            sliderIntensity.setOnValueChanged(() ->{
-                // Update intensity slider
-                sliderIntensity.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.intensity", (int)(sliderIntensity.sliderValue * 100) + "%");
-                if (sliderIntensity.dragging) {
-                    intensityValue = (float) sliderIntensity.sliderValue;
-                }
-            });
-
-            if (photoModeRenderer.getActiveShader() == null) {
-                sliderIntensity.enabled = false;
+        this.buttonShaders = new ListenerButtonElement(8, 0, 0, 120, 20, i18n.translateKeyAndFormat("gui.photo_mode.button.shader", i18n.translateKey("gui.photo_mode.button.shader.none")));
+        this.buttonShaders.setActionListener(() -> {
+            boolean ctrl = Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL);
+            if (ctrl) {
+                this.photoModeRenderer.first();
+            } else {
+                this.photoModeRenderer.next();
             }
-        }
+            this.sliderIntensity.enabled = this.photoModeRenderer.getActiveShader() != null;
+        });
+        this.buttonShaders.setOnValueChanged(() -> {
+            String activeShader = this.photoModeRenderer.getActiveShader();
+            if (activeShader == null) activeShader = i18n.translateKey("gui.photo_mode.button.shader.none");
+            activeShader = activeShader.toUpperCase(Locale.ROOT);
+            this.buttonShaders.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.shader", activeShader);
+        });
+        this.sliderIntensity = new ListenerSliderElement(9, 0, 0, 120, 20, i18n.translateKeyAndFormat("gui.photo_mode.button.intensity", (int) (this.intensityValue * 100) + "%"), this.intensityValue);
+        this.sliderIntensity.setOnValueChanged(() -> {
+            // Update intensity slider
+            this.sliderIntensity.displayString = i18n.translateKeyAndFormat("gui.photo_mode.button.intensity", (int) (this.sliderIntensity.sliderValue * 100) + "%");
+            if (this.sliderIntensity.dragging) {
+                this.intensityValue = (float) this.sliderIntensity.sliderValue;
+            }
+        });
 
-        if(Shaders.enableShaders) {
-            mc.setRenderer(photoModeRenderer);
+        if (this.photoModeRenderer.getActiveShader() == null) {
+            this.sliderIntensity.enabled = false;
         }
 
-        buttons.add(cameraRotateButton);
-        buttons.add(buttonTickToggle);
+        this.mc.setRenderer(this.photoModeRenderer);
 
-        int i=0;
-        List<ButtonElement> _buttons = new ArrayList<>(buttons);
-        for(ButtonElement button : _buttons) {
+        this.buttons.add(cameraRotateButton);
+        this.buttons.add(this.buttonTickToggle);
+
+        int i = 0;
+        List<ButtonElement> _buttons = new ArrayList<>(this.buttons);
+        for (ButtonElement button : _buttons) {
             button.yPosition = i++ * 21;
         }
 
-        buttons.add(buttonManualTick);
-        buttonManualTick.yPosition = buttonTickToggle.yPosition;
+        this.buttons.add(buttonManualTick);
+        buttonManualTick.yPosition = this.buttonTickToggle.yPosition;
 
-        currentCategory.addContextButtons(buttons);
+        this.currentCategory.addContextButtons(this.buttons);
 
-        leftSideButtons.add(buttonCenterScreen);
-        leftSideButtons.add(sliderTilt);
+        leftSideButtons.add(this.buttonCenterScreen);
+        leftSideButtons.add(this.sliderTilt);
 
-        if(Shaders.enableShaders) {
-            leftSideButtons.add(buttonShaders);
-            leftSideButtons.add(sliderIntensity);
-        }
+        leftSideButtons.add(this.buttonShaders);
+        leftSideButtons.add(this.sliderIntensity);
 
         int j = 0;
-        for (ButtonElement button: leftSideButtons){
+        for (ButtonElement button : leftSideButtons) {
             button.yPosition = j++ * 21;
         }
 
-        buttons.addAll(leftSideButtons);
+        this.buttons.addAll(leftSideButtons);
 
-        ListenerTextFieldElement rField = new ListenerTextFieldElement(this, fontRenderer, 0, j++ * 21, 40, 20, String.valueOf(bgRed), "Red");
+        ListenerTextFieldElement rField = new ListenerTextFieldElement(this, this.fontRenderer, 0, j++ * 21, 40, 20, String.valueOf(this.bgRed), "Red");
         rField.setPrefaceText("R: ");
         rField.setKeyListener(key -> {
             try {
-                bgRed = Integer.parseInt(rField.getText());
-            } catch (Exception ignored){}
+                this.bgRed = Integer.parseInt(rField.getText());
+            } catch (Exception ignored) {
+            }
         });
         rField.setActionListener(() -> {
-            if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)){
-                rField.setText(String.valueOf(defaultRed));
-                bgRed = defaultRed;
+            if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)) {
+                rField.setText(String.valueOf(this.defaultRed));
+                this.bgRed = this.defaultRed;
             }
         });
-        ListenerTextFieldElement gField = new ListenerTextFieldElement(this, fontRenderer, 40, rField.yPosition, 40, 20, String.valueOf(bgGreen), "Green");
+        ListenerTextFieldElement gField = new ListenerTextFieldElement(this, this.fontRenderer, 40, rField.yPosition, 40, 20, String.valueOf(this.bgGreen), "Green");
         gField.setPrefaceText("G: ");
         gField.setKeyListener(key -> {
             try {
-                bgGreen = Integer.parseInt(gField.getText());
-            } catch (Exception ignored){}
+                this.bgGreen = Integer.parseInt(gField.getText());
+            } catch (Exception ignored) {
+            }
         });
         gField.setActionListener(() -> {
-            if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)){
-                gField.setText(String.valueOf(defaultGreen));
-                bgGreen = defaultGreen;
+            if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)) {
+                gField.setText(String.valueOf(this.defaultGreen));
+                this.bgGreen = this.defaultGreen;
             }
         });
-        ListenerTextFieldElement bField = new ListenerTextFieldElement(this, fontRenderer, 80, rField.yPosition, 40, 20, String.valueOf(bgBlue), "Blue");
+        ListenerTextFieldElement bField = new ListenerTextFieldElement(this, this.fontRenderer, 80, rField.yPosition, 40, 20, String.valueOf(this.bgBlue), "Blue");
         bField.setPrefaceText("B: ");
         bField.setKeyListener(key -> {
             try {
-                bgBlue = Integer.parseInt(bField.getText());
-            } catch (Exception ignored){}
+                this.bgBlue = Integer.parseInt(bField.getText());
+            } catch (Exception ignored) {
+            }
         });
         bField.setActionListener(() -> {
-            if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)){
-                bField.setText(String.valueOf(defaultBlue));
-                bgBlue = defaultBlue;
+            if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL)) {
+                bField.setText(String.valueOf(this.defaultBlue));
+                this.bgBlue = this.defaultBlue;
             }
         });
 
-        buttons.add(rField);
-        buttons.add(gField);
-        buttons.add(bField);
-
-        buttons.add(buttonRotateLeft);
-        buttons.add(buttonRotateRight);
-        buttons.add(buttonTakeScreenshot);
-        buttons.add(bulkRender);
-        buttons.add(buttonOpenScreenshotFolder);
-        buttons.add(buttonPrevEntry);
-        buttons.add(buttonNextEntry);
-        buttons.add(buttonCategory);
-        buttons.add(buttonReloadTextures);
-        buttons.add(buttonExit);
+        this.buttons.add(rField);
+        this.buttons.add(gField);
+        this.buttons.add(bField);
+
+        this.buttons.add(this.buttonRotateLeft);
+        this.buttons.add(this.buttonRotateRight);
+        this.buttons.add(this.buttonTakeScreenshot);
+        this.buttons.add(bulkRender);
+        this.buttons.add(this.buttonOpenScreenshotFolder);
+        this.buttons.add(this.buttonPrevEntry);
+        this.buttons.add(this.buttonNextEntry);
+        this.buttons.add(this.buttonCategory);
+        this.buttons.add(this.buttonReloadTextures);
+        this.buttons.add(this.buttonExit);
     }
-    private void setCategory(ModelViewerCategory category){
-        if (currentCategory != null){
-            currentCategory.onClose();
+
+    private void setCategory(ModelViewerCategory category) {
+        if (this.currentCategory != null) {
+            this.currentCategory.onClose();
         }
-        currentCategory = category;
-        if (currentCategory != null){
-            currentCategory.onOpen();
+        this.currentCategory = category;
+        if (this.currentCategory != null) {
+            this.currentCategory.onOpen();
         }
         init();
     }
-    public static int cycleItemId(int itemId, int offset){
+
+    public static int cycleItemId(int itemId, int offset) {
         int id = (itemId + Item.itemsList.length + offset) % Item.itemsList.length;
-        while (Item.itemsList[id] == null){
+        while (Item.itemsList[id] == null) {
             id = (id + (int) Math.signum(offset) + Item.itemsList.length) % Item.itemsList.length;
         }
         return id;
     }
+
     private @Nullable ModelViewerCategory.Info lastInfo = null;
+
     @Override
-    public void render(int mx, int my, float partialTick)
-    {
-        if (lastInfo != null) {
-            specificScreenshot(lastInfo.outputFile());
+    public void render(int mx, int my, float partialTick) {
+        if (this.lastInfo != null) {
+            specificScreenshot(this.lastInfo.outputFile());
         }
-        if (this.currentCategory == blockCategory && !blockCategoryBulkRenders.isEmpty()) {
-            lastInfo = blockCategoryBulkRenders.remove(0);
-            mc.currentWorld.entities.clear();
-            mc.currentWorld.tileEntityList.clear();
-            blockCategory.setupRender(lastInfo);
-            iRotation = iRotationGoal = lastInfo.renderRotation();
-            iZoom = iZoomGoal = lastInfo.renderZoom();
+        if (this.currentCategory == this.blockCategory && !this.blockCategoryBulkRenders.isEmpty()) {
+            this.lastInfo = this.blockCategoryBulkRenders.remove(0);
+            this.mc.currentWorld.entities.clear();
+            this.mc.currentWorld.tileEntityList.clear();
+            this.blockCategory.setupRender(this.lastInfo);
+            this.iRotation = this.iRotationGoal = this.lastInfo.renderRotation();
+            this.iZoom = this.iZoomGoal = this.lastInfo.renderZoom();
         } else {
-            lastInfo = null;
+            this.lastInfo = null;
         }
 
-        GL11.glViewport(0, 0, mc.gameWindow.getWidthPixels(), mc.gameWindow.getHeightPixels());
-        GL11.glMatrixMode(GL11.GL_PROJECTION);
-        GL11.glLoadIdentity();
-        GL11.glMatrixMode(GL11.GL_MODELVIEW /*GL_MODELVIEW0_ARB*/);
-        GL11.glLoadIdentity();
-        GL11.glClear(256);
-        GL11.glMatrixMode(GL11.GL_PROJECTION);
-        GL11.glLoadIdentity();
-        GL11.glOrtho(0.0D, mc.resolution.getExactScaledWidthScreenCoords(), mc.resolution.getExactScaledHeightScreenCoords(), 0.0D, 1000D, 3000D);
-        GL11.glMatrixMode(GL11.GL_MODELVIEW /*GL_MODELVIEW0_ARB*/);
-        GL11.glLoadIdentity();
-        GL11.glTranslatef(0.0F, 0.0F, -2000F);
-
-        if (rotateToCamera){
-            mc.thePlayer.yRotO = mc.thePlayer.yRot = getRotation(partialTick) * 45f - 135f;
+        GL41.glViewport(0, 0, this.mc.gameWindow.getWidthPixels(), this.mc.gameWindow.getHeightPixels());
+        GLRenderer.projectionM4f().identity().ortho(0.0f, (float) this.mc.resolution.getExactScaledWidthScreenCoords(), (float) this.mc.resolution.getExactScaledHeightScreenCoords(), 0.0f, 1000f, 3000f);
+        GLRenderer.viewM4f().identity();
+        GLRenderer.modelM4f().identity();
+        GL41.glClear(GL41.GL_DEPTH_BUFFER_BIT);
+        GLRenderer.modelM4f().translate(0.0F, 0.0F, -2000F);
+
+        if (this.rotateToCamera) {
+            this.mc.thePlayer.yRotO = this.mc.thePlayer.yRot = getRotation(partialTick) * 45f - 135f;
         } else {
-            mc.thePlayer.yRotO = mc.thePlayer.yRot = 180;
+            this.mc.thePlayer.yRotO = this.mc.thePlayer.yRot = 180;
         }
 
-        lastIZoom = iZoom;
-        if (iZoom != iZoomGoal)
-        {
-            iZoom += (iZoomGoal - iZoom) * 0.08f;
-            if (Math.abs(iZoom - iZoomGoal) < 0.0005f) iZoom = iZoomGoal;
+        this.lastIZoom = this.iZoom;
+        if (this.iZoom != this.iZoomGoal) {
+            this.iZoom += (this.iZoomGoal - this.iZoom) * 0.08f;
+            if (Math.abs(this.iZoom - this.iZoomGoal) < 0.0005f) this.iZoom = this.iZoomGoal;
         }
 
-        lastIRotation = iRotation;
-        if (iRotation != iRotationGoal)
-        {
-            iRotation += (iRotationGoal - iRotation) * 0.08f;
-            if (Math.abs(iRotation - iRotationGoal) < 0.0005f) iRotation = iRotationGoal;
+        this.lastIRotation = this.iRotation;
+        if (this.iRotation != this.iRotationGoal) {
+            this.iRotation += (this.iRotationGoal - this.iRotation) * 0.08f;
+            if (Math.abs(this.iRotation - this.iRotationGoal) < 0.0005f) this.iRotation = this.iRotationGoal;
         }
 
-        lastITilt = iTilt;
-        if (iTilt != iTiltGoal)
-        {
-            iTilt += (iTiltGoal - iTilt) * 0.08f;
-            if (Math.abs(iTilt - iTiltGoal) < 0.01f) iTilt = iTiltGoal;
+        this.lastITilt = this.iTilt;
+        if (this.iTilt != this.iTiltGoal) {
+            this.iTilt += (this.iTiltGoal - this.iTilt) * 0.08f;
+            if (Math.abs(this.iTilt - this.iTiltGoal) < 0.01f) this.iTilt = this.iTiltGoal;
         }
 
-        lastIPanX = iPanX;
-        if (iPanX != iPanXGoal)
-        {
-            iPanX += (iPanXGoal - iPanX) * 0.4f;
-            if (Math.abs(iPanX - iPanXGoal) < 0.01f) iPanX = iPanXGoal;
+        this.lastIPanX = this.iPanX;
+        if (this.iPanX != this.iPanXGoal) {
+            this.iPanX += (this.iPanXGoal - this.iPanX) * 0.4f;
+            if (Math.abs(this.iPanX - this.iPanXGoal) < 0.01f) this.iPanX = this.iPanXGoal;
         }
 
-        lastIPanY = iPanY;
-        if (iPanY != iPanYGoal)
-        {
-            iPanY += (iPanYGoal - iPanY) * 0.4f;
-            if (Math.abs(iPanY - iPanYGoal) < 0.01f) iPanY = iPanYGoal;
+        this.lastIPanY = this.iPanY;
+        if (this.iPanY != this.iPanYGoal) {
+            this.iPanY += (this.iPanYGoal - this.iPanY) * 0.4f;
+            if (Math.abs(this.iPanY - this.iPanYGoal) < 0.01f) this.iPanY = this.iPanYGoal;
         }
 
-        buttonCenterScreen.enabled = (iPanX != 0 || iPanY != 0) && !(iPanXGoal == 0 && iPanYGoal == 0);
+        this.buttonCenterScreen.enabled = (this.iPanX != 0 || this.iPanY != 0) && !(this.iPanXGoal == 0 && this.iPanYGoal == 0);
 
-        List<ButtonElement> _buttons = new ArrayList<>(buttons);
+        List<ButtonElement> _buttons = new ArrayList<>(this.buttons);
         for (ButtonElement button : _buttons) {
-            button.drawButton(mc, mx, my);
+            button.drawButton(this.mc, mx, my);
         }
 
         scroll(Mouse.getDWheel());
 
-//        TileEntityRenderDispatcher.instance.renderTileEntity(Tessellator.instance, new TileEntity(), -0.5D, -0.75D, -0.5D, partialTick);
+//        TileEntityRenderDispatcher.instance.renderTileEntity(GLRenderer.getTessellator(), new TileEntity(), -0.5D, -0.75D, -0.5D, partialTick);
 
-        drawStringCenteredShadow(fontRenderer, currentCategory.getCurrentDisplayInfo(I18n.getInstance()), width/2, 1, 0xffffff);
+        drawStringCenteredShadow(this.fontRenderer, this.currentCategory.getCurrentDisplayInfo(I18n.getInstance()), this.width / 2, 1, 0xffffff);
     }
+
     @Override
-    public void keyPressed(char eventCharacter, int eventKey, int mx, int my)
-    {
+    public void keyPressed(char eventCharacter, int eventKey, int mx, int my) {
         if (eventKey == Keyboard.KEY_ESCAPE) {
             exitToMenu();
         }
-        List<ButtonElement> _buttons = new ArrayList<>(buttons);
-        for (ButtonElement button : _buttons){
-            if (button instanceof IListenerElement && button.isHovered(mx, my)){
-                ((IListenerElement<?>) button).onKeyTyped(eventCharacter, eventKey);
+        List<ButtonElement> _buttons = new ArrayList<>(this.buttons);
+        for (ButtonElement button : _buttons) {
+            if (button instanceof IListenerElement<?> element && button.isHovered(mx, my)) {
+                element.onKeyTyped(eventCharacter, eventKey);
             }
         }
     }
-    private void exitToMenu(){
-        currentCategory.onClose();
-        mc.changeWorld(null);
-        mc.displayScreen(new ScreenOptions(null, OptionsPages.DEBUG));
+
+    private void exitToMenu() {
+        this.currentCategory.onClose();
+        this.mc.changeWorld(null);
+        this.mc.displayScreen(new ScreenOptions(null, OptionsPages.DEBUG));
     }
-    public static int cycleBlockId(int id, int idOff){
+
+    public static int cycleBlockId(int id, int idOff) {
         int id2 = (id + Blocks.blocksList.length + idOff) % Blocks.blocksList.length;
-        while (Blocks.blocksList[id2] == null){
+        while (Blocks.blocksList[id2] == null) {
             id2 = (id2 + (int) Math.signum(idOff) + Blocks.blocksList.length) % Blocks.blocksList.length;
         }
         return id2;
     }
+
     @Override
     public void removed() {
-        if(Shaders.enableShaders) {
-            mc.setRenderer(previousRenderer);
-        }
+        this.mc.setRenderer(this.previousRenderer);
         Minecraft.doPartialTick = true;
     }
+
     @Override
-    public void tick()
-    {
+    public void tick() {
         super.tick();
-        List<ButtonElement> _buttons = new ArrayList<>(buttons);
-        for (ButtonElement button : _buttons){
-            if (button instanceof ListenerButtonElement){
-                ((ListenerButtonElement) button).tick();
+        List<ButtonElement> _buttons = new ArrayList<>(this.buttons);
+        for (ButtonElement button : _buttons) {
+            if (button instanceof ListenerButtonElement element) {
+                element.tick();
             }
         }
-        if (tickProgress){
+        if (this.tickProgress) {
             entryTick();
         }
-        Minecraft.doPartialTick = tickProgress;
+        Minecraft.doPartialTick = this.tickProgress;
     }
-    private void entryTick(){
-        mc.textureManager.updateDynamicTextures(false);
-        mc.particleEngine.tick();
-        currentCategory.onTick();
+
+    private void entryTick() {
+        this.mc.textureManager.updateDynamicTextures(false);
+        this.mc.particleEngine.tick();
+        this.currentCategory.onTick();
         // TODO this fixes world time based animation, but also ticks things like wind and im not certain on the best way to set wind direction arbitrarily right now
 //        mc.theWorld.getLevelData().setWorldTime(mc.theWorld.getWorldTime() + 1);
     }
+
     @Override
     protected void buttonClicked(@NotNull ButtonElement button) {
         // Overrides the regular GuiPhotomode's method
     }
 
     public long timeLastKeyPressed = System.currentTimeMillis();
+
     @Override
     public void textChanged(ListenerTextFieldElement textField) {
-        timeLastKeyPressed = System.currentTimeMillis();
+        this.timeLastKeyPressed = System.currentTimeMillis();
     }
-    public float[] getBackgroundFogColor(){
-        return new float[]{bgRed/255f, bgGreen/255f, bgBlue/255f};
+
+    public float[] getBackgroundFogColor() {
+        return new float[]{this.bgRed / 255f, this.bgGreen / 255f, this.bgBlue / 255f};
     }
+
     private static final DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd_HH.mm.ss");
-    public void screenShot(){
+
+    public void screenShot() {
         try {
-            File screenshotsDir = new File(mc.getMinecraftDir(), "screenshots");
+            File screenshotsDir = new File(this.mc.getMinecraftDir(), "screenshots");
             //noinspection ResultOfMethodCallIgnored
             screenshotsDir.mkdir();
-            Texture texture = ((ShadersRenderer)mc.renderer).getWorldFramebufferTex();
+            Texture texture = ((ShadersRenderer) this.mc.renderer).getWorldFramebufferColor();
             texture.bind();
 
             int w = glGetTexLevelParameteri(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH);
@@ -492,7 +482,7 @@ public class ScreenModelViewer extends ScreenPhotoMode implements ListenerTextFi
 
             buffer.position(0).limit(size);
             glGetTexImage(GL_TEXTURE_2D, 0, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
-            if(glGetError() == 0) {
+            if (glGetError() == 0) {
                 buffer.position(0);
                 File outPut;
                 String timeStamp = "Render_" + dateFormat.format(new Date());
@@ -502,17 +492,17 @@ public class ScreenModelViewer extends ScreenPhotoMode implements ListenerTextFi
                 }
                 ImageUtils.saveExternalImage(Textures.getImage(buffer, w, h, true, true), outPut);
 
-            }else {
+            } else {
                 LOGGER.warn("Cannot get pixel data for screenshot!");
             }
-        } catch (Exception e){
+        } catch (Exception e) {
             LOGGER.error("Exception while trying to take Model Viewer ScreenShot", e);
         }
     }
 
     public void specificScreenshot(@NotNull File destination) {
         try {
-            Texture texture = ((ShadersRenderer)mc.renderer).getWorldFramebufferTex();
+            Texture texture = ((ShadersRenderer) this.mc.renderer).getWorldFramebufferColor();
             texture.bind();
 
             int w = glGetTexLevelParameteri(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH);
@@ -524,28 +514,28 @@ public class ScreenModelViewer extends ScreenPhotoMode implements ListenerTextFi
 
             buffer.position(0).limit(size);
             glGetTexImage(GL_TEXTURE_2D, 0, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
-            if(glGetError() == 0) {
+            if (glGetError() == 0) {
                 buffer.position(0);
                 ImageUtils.saveExternalImage(Textures.getImage(buffer, w, h, true, true), destination);
 
-            }else {
+            } else {
                 LOGGER.warn("Cannot get pixel data for screenshot!");
             }
-        } catch (Exception e){
+        } catch (Exception e) {
             LOGGER.error("Exception while trying to take Model Viewer ScreenShot", e);
         }
     }
 
     public void bulkRender() {
-        iRotation = iRotationGoal = 0;
-        iPanX = iPanXGoal = lastIPanX = 0;
-        iPanY = iPanYGoal = lastIPanY = -0.4574755f;
-        iZoom = iZoomGoal = 8.5f;
-        mc.gameWindow.setWindowSize(1024, 1024);
-        File bulkOutputDir = new File(mc.getMinecraftDir(), "bulkRenders");
+        this.iRotation = this.iRotationGoal = 0;
+        this.iPanX = this.iPanXGoal = this.lastIPanX = 0;
+        this.iPanY = this.iPanYGoal = this.lastIPanY = -0.4574755f;
+        this.iZoom = this.iZoomGoal = 8.5f;
+        this.mc.gameWindow.setWindowSize(1024, 1024);
+        File bulkOutputDir = new File(this.mc.getMinecraftDir(), "bulkRenders");
         bulkOutputDir.mkdirs();
 
-        setCategory(blockCategory);
-        blockCategory.queueBulkRender(bulkOutputDir, blockCategoryBulkRenders);
+        setCategory(this.blockCategory);
+        this.blockCategory.queueBulkRender(bulkOutputDir, this.blockCategoryBulkRenders);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/ScreenNBTEditor.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/ScreenNBTEditor.java
index d9a477db9..372f7bb87 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/ScreenNBTEditor.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/ScreenNBTEditor.java
@@ -2,22 +2,17 @@ package net.minecraft.client.gui.nbteditor;
 
 import com.mojang.logging.LogUtils;
 import com.mojang.nbt.tags.CompoundTag;
-import com.mojang.nbt.tags.Tag;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.gui.nbteditor.components.AbstractTagComponent;
 import net.minecraft.client.gui.nbteditor.components.CompoundTagComponent;
 import net.minecraft.client.render.Scissor;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 import org.slf4j.Logger;
 
-import java.util.ArrayList;
-import java.util.Comparator;
-import java.util.List;
 import java.util.function.Function;
 
 public class ScreenNBTEditor extends Screen {
@@ -48,102 +43,102 @@ public class ScreenNBTEditor extends Screen {
     @Override
     public void removed() {
         if (this.tagAction != null) {
-            this.tagAction.apply((CompoundTag) compoundTagComponent.tag);
+            this.tagAction.apply((CompoundTag) this.compoundTagComponent.tag);
         }
     }
 
     @Override
     public void render(int mx, int my, float partialTick) {
-        int compHeight = compoundTagComponent.height(-1, -1, partialTick);
+        int compHeight = this.compoundTagComponent.height(-1, -1, partialTick);
         int minScroll = 0;
-        int maxScroll = Math.max(compHeight - (height - 84), 0);
+        int maxScroll = Math.max(compHeight - (this.height - 84), 0);
         this.scroll += Mouse.getDWheel() * 10;
         this.scroll = MathHelper.clamp(this.scroll, -maxScroll, minScroll);
 
         renderBackground();
         super.render(mx, my, partialTick);
 
-        Tessellator t = Tessellator.instance;
+        TessellatorGeneral t = GLRenderer.getTessellator();
 
         {
-            int popupWidth = width/2 + 40;
-            int popupHeight = height - 40;
-            int popupX = width / 2 - popupWidth / 2;
-            int popupY = height / 2 - popupHeight / 2;
+            int popupWidth = this.width / 2 + 40;
+            int popupHeight = this.height - 40;
+            int popupX = this.width / 2 - popupWidth / 2;
+            int popupY = this.height / 2 - popupHeight / 2;
 
-            GL11.glDisable(GL11.GL_LIGHTING);
-            GL11.glDisable(GL11.GL_FOG);
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            GLRenderer.globalSetLightEnabled(false);
+//            GL11.glDisable(GL11.GL_FOG);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
 
-            GL11.glEnable(GL11.GL_TEXTURE_2D);
+//            GL11.glEnable(GL11.GL_TEXTURE_2D);
             float f = 32F;
             t.startDrawingQuads();
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            t.setColorOpaque_I(0x404040);
-            t.addVertexWithUV(popupX, popupY + popupHeight, 0.0D, 0.0D, (float)popupHeight / f);
-            t.addVertexWithUV(popupX + popupWidth, popupY + popupHeight, 0.0D, (float)popupWidth / f, (float)popupHeight / f);
-            t.addVertexWithUV(popupX + popupWidth, popupY, 0.0D, (float)popupWidth / f, 0);
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+            t.setColorOpaque1i(0x404040);
+            t.addVertexWithUV(popupX, popupY + popupHeight, 0.0D, 0.0D, (float) popupHeight / f);
+            t.addVertexWithUV(popupX + popupWidth, popupY + popupHeight, 0.0D, (float) popupWidth / f, (float) popupHeight / f);
+            t.addVertexWithUV(popupX + popupWidth, popupY, 0.0D, (float) popupWidth / f, 0);
             t.addVertexWithUV(popupX, popupY, 0.0D, 0.0D, 0);
             t.draw();
 
-            drawRect(width/4, 40, (width * 3)/4, height - 40, 0x88000000);
+            drawRect(this.width / 4, 40, (this.width * 3) / 4, this.height - 40, 0x88000000);
         }
 
-        fontRenderer.renderCentered(t, title, width/2, 26).setShadow().call();
+        this.fontRenderer.renderCentered(this.title, this.width / 2, 26).setShadow().call();
 
         if (minScroll != maxScroll) {
-            drawRect((width * 3)/4 - 5, 41, (width * 3)/4 - 1, height - 43, 0xFF000000);
+            drawRect((this.width * 3) / 4 - 5, 41, (this.width * 3) / 4 - 1, this.height - 43, 0xFF000000);
 
             int scrollableRegion = compHeight;
-            int regionHeight = height - 84;
-            int sMin = (int) scroll;
+            int regionHeight = this.height - 84;
+            int sMin = (int) this.scroll;
 
-            int barMinX = (width * 3)/4 - 6;
-            int barMaxX = (width * 3)/4 - 2;
-            int barMinY = (42 - MathHelper.round(((double)sMin/scrollableRegion) * regionHeight));
-            int barMaxY = barMinY + MathHelper.round(((double)regionHeight/scrollableRegion) * regionHeight);
+            int barMinX = (this.width * 3) / 4 - 6;
+            int barMaxX = (this.width * 3) / 4 - 2;
+            int barMinY = (42 - MathHelper.round(((double) sMin / scrollableRegion) * regionHeight));
+            int barMaxY = barMinY + MathHelper.round(((double) regionHeight / scrollableRegion) * regionHeight);
 
             boolean hovered = mx >= barMinX && mx <= barMaxX && my >= barMinY && my <= barMaxY;
             drawRect(barMinX, barMinY, barMaxX, barMaxY, hovered ? 0xFFCCCCFF : 0xFFFFFFFF);
         }
 
-        Scissor.enable(width/4 - 20, 40, width/2 + 13, height - 80);
-        int y = (int) (42 + scroll);
+        Scissor.enable(this.width / 4 - 20, 40, this.width / 2 + 13, this.height - 80);
+        int y = (int) (42 + this.scroll);
         boolean inPane =
-            mx >= width/4 - 20 &&
-            mx <=(width * 3)/4 -20 + 13 &&
-            my >= 40 &&
-            my <= height - 40;
-        compoundTagComponent.render(t, width/4 + 2, y, inPane ? mx - width/4 : -1, inPane ? my - y : -1, partialTick);
+            mx >= this.width / 4 - 20 &&
+                mx <= (this.width * 3) / 4 - 20 + 13 &&
+                my >= 40 &&
+                my <= this.height - 40;
+        this.compoundTagComponent.render(t, this.width / 4 + 2, y, inPane ? mx - this.width / 4 : -1, inPane ? my - y : -1, partialTick);
         Scissor.disable();
 
-        drawBox(width/4 - 20, 20, (width * 3)/4 + 20, height - 20, 0xFFFFFFFF, 1);
-        drawBox(width/4, 40, (width * 3)/4, height - 40, 0xFFFFFFFF, 1);
+        drawBox(this.width / 4 - 20, 20, (this.width * 3) / 4 + 20, this.height - 20, 0xFFFFFFFF, 1);
+        drawBox(this.width / 4, 40, (this.width * 3) / 4, this.height - 40, 0xFFFFFFFF, 1);
     }
 
     @Override
     public void mouseClicked(int mx, int my, int buttonNum) {
         super.mouseClicked(mx, my, buttonNum);
 
-        int y = (int) (42 + scroll);
+        int y = (int) (42 + this.scroll);
         boolean inPane =
-            mx >= width/4 - 20 &&
-                mx <=(width * 3)/4 -20 + 13 &&
+            mx >= this.width / 4 - 20 &&
+                mx <= (this.width * 3) / 4 - 20 + 13 &&
                 my >= 40 &&
-                my <= height - 40;
-        compoundTagComponent.onMouseClick(inPane ? mx - width/4 : -1, inPane ? my - y : -1, buttonNum, 1);
+                my <= this.height - 40;
+        this.compoundTagComponent.onMouseClick(inPane ? mx - this.width / 4 : -1, inPane ? my - y : -1, buttonNum, 1);
     }
 
     @Override
     public void mouseReleased(int mx, int my, int buttonNum) {
         super.mouseReleased(mx, my, buttonNum);
 
-        int y = (int) (42 + scroll);
+        int y = (int) (42 + this.scroll);
         boolean inPane =
-            mx >= width/4 - 20 &&
-                mx <=(width * 3)/4 -20 + 13 &&
+            mx >= this.width / 4 - 20 &&
+                mx <= (this.width * 3) / 4 - 20 + 13 &&
                 my >= 40 &&
-                my <= height - 40;
-        compoundTagComponent.onMouseRelease(inPane ? mx - width/4 : -1, inPane ? my - y : -1, buttonNum, 1);
+                my <= this.height - 40;
+        this.compoundTagComponent.onMouseRelease(inPane ? mx - this.width / 4 : -1, inPane ? my - y : -1, buttonNum, 1);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/AbstractTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/AbstractTagComponent.java
index e31a922bf..5149e91cc 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/AbstractTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/AbstractTagComponent.java
@@ -16,11 +16,11 @@ import com.mojang.nbt.tags.StringTag;
 import com.mojang.nbt.tags.Tag;
 import net.minecraft.client.gui.Gui;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 public abstract class AbstractTagComponent<T> extends Gui {
     public static final int COLOR_BACKGROUND = 0x88A0A0A0;
@@ -36,8 +36,8 @@ public abstract class AbstractTagComponent<T> extends Gui {
         this.tag = tag;
     }
 
-    public void render(@NotNull Tessellator t, int offX, int offY, int mx, int my, float partialTick) {
-        GL11.glColor4f(1, 1, 1, 1);
+    public void render(@NotNull TessellatorGeneral t, int offX, int offY, int mx, int my, float partialTick) {
+        GLRenderer.setColor4f(1, 1, 1, 1);
         drawGuiIcon(offX, offY, 12, 12, getIcon(mx, my, partialTick));
     }
 
@@ -45,7 +45,7 @@ public abstract class AbstractTagComponent<T> extends Gui {
         return 12;
     }
     public int width(int mx, int my, float partialTick) {
-        return attachedScreen.width/2;
+        return this.attachedScreen.width/2;
     }
 
     public boolean isHovered(int mx, int my, float partialTick) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ArrayTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ArrayTagComponent.java
index c23eb9589..553581180 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ArrayTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ArrayTagComponent.java
@@ -4,12 +4,9 @@ import com.mojang.logging.LogUtils;
 import com.mojang.nbt.tags.Tag;
 import net.minecraft.client.gui.Screen;
 import net.minecraft.client.gui.popup.PopupBuilder;
-import net.minecraft.client.render.tessellator.Tessellator;
 import org.jetbrains.annotations.NotNull;
 import org.slf4j.Logger;
 
-import java.lang.reflect.Array;
-
 public abstract class ArrayTagComponent<T> extends AbstractTagComponent<T> {
     private static final Logger LOGGER = LogUtils.getLogger();
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ByteArrayTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ByteArrayTagComponent.java
index 2c117f799..4b0dbbad4 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ByteArrayTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ByteArrayTagComponent.java
@@ -1,15 +1,12 @@
 package net.minecraft.client.gui.nbteditor.components;
 
-import com.mojang.logging.LogUtils;
 import com.mojang.nbt.tags.ByteArrayTag;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.gui.popup.PopupBuilder;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.DyeColor;
 import org.jetbrains.annotations.NotNull;
-import org.slf4j.Logger;
 
 public class ByteArrayTagComponent extends ArrayTagComponent<byte[]> {
     public static final @NotNull IconCoordinate icon = TextureRegistry.getTexture("minecraft:gui/screen/nbt/byte_array_tag");
@@ -20,13 +17,13 @@ public class ByteArrayTagComponent extends ArrayTagComponent<byte[]> {
     }
 
     @Override
-    public void render(@NotNull Tessellator t, int offX, int offY, int mx, int my, float partialTick) {
+    public void render(@NotNull TessellatorGeneral t, int offX, int offY, int mx, int my, float partialTick) {
         super.render(t, offX, offY, mx, my, partialTick);
         drawRect(offX + 12 + COMPONENT_PADDING, offY, offX + width(mx, my, partialTick), offY + height(mx, my, partialTick), isHovered(mx, my, partialTick) ? COLOR_BACKGROUND_HIGHLIGHTED : COLOR_BACKGROUND);
-        attachedScreen.fontRenderer.render(t, tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, ": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, this.tag.getValue().length, attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
-        attachedScreen.fontRenderer.render(t, " bytes", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(this.tag.getValue().length, attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(" bytes", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/CompoundTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/CompoundTagComponent.java
index da7136917..1e409066c 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/CompoundTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/CompoundTagComponent.java
@@ -3,7 +3,7 @@ package net.minecraft.client.gui.nbteditor.components;
 import com.mojang.nbt.tags.CompoundTag;
 import com.mojang.nbt.tags.Tag;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.DyeColor;
@@ -33,14 +33,14 @@ public class CompoundTagComponent extends AbstractTagComponent<@NotNull Map<Stri
     }
 
     @Override
-    public void render(@NotNull Tessellator t, int offX, int offY, int mx, int my, float partialTick) {
+    public void render(@NotNull TessellatorGeneral t, int offX, int offY, int mx, int my, float partialTick) {
         super.render(t, offX, offY, mx, my, partialTick);
         drawRect(offX + 12 + COMPONENT_PADDING, offY, offX + super.width(mx, my, partialTick), offY + super.height(mx, my, partialTick),
             (mx >= 0 && mx <= super.width(mx, my, partialTick) && my >= 0 && my <= super.height(mx, my, partialTick)) ? COLOR_BACKGROUND_HIGHLIGHTED : COLOR_BACKGROUND);
-        attachedScreen.fontRenderer.render(t, tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, ": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, this.tag.getValue().size(), attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
-        attachedScreen.fontRenderer.render(t, " entries", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(this.tag.getValue().size(), attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(" entries", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
 
         if (expanded) {
             int y = offY + super.height(mx, my, partialTick) + COMPONENT_PADDING;
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/DoubleArrayTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/DoubleArrayTagComponent.java
index 591c9a606..7f63dbc4e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/DoubleArrayTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/DoubleArrayTagComponent.java
@@ -2,7 +2,7 @@ package net.minecraft.client.gui.nbteditor.components;
 
 import com.mojang.nbt.tags.DoubleArrayTag;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.DyeColor;
@@ -21,13 +21,13 @@ public class DoubleArrayTagComponent extends ArrayTagComponent<double[]> {
     }
 
     @Override
-    public void render(@NotNull Tessellator t, int offX, int offY, int mx, int my, float partialTick) {
+    public void render(@NotNull TessellatorGeneral t, int offX, int offY, int mx, int my, float partialTick) {
         super.render(t, offX, offY, mx, my, partialTick);
         drawRect(offX + 12 + COMPONENT_PADDING, offY, offX + width(mx, my, partialTick), offY + height(mx, my, partialTick), isHovered(mx, my, partialTick) ? COLOR_BACKGROUND_HIGHLIGHTED : COLOR_BACKGROUND);
-        attachedScreen.fontRenderer.render(t, tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, ": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, this.tag.getValue().length, attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
-        attachedScreen.fontRenderer.render(t, " doubles", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(this.tag.getValue().length, attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(" doubles", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ListTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ListTagComponent.java
index fb4b281ca..8b291f73e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ListTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ListTagComponent.java
@@ -3,7 +3,7 @@ package net.minecraft.client.gui.nbteditor.components;
 import com.mojang.nbt.tags.ListTag;
 import com.mojang.nbt.tags.Tag;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.DyeColor;
@@ -32,14 +32,14 @@ public class ListTagComponent extends AbstractTagComponent<List<Tag<?>>>{
     }
 
     @Override
-    public void render(@NotNull Tessellator t, int offX, int offY, int mx, int my, float partialTick) {
+    public void render(@NotNull TessellatorGeneral t, int offX, int offY, int mx, int my, float partialTick) {
         super.render(t, offX, offY, mx, my, partialTick);
         drawRect(offX + 12 + COMPONENT_PADDING, offY, offX + super.width(mx, my, partialTick), offY + super.height(mx, my, partialTick),
             (mx >= 0 && mx <= super.width(mx, my, partialTick) && my >= 0 && my <= super.height(mx, my, partialTick)) ? COLOR_BACKGROUND_HIGHLIGHTED : COLOR_BACKGROUND);
-        attachedScreen.fontRenderer.render(t, tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, ": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, this.tag.getValue().size(), attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
-        attachedScreen.fontRenderer.render(t, " entries", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(this.tag.getValue().size(), attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(" entries", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
 
         if (expanded) {
             int y = offY + super.height(mx, my, partialTick) + COMPONENT_PADDING;
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/LongArrayTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/LongArrayTagComponent.java
index 12e9bbe14..1b341aa35 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/LongArrayTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/LongArrayTagComponent.java
@@ -2,7 +2,7 @@ package net.minecraft.client.gui.nbteditor.components;
 
 import com.mojang.nbt.tags.LongArrayTag;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.DyeColor;
@@ -21,13 +21,13 @@ public class LongArrayTagComponent extends ArrayTagComponent<long[]> {
     }
 
     @Override
-    public void render(@NotNull Tessellator t, int offX, int offY, int mx, int my, float partialTick) {
+    public void render(@NotNull TessellatorGeneral t, int offX, int offY, int mx, int my, float partialTick) {
         super.render(t, offX, offY, mx, my, partialTick);
         drawRect(offX + 12 + COMPONENT_PADDING, offY, offX + width(mx, my, partialTick), offY + height(mx, my, partialTick), isHovered(mx, my, partialTick) ? COLOR_BACKGROUND_HIGHLIGHTED : COLOR_BACKGROUND);
-        attachedScreen.fontRenderer.render(t, tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, ": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, this.tag.getValue().length, attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
-        attachedScreen.fontRenderer.render(t, " longs", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(this.tag.getValue().length, attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(" longs", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ShortArrayTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ShortArrayTagComponent.java
index 3e71cb7e3..0e31032a3 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ShortArrayTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ShortArrayTagComponent.java
@@ -2,7 +2,7 @@ package net.minecraft.client.gui.nbteditor.components;
 
 import com.mojang.nbt.tags.ShortArrayTag;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.DyeColor;
@@ -21,13 +21,13 @@ public class ShortArrayTagComponent extends ArrayTagComponent<short[]> {
     }
 
     @Override
-    public void render(@NotNull Tessellator t, int offX, int offY, int mx, int my, float partialTick) {
+    public void render(@NotNull TessellatorGeneral t, int offX, int offY, int mx, int my, float partialTick) {
         super.render(t, offX, offY, mx, my, partialTick);
         drawRect(offX + 12 + COMPONENT_PADDING, offY, offX + width(mx, my, partialTick), offY + height(mx, my, partialTick), isHovered(mx, my, partialTick) ? COLOR_BACKGROUND_HIGHLIGHTED : COLOR_BACKGROUND);
-        attachedScreen.fontRenderer.render(t, tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, ": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, this.tag.getValue().length, attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
-        attachedScreen.fontRenderer.render(t, " shorts", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(this.tag.getValue().length, attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
+        attachedScreen.fontRenderer.render(" shorts", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).call();
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ValueTagComponent.java b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ValueTagComponent.java
index 27bcc7032..8ba6c53ae 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ValueTagComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/nbteditor/components/ValueTagComponent.java
@@ -4,7 +4,7 @@ import com.mojang.logging.LogUtils;
 import com.mojang.nbt.tags.Tag;
 import net.minecraft.client.gui.Screen;
 import net.minecraft.client.gui.popup.PopupBuilder;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.util.helper.DyeColor;
 import org.jetbrains.annotations.NotNull;
 import org.slf4j.Logger;
@@ -16,12 +16,12 @@ public abstract class ValueTagComponent<T> extends AbstractTagComponent<T>{
     }
 
     @Override
-    public void render(@NotNull Tessellator t, int offX, int offY, int mx, int my, float partialTick) {
+    public void render(@NotNull TessellatorGeneral t, int offX, int offY, int mx, int my, float partialTick) {
         super.render(t, offX, offY, mx, my, partialTick);
         drawRect(offX + 12 + COMPONENT_PADDING, offY, offX + width(mx, my, partialTick), offY + height(mx, my, partialTick), isHovered(mx, my, partialTick) ? COLOR_BACKGROUND_HIGHLIGHTED : COLOR_BACKGROUND);
-        attachedScreen.fontRenderer.render(t, tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, ": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
-        attachedScreen.fontRenderer.render(t, tag.getValue().toString(), attachedScreen.fontRenderer.getLastEndingX(), offY + 2).call();
+        attachedScreen.fontRenderer.render(tag.getTagName(), offX + 12 + COMPONENT_PADDING + TEXT_PADDING, offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(": ", attachedScreen.fontRenderer.getLastEndingX(), offY + TEXT_PADDING).setColor(DyeColor.YELLOW.color).call();
+        attachedScreen.fontRenderer.render(tag.getValue().toString(), attachedScreen.fontRenderer.getLastEndingX(), offY + 2).call();
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/ScreenOptions.java b/game/client/src/main/java/net/minecraft/client/gui/options/ScreenOptions.java
index 6f64a7b56..33b7a21cd 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/ScreenOptions.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/ScreenOptions.java
@@ -13,20 +13,20 @@ import net.minecraft.client.gui.options.data.OptionsPageRegistry;
 import net.minecraft.client.input.controller.ControllerInput;
 import net.minecraft.client.option.KeyBinding;
 import net.minecraft.client.render.Scissor;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.sound.SoundCategory;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
-
-import static org.lwjgl.opengl.GL11.*;
 
 public class ScreenOptions
-    extends Screen
-{
+    extends Screen {
     private static final int TOP_SPACING = 24;
     private static final int BUTTON_SPACING = 4;
     private static final int SEPARATOR_WIDTH = 8;
@@ -40,7 +40,7 @@ public class ScreenOptions
 
     private float optionsScrollAmount = 0.0f;
     private float pagesListScrollAmount = 0.0f;
-    private int top, bottom, optionsScrollRegionHeight, pagesListScrollRegionHeight, pageWidth, pagesListWidth;
+    public int top, bottom, optionsScrollRegionHeight, pagesListScrollRegionHeight, pageWidth, pagesListWidth;
 
     private Float oldOptionsScrollAmount;
     private Float oldPagesListScrollAmount;
@@ -50,39 +50,36 @@ public class ScreenOptions
     private int clickedComponentY;
     private ItemElement renderItem = null;
 
-    private boolean doOptionsScroll = true;
-    private boolean doPagesListScroll = true;
+    private final boolean doOptionsScroll = true;
+    private final boolean doPagesListScroll = true;
 
     private @Nullable TooltipElement tooltip = null;
 
-    public ScreenOptions(Screen parent)
-    {
+    public ScreenOptions(Screen parent) {
         this(parent, OptionsPages.GENERAL);
     }
 
-    public ScreenOptions(Screen parent, OptionsPage selectedPage)
-    {
+    public ScreenOptions(Screen parent, OptionsPage selectedPage) {
         super(parent);
         this.selectedPage = selectedPage;
         queueReload = false;
     }
 
     @Override
-    public void init()
-    {
+    public void init() {
         super.init();
 
-        buttons.add(new ButtonElement(0, width / 2 - 100, height - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.options.button.done")));
+        this.buttons.add(new ButtonElement(0, this.width / 2 - 100, this.height - (BUTTON_SPACING + 20), 200, 20, I18n.getInstance().translateKey("gui.options.button.done")));
 
-        top = TOP_SPACING;
-        bottom = height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
+        this.top = TOP_SPACING;
+        this.bottom = this.height - (BUTTON_SPACING + 20 + BUTTON_SPACING);
 
-        optionsScrollRegionHeight = bottom - top;
-        pagesListScrollRegionHeight = bottom - top;
+        this.optionsScrollRegionHeight = this.bottom - this.top;
+        this.pagesListScrollRegionHeight = this.bottom - this.top;
 
-        this.renderItem = new ItemElement(mc);
+        this.renderItem = new ItemElement(this.mc);
 
-        this.selectedPage.initComponents(mc);
+        this.selectedPage.initComponents(this.mc);
 
         this.tooltip = new TooltipElement(this.mc);
     }
@@ -102,47 +99,43 @@ public class ScreenOptions
             return;
         }
 
-        if (eventKey == Keyboard.KEY_ESCAPE)
-        {
-            mc.texturePackList.refreshIfReady(); // Sets the texturepacks on menu close
+        if (eventKey == Keyboard.KEY_ESCAPE) {
+            this.mc.texturePackList.refreshIfReady(); // Sets the texturepacks on menu close
             reloadIfReady();
-            mc.displayScreen(getParentScreen());
-        }
-        else
-        {
-            for (OptionsComponent component : selectedPage.getComponents())
-            {
+            this.mc.displayScreen(getParentScreen());
+        } else {
+            for (OptionsComponent component : this.selectedPage.getComponents()) {
                 component.onKeyPress(eventKey, eventCharacter);
             }
         }
     }
 
-    private void drawPageItems(int x, int y, int width, int mouseX, int mouseY)
-    {
+    private void drawPageItems(int x, int y, int width, int mouseX, int mouseY) {
         int y2 = y;
-        for (OptionsComponent component : selectedPage.getComponents())
-        {
-            component.render(x, y2, width, mouseX - x, mouseY - y2);
+        for (OptionsComponent component : this.selectedPage.getComponents()) {
+            if (y2 + component.getHeight() >= this.top && y2 <= this.bottom) {
+                component.render(this, x, y2, width, mouseX - x, mouseY - y2);
+            }
             y2 += component.getHeight();
         }
     }
 
     private void drawPagesListItems(int x, int y, int width, int mouseX, int mouseY) {
         int y2 = y;
-        for(OptionsPage page : OptionsPageRegistry.getInstance().getPages()) {
+        for (OptionsPage page : OptionsPageRegistry.getInstance().getPages()) {
             if (!page.isVisible(this.mc)) {
                 continue;
             }
 
             String translated = I18n.getInstance().translateKey(page.getTranslationKey());
             int textColor = 0xFF7F7F7F;
-            if (page == selectedPage) {
+            if (page == this.selectedPage) {
                 textColor = 0xFFFFFFFF;
             }
             if (mouseX >= x && mouseX < x + width && mouseY >= y2 && mouseY < y2 + PAGE_BUTTON_HEIGHT) {
                 textColor = 0xFFFFFFA0;
             }
-            renderItem.render(page.getIcon(), x, y2 + (PAGE_BUTTON_HEIGHT / 2) - 9);
+            this.renderItem.render(page.getIcon(), x, y2 + (PAGE_BUTTON_HEIGHT / 2) - 9);
             drawStringShadow(this.fontRenderer, translated, x + 19, y2 + (PAGE_BUTTON_HEIGHT / 2) - 4, textColor);
             y2 += PAGE_BUTTON_HEIGHT;
         }
@@ -150,8 +143,7 @@ public class ScreenOptions
 
     @Override
     public void tick() {
-        for (OptionsComponent component : selectedPage.getComponents())
-        {
+        for (OptionsComponent component : this.selectedPage.getComponents()) {
             component.tick();
         }
     }
@@ -160,56 +152,57 @@ public class ScreenOptions
     protected void buttonClicked(@NotNull ButtonElement button) {
         super.buttonClicked(button);
 
-        if (button.id == 0)
-        {
-            mc.displayScreen(getParentScreen());
-            mc.texturePackList.refreshIfReady(); // Sets the texturepacks on menu close
+        if (button.id == 0) {
+            this.mc.displayScreen(getParentScreen());
+            this.mc.texturePackList.refreshIfReady(); // Sets the texturepacks on menu close
             reloadIfReady();
         }
     }
 
     @Override
     public void removed() {
-        for (OptionsComponent component : selectedPage.getComponents()) {
+        for (OptionsComponent component : this.selectedPage.getComponents()) {
             component.onClose();
         }
         super.removed();
-        mc.gameSettings.saveOptions();
-        mc.texturePackList.refreshIfReady();
+        this.mc.gameSettings.saveOptions();
+        this.mc.texturePackList.refreshIfReady();
         reloadIfReady();
     }
 
     private void scrollOptions(float amount) {
-        if(amount == 0.0f) return;
+        if (amount == 0.0f) return;
 
-        optionsScrollAmount += amount;
+        this.optionsScrollAmount += amount;
         onScrollOptions();
     }
 
     private void onScrollOptions() {
         int totalPageHeight = getTotalPageHeight();
-        if (optionsScrollAmount < 0 || optionsScrollRegionHeight > totalPageHeight) optionsScrollAmount = 0;
-        else if (optionsScrollAmount > totalPageHeight - optionsScrollRegionHeight) optionsScrollAmount = totalPageHeight - optionsScrollRegionHeight;
+        if (this.optionsScrollAmount < 0 || this.optionsScrollRegionHeight > totalPageHeight)
+            this.optionsScrollAmount = 0;
+        else if (this.optionsScrollAmount > totalPageHeight - this.optionsScrollRegionHeight)
+            this.optionsScrollAmount = totalPageHeight - this.optionsScrollRegionHeight;
     }
 
     private void scrollPagesList(float amount) {
-        if(amount == 0.0f) return;
+        if (amount == 0.0f) return;
 
-        pagesListScrollAmount += amount;
+        this.pagesListScrollAmount += amount;
         onScrollPagesList();
     }
 
     private void onScrollPagesList() {
         int totalPagesListHeight = getTotalPagesListHeight();
-        if (pagesListScrollAmount < 0 || pagesListScrollRegionHeight > totalPagesListHeight) pagesListScrollAmount = 0;
-        else if (pagesListScrollAmount > totalPagesListHeight - pagesListScrollRegionHeight) pagesListScrollAmount = totalPagesListHeight - pagesListScrollRegionHeight;
+        if (this.pagesListScrollAmount < 0 || this.pagesListScrollRegionHeight > totalPagesListHeight)
+            this.pagesListScrollAmount = 0;
+        else if (this.pagesListScrollAmount > totalPagesListHeight - this.pagesListScrollRegionHeight)
+            this.pagesListScrollAmount = totalPagesListHeight - this.pagesListScrollRegionHeight;
     }
 
-    private int getTotalPageHeight()
-    {
+    private int getTotalPageHeight() {
         int totalPageHeight = 0;
-        for (OptionsComponent component : selectedPage.getComponents())
-        {
+        for (OptionsComponent component : this.selectedPage.getComponents()) {
             totalPageHeight += component.getHeight();
         }
         return totalPageHeight;
@@ -217,7 +210,7 @@ public class ScreenOptions
 
     private int getTotalPagesListHeight() {
         int acc = 0;
-        for(OptionsPage page : OptionsPageRegistry.getInstance().getPages()) {
+        for (OptionsPage page : OptionsPageRegistry.getInstance().getPages()) {
             if (!page.isVisible(this.mc)) {
                 continue;
             }
@@ -228,19 +221,18 @@ public class ScreenOptions
     }
 
     @Override
-    public void render(int mx, int my, float renderPartialTicks)
-    {
+    public void render(int mx, int my, float renderPartialTicks) {
         if (pickingKeyBinding != null && pickingKeyBindingComponent != null) {
             mx = -1;
             my = -1;
-        } else if (doOptionsScroll && mx > pagesListWidth + SEPARATOR_WIDTH + PADDING && mx < width) {
+        } else if (this.doOptionsScroll && mx > this.pagesListWidth + SEPARATOR_WIDTH + PADDING && mx < this.width) {
             if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL)) {
                 scrollOptions(Mouse.getDWheel() / -0.01f);
             } else {
                 scrollOptions(Mouse.getDWheel() / -0.05f);
             }
             onScrollOptions();
-        } else if (doPagesListScroll && mx >= 0 && mx <= pagesListWidth) {
+        } else if (this.doPagesListScroll && mx >= 0 && mx <= this.pagesListWidth) {
             if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL)) {
                 scrollPagesList(Mouse.getDWheel() / -0.01f);
             } else {
@@ -249,86 +241,86 @@ public class ScreenOptions
             onScrollPagesList();
         }
 
-        if (pickingKeyBinding == null && pickingKeyBindingComponent == null && mc.controllerInput != null) {
-            final int xc = (int) mc.controllerInput.cursorX;
-            if (doOptionsScroll && xc > pagesListWidth + SEPARATOR_WIDTH + PADDING && xc < width) {
-                scrollOptions(mc.controllerInput.joyRight.getY() / 0.2f);
+        if (pickingKeyBinding == null && pickingKeyBindingComponent == null && this.mc.controllerInput != null) {
+            final int xc = (int) this.mc.controllerInput.cursorX;
+            if (this.doOptionsScroll && xc > this.pagesListWidth + SEPARATOR_WIDTH + PADDING && xc < this.width) {
+                scrollOptions(this.mc.controllerInput.joyRight.getY() / 0.2f);
                 onScrollOptions();
-            } else if (doPagesListScroll && xc >= 0 && xc <= pagesListWidth) {
-                scrollPagesList(mc.controllerInput.joyRight.getY() / 0.2f);
+            } else if (this.doPagesListScroll && xc >= 0 && xc <= this.pagesListWidth) {
+                scrollPagesList(this.mc.controllerInput.joyRight.getY() / 0.2f);
                 onScrollPagesList();
             }
         }
 
-        pagesListWidth = (int)(width * 0.25f);
-        pageWidth = width - (pagesListWidth + SEPARATOR_WIDTH + (PADDING * 2));
+        this.pagesListWidth = (int) (this.width * 0.25f);
+        this.pageWidth = this.width - (this.pagesListWidth + SEPARATOR_WIDTH + (PADDING * 2));
         I18n i18n = I18n.getInstance();
 
         renderBackground();
-        overlayBackground(0, width, 0, top);
-        overlayBackground(0, width, bottom, height);
+        overlayBackground(0, this.width, 0, this.top);
+        overlayBackground(0, this.width, this.bottom, this.height);
 
-        Scissor.enable(0, top, width, bottom - top);
-        if (my >= top && my <= bottom) {
-            drawPageItems(pagesListWidth + SEPARATOR_WIDTH + PADDING, top - (int) optionsScrollAmount, pageWidth - 8, mx, my);
+        Scissor.enable(0, this.top, this.width, this.bottom - this.top);
+        if (my >= this.top && my <= this.bottom) {
+            drawPageItems(this.pagesListWidth + SEPARATOR_WIDTH + PADDING, this.top - (int) this.optionsScrollAmount, this.pageWidth - 8, mx, my);
         } else {
-            drawPageItems(pagesListWidth + SEPARATOR_WIDTH + PADDING, top - (int) optionsScrollAmount, pageWidth - 8, -1, -1);
+            drawPageItems(this.pagesListWidth + SEPARATOR_WIDTH + PADDING, this.top - (int) this.optionsScrollAmount, this.pageWidth - 8, -1, -1);
         }
         Scissor.disable();
 
-        Scissor.enable(0, top, pagesListWidth, bottom - top);
+        Scissor.enable(0, this.top, this.pagesListWidth, this.bottom - this.top);
         int pagesListHeight = getTotalPagesListHeight();
-        int pagesListY = top - (int) pagesListScrollAmount;
-        if (pagesListHeight < bottom - top) {
-            pagesListY = top + (bottom - top - pagesListHeight) / 2;
+        int pagesListY = this.top - (int) this.pagesListScrollAmount;
+        if (pagesListHeight < this.bottom - this.top) {
+            pagesListY = this.top + (this.bottom - this.top - pagesListHeight) / 2;
         }
-        if (my >= top && my <= bottom) {
-            drawPagesListItems(PADDING - 4, pagesListY, pagesListWidth - PADDING, mx, my);
+        if (my >= this.top && my <= this.bottom) {
+            drawPagesListItems(PADDING - 4, pagesListY, this.pagesListWidth - PADDING, mx, my);
         } else {
-            drawPagesListItems(PADDING - 4, pagesListY, pagesListWidth - PADDING, -1, -1);
+            drawPagesListItems(PADDING - 4, pagesListY, this.pagesListWidth - PADDING, -1, -1);
         }
         Scissor.disable();
 
         // Draw shadows
-        if (mc.currentWorld == null)
-        {
-            Tessellator tessellator = Tessellator.instance;
-            GL11.glDisable(GL_DEPTH_TEST);
-            int shadowSize = 4;
-            GL11.glEnable(GL_BLEND);
-            GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-            GL11.glDisable(GL_ALPHA_TEST);
-            GL11.glShadeModel(GL_SMOOTH);
-            GL11.glDisable(GL_TEXTURE_2D);
+        if (this.mc.currentWorld == null) {
 
+            int shadowSize = 4;
+//            GL11.glDisable(GL_ALPHA_TEST);
+//            GL11.glShadeModel(GL_SMOOTH);
+
+            GLRenderer.pushFrame();
+            GLRenderer.setShader(Shaders.COLOR);
+            GLRenderer.enableState(State.DEPTH_TEST);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
             tessellator.startDrawingQuads();
-            tessellator.setColorRGBA_I(0, 0);
-            tessellator.addVertexWithUV(0, top + shadowSize, 0.0D, 0.0D, 1.0D);
-            tessellator.addVertexWithUV(width, top + shadowSize, 0.0D, 1.0D, 1.0D);
-            tessellator.setColorRGBA_I(0, 255);
-            tessellator.addVertexWithUV(width, top, 0.0D, 1.0D, 0.0D);
-            tessellator.addVertexWithUV(0, top, 0.0D, 0.0D, 0.0D);
+            tessellator.setColor2i(0, 0);
+            tessellator.addVertexWithUV(0, this.top + shadowSize, 0.0D, 0.0D, 1.0D);
+            tessellator.addVertexWithUV(this.width, this.top + shadowSize, 0.0D, 1.0D, 1.0D);
+            tessellator.setColor2i(0, 255);
+            tessellator.addVertexWithUV(this.width, this.top, 0.0D, 1.0D, 0.0D);
+            tessellator.addVertexWithUV(0, this.top, 0.0D, 0.0D, 0.0D);
             tessellator.draw();
 
             tessellator.startDrawingQuads();
-            tessellator.setColorRGBA_I(0, 255);
-            tessellator.addVertexWithUV(0, bottom, 0.0D, 0.0D, 1.0D);
-            tessellator.addVertexWithUV(width, bottom, 0.0D, 1.0D, 1.0D);
-            tessellator.setColorRGBA_I(0, 0);
-            tessellator.addVertexWithUV(width, bottom - shadowSize, 0.0D, 1.0D, 0.0D);
-            tessellator.addVertexWithUV(0, bottom - shadowSize, 0.0D, 0.0D, 0.0D);
+            tessellator.setColor2i(0, 255);
+            tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0.0D, 1.0D);
+            tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, 1.0D, 1.0D);
+            tessellator.setColor2i(0, 0);
+            tessellator.addVertexWithUV(this.width, this.bottom - shadowSize, 0.0D, 1.0D, 0.0D);
+            tessellator.addVertexWithUV(0, this.bottom - shadowSize, 0.0D, 0.0D, 0.0D);
             tessellator.draw();
 
-            GL11.glEnable(GL_TEXTURE_2D);
-            GL11.glShadeModel(GL_FLAT);
-            GL11.glEnable(GL_ALPHA_TEST);
-            GL11.glDisable(GL_BLEND);
+            GLRenderer.popFrame();
+//            GL11.glShadeModel(GL_FLAT);
+//            GL11.glEnable(GL_ALPHA_TEST);
         }
 
-        overlayBackground(pagesListWidth, pagesListWidth + SEPARATOR_WIDTH, top, bottom);
+        overlayBackground(this.pagesListWidth, this.pagesListWidth + SEPARATOR_WIDTH, this.top, this.bottom);
 
         String titleLanguageKey = "gui.options.title";
-        drawStringCenteredShadow(fontRenderer, i18n.translateKey(titleLanguageKey), width / 2, 5, 0xffffff);
+        drawStringCenteredShadow(this.fontRenderer, i18n.translateKey(titleLanguageKey), this.width / 2, 5, 0xffffff);
 
         drawOptionsScrollBar(mx, my);
         drawPagesListScrollBar(mx, my);
@@ -337,7 +329,7 @@ public class ScreenOptions
 
         if (this.tooltip != null) {
             @Nullable String tooltipTranslationKey = null;
-            for (OptionsComponent component : selectedPage.getComponents()) {
+            for (OptionsComponent component : this.selectedPage.getComponents()) {
                 @Nullable String componentTooltip = component.getTooltipTranslationKey();
                 if (componentTooltip != null) {
                     tooltipTranslationKey = componentTooltip;
@@ -351,104 +343,99 @@ public class ScreenOptions
         }
 
         if (pickingKeyBinding != null && pickingKeyBindingComponent != null) {
-            drawRect(0, 0, width, height, 0xA0000000);
-            drawStringCenteredNoShadow(fontRenderer, i18n.translateKeyAndFormat("gui.options.label.picking_keybinding", i18n.translateKey(pickingKeyBinding.getId())), width / 2, height / 2 - 4, 0xffffff);
+            drawRect(0, 0, this.width, this.height, 0xA0000000);
+            drawStringCenteredNoShadow(this.fontRenderer, i18n.translateKeyAndFormat("gui.options.label.picking_keybinding", i18n.translateKey(pickingKeyBinding.getId())), this.width / 2, this.height / 2 - 4, 0xffffff);
         }
     }
 
     protected void drawOptionsScrollBar(int mouseX, int mouseY) {
         float totalPageHeight = getTotalPageHeight();
-        float scrollBarHeightPercent = optionsScrollRegionHeight / totalPageHeight;
+        float scrollBarHeightPercent = this.optionsScrollRegionHeight / totalPageHeight;
 
-        if(scrollBarHeightPercent > 1.0f) return;
+        if (scrollBarHeightPercent > 1.0f) return;
 
-        glDisable(GL_TEXTURE_2D);
+        int scrollBarX = this.width - 6;
 
-        int scrollBarX = width - 6;
-
-        int scrollBarHeightPx = (int) (scrollBarHeightPercent * optionsScrollRegionHeight);
-        if(scrollBarHeightPx < 32) {
+        int scrollBarHeightPx = (int) (scrollBarHeightPercent * this.optionsScrollRegionHeight);
+        if (scrollBarHeightPx < 32) {
             scrollBarHeightPx = 32;
         }
 
-        float scrollPercent = optionsScrollAmount / (totalPageHeight - optionsScrollRegionHeight);
-
-        int scrollBarY = (int) (top + (optionsScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
+        float scrollPercent = this.optionsScrollAmount / (totalPageHeight - this.optionsScrollRegionHeight);
 
-        Tessellator t = Tessellator.instance;
+        int scrollBarY = (int) (this.top + (this.optionsScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
 
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        TessellatorGeneral t = GLRenderer.getTessellator();
         t.startDrawingQuads();
-        t.setColorOpaque(0, 0, 0);
-        t.drawRectangle(scrollBarX, top, 6, optionsScrollRegionHeight);
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColorOpaque3i(0, 0, 0);
+        t.drawRectangle(scrollBarX, this.top, 6, this.optionsScrollRegionHeight);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(scrollBarX, scrollBarY, 6, scrollBarHeightPx);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(scrollBarX + 1, scrollBarY, 5, scrollBarHeightPx - 1);
         t.draw();
+        GLRenderer.popFrame();
 
-        glEnable(GL_TEXTURE_2D);
-
-        if(clickX != null && clickY != null) {
-            if(clickX >= scrollBarX && clickY >= top && clickX <= scrollBarX + 6 && clickY < bottom) {
-                if(oldOptionsScrollAmount == null) {
-                    oldOptionsScrollAmount = optionsScrollAmount;
+        if (this.clickX != null && this.clickY != null) {
+            if (this.clickX >= scrollBarX && this.clickY >= this.top && this.clickX <= scrollBarX + 6 && this.clickY < this.bottom) {
+                if (this.oldOptionsScrollAmount == null) {
+                    this.oldOptionsScrollAmount = this.optionsScrollAmount;
                 }
-                optionsScrollAmount = oldOptionsScrollAmount + (clickY - mouseY) * (1.0f / scrollBarHeightPercent) * -1.0f;
+                this.optionsScrollAmount = this.oldOptionsScrollAmount + (this.clickY - mouseY) * (1.0f / scrollBarHeightPercent) * -1.0f;
                 onScrollOptions();
             }
-        }else {
-            oldOptionsScrollAmount = null;
+        } else {
+            this.oldOptionsScrollAmount = null;
         }
     }
 
     protected void drawPagesListScrollBar(int mouseX, int mouseY) {
         float totalPagesListHeight = getTotalPagesListHeight();
-        float scrollBarHeightPercent = pagesListScrollRegionHeight / totalPagesListHeight;
+        float scrollBarHeightPercent = this.pagesListScrollRegionHeight / totalPagesListHeight;
 
-        if(scrollBarHeightPercent > 1.0f) return;
+        if (scrollBarHeightPercent > 1.0f) return;
 
-        glDisable(GL_TEXTURE_2D);
+        int scrollBarX = this.pagesListWidth - 6;
 
-        int scrollBarX = pagesListWidth - 6;
-
-        int scrollBarHeightPx = (int) (scrollBarHeightPercent * pagesListScrollRegionHeight);
-        if(scrollBarHeightPx < 32) {
+        int scrollBarHeightPx = (int) (scrollBarHeightPercent * this.pagesListScrollRegionHeight);
+        if (scrollBarHeightPx < 32) {
             scrollBarHeightPx = 32;
         }
 
-        float scrollPercent = pagesListScrollAmount / (totalPagesListHeight - pagesListScrollRegionHeight);
-
-        int scrollBarY = (int) (top + (pagesListScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
+        float scrollPercent = this.pagesListScrollAmount / (totalPagesListHeight - this.pagesListScrollRegionHeight);
 
-        Tessellator t = Tessellator.instance;
+        int scrollBarY = (int) (this.top + (this.pagesListScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
 
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        TessellatorGeneral t = GLRenderer.getTessellator();
         t.startDrawingQuads();
-        t.setColorOpaque(0, 0, 0);
-        t.drawRectangle(scrollBarX, top, 6, pagesListScrollRegionHeight);
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColorOpaque3i(0, 0, 0);
+        t.drawRectangle(scrollBarX, this.top, 6, this.pagesListScrollRegionHeight);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(scrollBarX, scrollBarY, 6, scrollBarHeightPx);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(scrollBarX + 1, scrollBarY, 5, scrollBarHeightPx - 1);
         t.draw();
+        GLRenderer.popFrame();
 
-        glEnable(GL_TEXTURE_2D);
-
-        if(clickX != null && clickY != null) {
-            if(clickX >= scrollBarX && clickY >= top && clickX <= scrollBarX + 6 && clickY < bottom) {
-                if(oldPagesListScrollAmount == null) {
-                    oldPagesListScrollAmount = pagesListScrollAmount;
+        if (this.clickX != null && this.clickY != null) {
+            if (this.clickX >= scrollBarX && this.clickY >= this.top && this.clickX <= scrollBarX + 6 && this.clickY < this.bottom) {
+                if (this.oldPagesListScrollAmount == null) {
+                    this.oldPagesListScrollAmount = this.pagesListScrollAmount;
                 }
-                pagesListScrollAmount = oldPagesListScrollAmount + (clickY - mouseY) * (1.0f / scrollBarHeightPercent) * -1.0f;
+                this.pagesListScrollAmount = this.oldPagesListScrollAmount + (this.clickY - mouseY) * (1.0f / scrollBarHeightPercent) * -1.0f;
                 onScrollOptions();
             }
-        }else {
-            oldPagesListScrollAmount = null;
+        } else {
+            this.oldPagesListScrollAmount = null;
         }
     }
 
     @Override
-    public void mouseClicked(int mx, int my, int buttonNum)
-    {
+    public void mouseClicked(int mx, int my, int buttonNum) {
         if (pickingKeyBinding != null && pickingKeyBindingComponent != null) {
             pickingKeyBinding.bind(InputDevice.mouse, buttonNum);
             pickingKeyBindingComponent.update();
@@ -459,40 +446,39 @@ public class ScreenOptions
 
         super.mouseClicked(mx, my, buttonNum);
 
-        int left = pagesListWidth + SEPARATOR_WIDTH + PADDING;
+        int left = this.pagesListWidth + SEPARATOR_WIDTH + PADDING;
 
-        if (mx >= pagesListWidth + SEPARATOR_WIDTH && my >= top && my <= bottom) {
-            int componentY = top - (int) optionsScrollAmount;
-            for (OptionsComponent component : selectedPage.getComponents())
-            {
-                if (mx >= left && mx <= left + pageWidth - PADDING && my >= componentY && my <= componentY + component.getHeight()) {
-                    component.onMouseClick(buttonNum, left, componentY, pageWidth - PADDING, mx - left, my - componentY);
-                    clickedComponent = component;
-                    clickedComponentY = componentY;
+        if (mx >= this.pagesListWidth + SEPARATOR_WIDTH && my >= this.top && my <= this.bottom) {
+            int componentY = this.top - (int) this.optionsScrollAmount;
+            for (OptionsComponent component : this.selectedPage.getComponents()) {
+                if (mx >= left && mx <= left + this.pageWidth - PADDING && my >= componentY && my <= componentY + component.getHeight()) {
+                    component.onMouseClick(buttonNum, left, componentY, this.pageWidth - PADDING, mx - left, my - componentY);
+                    this.clickedComponent = component;
+                    this.clickedComponentY = componentY;
                     break;
                 }
                 componentY += component.getHeight();
             }
-        } else if (mx >= 0 && mx <= pagesListWidth && my >= top && my <= bottom) {
+        } else if (mx >= 0 && mx <= this.pagesListWidth && my >= this.top && my <= this.bottom) {
             int pagesListHeight = getTotalPagesListHeight();
-            int pagesListY = top - (int) pagesListScrollAmount;
-            if (pagesListHeight < bottom - top) {
-                pagesListY = top + (bottom - top - pagesListHeight) / 2;
+            int pagesListY = this.top - (int) this.pagesListScrollAmount;
+            if (pagesListHeight < this.bottom - this.top) {
+                pagesListY = this.top + (this.bottom - this.top - pagesListHeight) / 2;
             }
-            for(OptionsPage page : OptionsPageRegistry.getInstance().getPages()) {
+            for (OptionsPage page : OptionsPageRegistry.getInstance().getPages()) {
                 if (!page.isVisible(this.mc)) {
                     continue;
                 }
 
-                if (mx >= 0 && mx <= pagesListWidth && my >= pagesListY && my <= pagesListY + PAGE_BUTTON_HEIGHT) {
-                    for (OptionsComponent component : selectedPage.getComponents()) {
+                if (mx >= 0 && mx <= this.pagesListWidth && my >= pagesListY && my <= pagesListY + PAGE_BUTTON_HEIGHT) {
+                    for (OptionsComponent component : this.selectedPage.getComponents()) {
                         component.onClose();
                     }
-                    optionsScrollAmount = 0;
-                    selectedPage = page;
-                    this.selectedPage.initComponents(mc);
-                    mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
-                    mc.texturePackList.refreshIfReady();
+                    this.optionsScrollAmount = 0;
+                    this.selectedPage = page;
+                    this.selectedPage.initComponents(this.mc);
+                    this.mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
+                    this.mc.texturePackList.refreshIfReady();
                     reloadIfReady();
                     break;
                 }
@@ -500,8 +486,8 @@ public class ScreenOptions
             }
         }
 
-        clickX = mx;
-        clickY = my;
+        this.clickX = mx;
+        this.clickY = my;
     }
 
     @Override
@@ -510,21 +496,21 @@ public class ScreenOptions
 
         super.mouseReleased(mx, my, buttonNum);
 
-        int left = pagesListWidth + SEPARATOR_WIDTH + PADDING;
-        if (my >= top && my <= bottom) {
-            if (clickedComponent != null) {
+        int left = this.pagesListWidth + SEPARATOR_WIDTH + PADDING;
+        if (my >= this.top && my <= this.bottom) {
+            if (this.clickedComponent != null) {
                 if (buttonNum >= 0) {
-                    clickedComponent.onMouseRelease(buttonNum, left, clickedComponentY, pageWidth, mx - left, my - clickedComponentY);
-                    clickedComponent = null;
+                    this.clickedComponent.onMouseRelease(buttonNum, left, this.clickedComponentY, this.pageWidth, mx - left, my - this.clickedComponentY);
+                    this.clickedComponent = null;
                 } else {
-                    clickedComponent.onMouseMove(left, clickedComponentY, pageWidth, mx - left, my - clickedComponentY);
+                    this.clickedComponent.onMouseMove(left, this.clickedComponentY, this.pageWidth, mx - left, my - this.clickedComponentY);
                 }
             }
         }
 
-        if(buttonNum >= 0) {
-            clickX = null;
-            clickY = null;
+        if (buttonNum >= 0) {
+            this.clickX = null;
+            this.clickY = null;
         }
     }
 
@@ -532,48 +518,43 @@ public class ScreenOptions
     public void renderBackground() {
         super.renderBackground();
 
-        if (mc.currentWorld == null)
-        {
-            Tessellator tessellator = Tessellator.instance;
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        if (this.mc.currentWorld == null) {
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+            GLRenderer.setColor4f(1f, 1f, 1f, 1f);
             float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x202020);
+            tessellator.setColorOpaque1i(0x202020);
 
-            tessellator.addVertexWithUV(0, bottom, 0.0D, 0, (float)(bottom + (int) optionsScrollAmount) / scale);
-            tessellator.addVertexWithUV(width, bottom, 0.0D, (float)width / scale, (float)(bottom + (int) optionsScrollAmount) / scale);
-            tessellator.addVertexWithUV(width, top, 0.0D, (float)width / scale, (float)(top + (int) optionsScrollAmount) / scale);
-            tessellator.addVertexWithUV(0, top, 0.0D, 0, (float)(top + (int) optionsScrollAmount) / scale);
+            tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0, (float) (this.bottom + (int) this.optionsScrollAmount) / scale);
+            tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, (float) this.width / scale, (float) (this.bottom + (int) this.optionsScrollAmount) / scale);
+            tessellator.addVertexWithUV(this.width, this.top, 0.0D, (float) this.width / scale, (float) (this.top + (int) this.optionsScrollAmount) / scale);
+            tessellator.addVertexWithUV(0, this.top, 0.0D, 0, (float) (this.top + (int) this.optionsScrollAmount) / scale);
 
-            tessellator.addVertexWithUV(0, bottom, 0.0D, 0, (float)(bottom + (int) pagesListScrollAmount) / scale);
-            tessellator.addVertexWithUV(pagesListWidth, bottom, 0.0D, (float) pagesListWidth / scale, (float)(bottom + (int) pagesListScrollAmount) / scale);
-            tessellator.addVertexWithUV(pagesListWidth, top, 0.0D, (float) pagesListWidth / scale, (float)(top + (int) pagesListScrollAmount) / scale);
-            tessellator.addVertexWithUV(0, top, 0.0D, 0, (float)(top + (int) pagesListScrollAmount) / scale);
+            tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0, (float) (this.bottom + (int) this.pagesListScrollAmount) / scale);
+            tessellator.addVertexWithUV(this.pagesListWidth, this.bottom, 0.0D, (float) this.pagesListWidth / scale, (float) (this.bottom + (int) this.pagesListScrollAmount) / scale);
+            tessellator.addVertexWithUV(this.pagesListWidth, this.top, 0.0D, (float) this.pagesListWidth / scale, (float) (this.top + (int) this.pagesListScrollAmount) / scale);
+            tessellator.addVertexWithUV(0, this.top, 0.0D, 0, (float) (this.top + (int) this.pagesListScrollAmount) / scale);
 
             tessellator.draw();
-        }
-        else
-        {
-            drawRect(0, 0, width, top, 0x5F000000);
-            drawRect(0, bottom, width, height, 0x5F000000);
-            drawRect(pagesListWidth, top, pagesListWidth + SEPARATOR_WIDTH, bottom, 0x5F000000);
+        } else {
+            drawRect(0, 0, this.width, this.top, 0x5F000000);
+            drawRect(0, this.bottom, this.width, this.height, 0x5F000000);
+            drawRect(this.pagesListWidth, this.top, this.pagesListWidth + SEPARATOR_WIDTH, this.bottom, 0x5F000000);
         }
     }
 
-    private void overlayBackground(int minX, int maxX, int minY, int maxY)
-    {
-        if (mc.currentWorld == null)
-        {
-            Tessellator tessellator = Tessellator.instance;
-            mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+    private void overlayBackground(int minX, int maxX, int minY, int maxY) {
+        if (this.mc.currentWorld == null) {
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
+            GLRenderer.setColor4f(1f, 1f, 1f, 1f);
             float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x404040);
+            tessellator.setColorOpaque1i(0x404040);
             tessellator.addVertexWithUV(minX, maxY, 0.0D, (float) minX / scale, (float) maxY / scale);
             tessellator.addVertexWithUV(maxX, maxY, 0.0D, (float) maxX / scale, (float) maxY / scale);
-            tessellator.setColorOpaque_I(0x404040);
+            tessellator.setColorOpaque1i(0x404040);
             tessellator.addVertexWithUV(maxX, minY, 0.0D, (float) maxX / scale, (float) minY / scale);
             tessellator.addVertexWithUV(minX, minY, 0.0D, (float) minX / scale, (float) minY / scale);
             tessellator.draw();
@@ -582,32 +563,32 @@ public class ScreenOptions
 
     @Override
     public void guiSpecificControllerInput(@NotNull ControllerInput controller) {
-        if(controller.buttonStart.pressedThisFrame()) {
-            this.keyPressed((char)0, Keyboard.KEY_ESCAPE, -1, -1);
+        if (controller.buttonStart.pressedThisFrame()) {
+            this.keyPressed((char) 0, Keyboard.KEY_ESCAPE, -1, -1);
         }
-        if(controller.buttonA.pressedThisFrame()) {
-            this.mouseClicked((int)controller.cursorX, (int)controller.cursorY, 0);
+        if (controller.buttonA.pressedThisFrame()) {
+            this.mouseClicked((int) controller.cursorX, (int) controller.cursorY, 0);
         }
-        if(controller.buttonA.releasedThisFrame()) {
-            this.mouseReleased((int)controller.cursorX, (int)controller.cursorY, 0);
+        if (controller.buttonA.releasedThisFrame()) {
+            this.mouseReleased((int) controller.cursorX, (int) controller.cursorY, 0);
         }
-        if(controller.buttonY.pressedThisFrame()) {
-            this.mouseClicked((int)controller.cursorX, (int)controller.cursorY, 1);
+        if (controller.buttonY.pressedThisFrame()) {
+            this.mouseClicked((int) controller.cursorX, (int) controller.cursorY, 1);
         }
-        if(controller.buttonY.releasedThisFrame()) {
-            this.mouseReleased((int)controller.cursorX, (int)controller.cursorY, 1);
+        if (controller.buttonY.releasedThisFrame()) {
+            this.mouseReleased((int) controller.cursorX, (int) controller.cursorY, 1);
         }
-        if(controller.buttonX.pressedThisFrame()) {
-            this.mouseClicked((int)controller.cursorX, (int)controller.cursorY, 10);
+        if (controller.buttonX.pressedThisFrame()) {
+            this.mouseClicked((int) controller.cursorX, (int) controller.cursorY, 10);
         }
         if (controller.buttonB.pressedThisFrame()) {
-            mc.displayScreen(getParentScreen());
+            this.mc.displayScreen(getParentScreen());
         }
     }
 
     private void reloadIfReady() {
         if (queueReload) {
-            mc.renderGlobal.allChanged();
+            this.mc.renderGlobal.allChanged();
             queueReload = false;
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/AvailableTexturePackListComponent.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/AvailableTexturePackListComponent.java
index f76a3193c..9265f6782 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/AvailableTexturePackListComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/AvailableTexturePackListComponent.java
@@ -6,12 +6,15 @@ import java.util.ArrayList;
 import java.util.List;
 
 import net.minecraft.client.gui.ButtonElement;
+import net.minecraft.client.gui.options.ScreenOptions;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
 import net.minecraft.core.sound.SoundCategory;
+import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texturepack.TexturePack;
 import net.minecraft.client.util.helper.Colors;
 import net.minecraft.core.Global;
@@ -43,14 +46,14 @@ public class AvailableTexturePackListComponent
 
     @Override
     public void tick() {
-        if (size != mc.texturePackList.selectedPacks.size()){
-            size = mc.texturePackList.selectedPacks.size();
+        if (this.size != mc.texturePackList.selectedPacks.size()){
+            this.size = mc.texturePackList.selectedPacks.size();
             createTexturePackButtons();
             return;
         }
-    	updateTickCount++;
-    	if(updateTickCount >= 40) {
-    		updateTickCount = 0;
+        this.updateTickCount++;
+    	if(this.updateTickCount >= 40) {
+            this.updateTickCount = 0;
     		if(mc.texturePackList.updateAvailableTexturePacks()) {
     			createTexturePackButtons();
     		}
@@ -58,30 +61,30 @@ public class AvailableTexturePackListComponent
     }
     
     public void createTexturePackButtons() {
-        availablePacks.clear();
+        this.availablePacks.clear();
         
         List<TexturePack> texturePacks = mc.texturePackList.availableTexturePacks();
         for (int i = 0; i < texturePacks.size(); i++) {
             TexturePack texturePack = texturePacks.get(i);
             if (mc.texturePackList.selectedPacks.contains(texturePack)) continue;
             if (texturePack == mc.texturePackList.getDefaultTexturePack()) continue;
-            availablePacks.add(new TexturePackButton(i, texturePack));
+            this.availablePacks.add(new TexturePackButton(i, texturePack));
         }
     }
 
     @Override
     public int getHeight() {
-        if (availablePacks.isEmpty()) return 20;
-        return 3 + availablePacks.size() * (BUTTON_HEIGHT + 3);
+        if (this.availablePacks.isEmpty()) return 20;
+        return 3 + this.availablePacks.size() * (BUTTON_HEIGHT + 3);
     }
 
     @Override
-    public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        if (availablePacks.isEmpty()) {
-            mc.font.renderCentered(Tessellator.instance, I18n.getInstance().translateKey("gui.options.page.asset_packs.label.no_packs"), x + width / 2, y + 4).setShadow().setColor(0x5F7F7F7F).call();
+    public void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+        if (this.availablePacks.isEmpty()) {
+            mc.font.renderCentered(I18n.getInstance().translateKey("gui.options.page.asset_packs.label.no_packs"), x + width / 2, y + 4).setShadow().setColor(0x5F7F7F7F).call();
         }
-        for (int i = 0; i < availablePacks.size(); i++) {
-            TexturePackButton button = availablePacks.get(i);
+        for (int i = 0; i < this.availablePacks.size(); i++) {
+            TexturePackButton button = this.availablePacks.get(i);
             button.render(x, 3 + y + i * (BUTTON_HEIGHT + 3), width, relativeMouseX, relativeMouseY, i,
                     relativeMouseX >= 0 && relativeMouseX <= width && relativeMouseY >= 3 + i * (BUTTON_HEIGHT + 3) && relativeMouseY <= 3 + i * (BUTTON_HEIGHT + 3) + BUTTON_HEIGHT);
         }
@@ -89,8 +92,8 @@ public class AvailableTexturePackListComponent
 
     @Override
     public void onMouseClick(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        for (int i = 0; i < availablePacks.size(); i++) {
-            TexturePackButton button = availablePacks.get(i);
+        for (int i = 0; i < this.availablePacks.size(); i++) {
+            TexturePackButton button = this.availablePacks.get(i);
             if (button.isClickable() && relativeMouseX >= 0 && relativeMouseX <= width && relativeMouseY >= 3 + i * (BUTTON_HEIGHT + 3) && relativeMouseY <= 3 + i * (BUTTON_HEIGHT + 3) + BUTTON_HEIGHT) {
             	mc.texturePackList.setTexturePack(button.texturePack);
                 createTexturePackButtons();
@@ -115,7 +118,7 @@ public class AvailableTexturePackListComponent
     }
 
     private static class TexturePackButton {
-        private ButtonElement button;
+        private final ButtonElement button;
         public final int index;
         public final TexturePack texturePack;
         public final int height = BUTTON_HEIGHT;
@@ -123,7 +126,7 @@ public class AvailableTexturePackListComponent
         public TexturePackButton(int index, TexturePack texturePack) {
             this.index = index;
             this.texturePack = texturePack;
-            button = new ButtonElement(0, 0, 0, 20, 20, "+");
+            this.button = new ButtonElement(0, 0, 0, 20, 20, "+");
         }
 
         public boolean isClickable() {
@@ -131,79 +134,80 @@ public class AvailableTexturePackListComponent
         }
 
         public void render(int x, int y, int width, int mouseX, int mouseY, int index, boolean hovered) {
-            Tessellator tessellator = Tessellator.instance;
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
 
             setupButton(x, y, width, mouseX, mouseY);
 
             if (hovered) {
                 // Draw background
-                GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-                GL11.glDisable(GL11.GL_TEXTURE_2D);
+                GLRenderer.pushFrame();
+                GLRenderer.setShader(Shaders.COLOR);
+                GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
                 tessellator.startDrawingQuads();
 
-                tessellator.setColorOpaque_I(0x7F808080);
-                tessellator.addVertexWithUV(x - 2, y + height + 2, 0, 0, 1);
-                tessellator.addVertexWithUV(x + width + 2, y + height + 2, 0, 1, 1);
+                tessellator.setColorOpaque1i(0x7F808080);
+                tessellator.addVertexWithUV(x - 2, y + this.height + 2, 0, 0, 1);
+                tessellator.addVertexWithUV(x + width + 2, y + this.height + 2, 0, 1, 1);
                 tessellator.addVertexWithUV(x + width + 2, y - 2, 0, 1, 1);
                 tessellator.addVertexWithUV(x - 2, y - 2, 0, 0, 0);
 
-                tessellator.setColorOpaque_I(0);
-                tessellator.addVertexWithUV(x - 1, y + height + 1, 0, 0, 1);
-                tessellator.addVertexWithUV(x + width + 1, y + height + 1, 0, 1, 1);
+                tessellator.setColorOpaque1i(0);
+                tessellator.addVertexWithUV(x - 1, y + this.height + 1, 0, 0, 1);
+                tessellator.addVertexWithUV(x + width + 1, y + this.height + 1, 0, 1, 1);
                 tessellator.addVertexWithUV(x + width + 1, y - 1, 0, 1, 1);
                 tessellator.addVertexWithUV(x - 1, y - 1, 0, 0, 0);
 
                 tessellator.draw();
-                GL11.glEnable(GL11.GL_TEXTURE_2D);
+                GLRenderer.popFrame();
             }
 
             // Draw texture pack info
-            texturePack.bindThumbnailTexture(mc);
-            GL11.glColor4f(1, 1, 1, 1);
+            this.texturePack.bindThumbnailTexture(mc);
+            GLRenderer.setColor4f(1, 1, 1, 1);
 
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0xFFFFFF);
-            tessellator.addVertexWithUV(x, y + height, 0, 0, 1);
-            tessellator.addVertexWithUV(x + height, y + height, 0, 1, 1);
-            tessellator.addVertexWithUV(x + height, y, 0, 1, 0);
+            tessellator.setColorOpaque1i(0xFFFFFF);
+            tessellator.addVertexWithUV(x, y + this.height, 0, 0, 1);
+            tessellator.addVertexWithUV(x + this.height, y + this.height, 0, 1, 1);
+            tessellator.addVertexWithUV(x + this.height, y, 0, 1, 0);
             tessellator.addVertexWithUV(x, y, 0, 0, 0);
             tessellator.draw();
 
             int rgbVersion = 0x808080;
-            int format = texturePack.manifest.getFormat();
+            int format = this.texturePack.manifest.getFormat();
 
 			if(format == Global.ASSET_PACK_FORMAT) {
 				// Correct version
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getName(), x + this.height + 2, y + 1).call();
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getDescriptionLine1(), x + this.height + 2, y + 12).setColor(0x808080).call();
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getDescriptionLine2(), x + this.height + 2, y + 22).setColor(0x808080).call();
+                mc.font.render(this.texturePack.manifest.getName(), x + this.height + 2, y + 1).call();
+                mc.font.render(this.texturePack.manifest.getDescriptionLine1(), x + this.height + 2, y + 12).setColor(0x808080).call();
+                mc.font.render(this.texturePack.manifest.getDescriptionLine2(), x + this.height + 2, y + 22).setColor(0x808080).call();
 			}else if(format == -1) {
 				// Manifest error
-                mc.font.render(Tessellator.instance, TextFormatting.RED + this.texturePack.manifest.getName(), x + this.height + 2, y + 1).call();
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getDescriptionLine1(), x + this.height + 2, y + 12).setColor(0x808080).call();
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getDescriptionLine2(), x + this.height + 2, y + 22).setColor(0x808080).call();
+                mc.font.render(TextFormatting.RED + this.texturePack.manifest.getName(), x + this.height + 2, y + 1).call();
+                mc.font.render(this.texturePack.manifest.getDescriptionLine1(), x + this.height + 2, y + 12).setColor(0x808080).call();
+                mc.font.render(this.texturePack.manifest.getDescriptionLine2(), x + this.height + 2, y + 22).setColor(0x808080).call();
 				rgbVersion = Colors.allChatColors[TextFormatting.RED.id].getARGB();
 			}else {
 				// Wrong texture pack version
 				I18n i18n = I18n.getInstance();
-                mc.font.render(Tessellator.instance, TextFormatting.RED + this.texturePack.manifest.getName(), x + this.height + 2, y + 1).call();
-                mc.font.render(Tessellator.instance, i18n.translateKey("gui.options.page.asset_packs.label.outdated_pack.1"), x + this.height + 2, y + 12).setColor(0x808080).call();
-                mc.font.render(Tessellator.instance, i18n.translateKey("gui.options.page.asset_packs.label.outdated_pack.2"), x + this.height + 2, y + 22).setColor(0x808080).call();
+                mc.font.render(TextFormatting.RED + this.texturePack.manifest.getName(), x + this.height + 2, y + 1).call();
+                mc.font.render(i18n.translateKey("gui.options.page.asset_packs.label.outdated_pack.1"), x + this.height + 2, y + 12).setColor(0x808080).call();
+                mc.font.render(i18n.translateKey("gui.options.page.asset_packs.label.outdated_pack.2"), x + this.height + 2, y + 22).setColor(0x808080).call();
 				rgbVersion = Colors.allChatColors[TextFormatting.RED.id].getARGB();
 			}
 
             if (hovered){
-                button.drawButton(mc, mouseX + x, mouseY + y - 3 - index * (BUTTON_HEIGHT + 3));
-                x -= button.width + 3;
+                this.button.drawButton(mc, mouseX + x, mouseY + y - 3 - index * (BUTTON_HEIGHT + 3));
+                x -= this.button.width + 3;
             }
 
-            String version = texturePack.manifest.getPackVersion();
+            String version = this.texturePack.manifest.getPackVersion();
             int versionWidth = mc.font.stringWidth(version);
-            mc.font.render(Tessellator.instance, texturePack.manifest.getPackVersion(), x + width - versionWidth - 2, y + 1).setColor(rgbVersion).call();
+            mc.font.render(this.texturePack.manifest.getPackVersion(), x + width - versionWidth - 2, y + 1).setColor(rgbVersion).call();
         }
         public void setupButton(int x, int y, int width, int mouseX, int mouseY){
-            button.setX(x + width - button.width - 1);
-            button.setY(y + (height - button.height)/2);
+            this.button.setX(x + width - this.button.width - 1);
+            this.button.setY(y + (this.height - this.button.height)/2);
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/ButtonComponent.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/ButtonComponent.java
index fd1831b52..73c0e958e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/ButtonComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/ButtonComponent.java
@@ -2,15 +2,17 @@ package net.minecraft.client.gui.options.components;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ButtonElement;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.gui.options.ScreenOptions;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.window.CursorShape;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.sound.SoundCategory;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
-
-import static org.lwjgl.opengl.GL11.*;
 
 public abstract class ButtonComponent
     implements OptionsComponent
@@ -54,26 +56,22 @@ public abstract class ButtonComponent
     }
 
     @Override
-    public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY)
+    public void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY)
     {
-        String translated = I18n.getInstance().translateKey(translationKey);
+        String translated = I18n.getInstance().translateKey(this.translationKey);
         int textColor = 0xFFFFFFFF;
         if (relativeMouseX >= 0 && relativeMouseX <= width && relativeMouseY >= COMPONENT_SPACING && relativeMouseY <= getHeight() - COMPONENT_SPACING) {
             textColor = 0xFFFFFFA0;
         }
 
-        if (relativeMouseX >= 0 && relativeMouseX <= width - BUTTON_WIDTH && relativeMouseY >= COMPONENT_SPACING && relativeMouseY <= getHeight() - COMPONENT_SPACING) {
-            this.hovered = true;
-        } else {
-            this.hovered = false;
-        }
+        this.hovered = relativeMouseX >= 0 && relativeMouseX <= width - BUTTON_WIDTH && relativeMouseY >= COMPONENT_SPACING && relativeMouseY <= getHeight() - COMPONENT_SPACING;
 
-        mc.font.render(Tessellator.instance, translated, x, y + (getHeight() / 2) - 4).setShadow().setColor(textColor).call();
-        resetButton.enabled = !isDefault();
+        mc.font.render(translated, x, y + (getHeight() / 2) - 4).setShadow().setColor(textColor).call();
+        this.resetButton.enabled = !isDefault();
         renderButton(x, y, width - BUTTON_WIDTH, COMPONENT_SPACING, BUTTON_WIDTH, 20, relativeMouseX, relativeMouseY);
         int stringWidth = mc.font.stringWidth(translated);
         int lineMaxX = x + width - BUTTON_WIDTH - 8;
-        if (resetButton.enabled) lineMaxX -= 20;
+        if (this.resetButton.enabled) lineMaxX -= 20;
         drawRect(x + stringWidth + 8, y + getHeight() / 2, lineMaxX, y + getHeight() / 2 + 1, 0x5F7F7F7F);
     }
 
@@ -83,7 +81,7 @@ public abstract class ButtonComponent
         if (relativeMouseX >= width - BUTTON_WIDTH && relativeMouseX <= width && relativeMouseY >= COMPONENT_SPACING && relativeMouseY <= COMPONENT_SPACING + 20) {
             mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
             buttonClicked(mouseButton, x, y, width, getHeight(), relativeMouseX - (width - BUTTON_WIDTH), relativeMouseY - COMPONENT_SPACING);
-        } else if (resetButton.enabled && relativeMouseX >= width - BUTTON_WIDTH - 20 && relativeMouseX <= width - BUTTON_WIDTH && relativeMouseY >= COMPONENT_SPACING && relativeMouseY <= COMPONENT_SPACING + 20) {
+        } else if (this.resetButton.enabled && relativeMouseX >= width - BUTTON_WIDTH - 20 && relativeMouseX <= width - BUTTON_WIDTH && relativeMouseY >= COMPONENT_SPACING && relativeMouseY <= COMPONENT_SPACING + 20) {
             mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
             resetValue();
         }
@@ -111,15 +109,15 @@ public abstract class ButtonComponent
     @Override
     public boolean matchesSearchTerm(String term)
     {
-        return I18n.getInstance().translateKey(translationKey).toLowerCase().contains(term.toLowerCase());
+        return I18n.getInstance().translateKey(this.translationKey).toLowerCase().contains(term.toLowerCase());
     }
 
     protected void renderButton(int x, int y, int relativeButtonX, int relativeButtonY, int buttonWidth, int buttonHeight, int relativeMouseX, int relativeMouseY) {
-        if (resetButton.enabled) {
-            resetButton.xPosition = x + relativeButtonX - 20;
-            resetButton.yPosition = y + relativeButtonY;
+        if (this.resetButton.enabled) {
+            this.resetButton.xPosition = x + relativeButtonX - 20;
+            this.resetButton.yPosition = y + relativeButtonY;
 
-            resetButton.drawButton(mc, x + relativeMouseX, y + relativeMouseY);
+            this.resetButton.drawButton(mc, x + relativeMouseX, y + relativeMouseY);
 
             if (relativeMouseX >= relativeButtonX && relativeMouseX < relativeButtonX + buttonWidth && relativeMouseY >= relativeButtonY && relativeButtonY < relativeButtonY + buttonHeight) {
                 mc.currentScreen.setDesiredCursor(CursorShape.HAND);
@@ -127,21 +125,20 @@ public abstract class ButtonComponent
         }
     }
 
-    protected void drawRect(int minX, int minY, int maxX, int maxY, int argb)
-    {
-        Tessellator tessellator = Tessellator.instance;
-        GL11.glEnable(GL_BLEND);
-        GL11.glDisable(GL_TEXTURE_2D);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    protected void drawRect(int minX, int minY, int maxX, int maxY, int argb) {
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_I(argb & 0x00FFFFFF, argb >> 24 & 0xff);
+        tessellator.setColor2i(argb & 0x00FFFFFF, argb >> 24 & 0xff);
         tessellator.addVertex(minX, maxY, 0.0D);
         tessellator.addVertex(maxX, maxY, 0.0D);
         tessellator.addVertex(maxX, minY, 0.0D);
         tessellator.addVertex(minX, minY, 0.0D);
         tessellator.draw();
-        GL11.glEnable(GL_TEXTURE_2D);
-        GL11.glDisable(GL_BLEND);
+        GLRenderer.popFrame();
     }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/LanguagePackListComponent.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/LanguagePackListComponent.java
index 92e8fa27b..ae1424cce 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/LanguagePackListComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/LanguagePackListComponent.java
@@ -2,12 +2,15 @@ package net.minecraft.client.gui.options.components;
 
 import com.mojang.logging.LogUtils;
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.gui.options.ScreenOptions;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.lang.Language;
 import net.minecraft.core.lang.LanguageSeeker;
+import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.slf4j.Logger;
 
 import java.io.IOException;
@@ -37,13 +40,13 @@ public class LanguagePackListComponent
 
     @Override
     public void init(Minecraft mc) {
-        buttons.clear();
+        this.buttons.clear();
 
         try {
-            languages = LanguageSeeker.getAvailableLanguages();
-            for (int i = 0; i < languages.size(); i++) {
-                Language language = languages.get(i);
-                buttons.add(new LanguagePackComponent(i, language));
+            this.languages = LanguageSeeker.getAvailableLanguages();
+            for (int i = 0; i < this.languages.size(); i++) {
+                Language language = this.languages.get(i);
+                this.buttons.add(new LanguagePackComponent(i, language));
             }
         } catch (IOException e) {
             LOGGER.error("Exception while getting available languages!", e);
@@ -52,21 +55,21 @@ public class LanguagePackListComponent
 
     @Override
     public int getHeight() {
-        return buttons.size() * BUTTON_HEIGHT;
+        return this.buttons.size() * BUTTON_HEIGHT;
     }
 
     @Override
-    public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        for (int i = 0; i < buttons.size(); i++) {
-            LanguagePackComponent button = buttons.get(i);
+    public void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+        for (int i = 0; i < this.buttons.size(); i++) {
+            LanguagePackComponent button = this.buttons.get(i);
             button.render(x, 3 + y + i * (BUTTON_HEIGHT + 3), width, relativeMouseX, relativeMouseY);
         }
     }
 
     @Override
     public void onMouseClick(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        for (int i = 0; i < buttons.size(); i++) {
-            LanguagePackComponent button = buttons.get(i);
+        for (int i = 0; i < this.buttons.size(); i++) {
+            LanguagePackComponent button = this.buttons.get(i);
             if (relativeMouseX >= 0 && relativeMouseX <= width && relativeMouseY >= 3 + i * (BUTTON_HEIGHT + 3) && relativeMouseY <= 3 + i * (BUTTON_HEIGHT + 3) + BUTTON_HEIGHT) {
                 String lang = button.languagePack.getId();
                 mc.gameSettings.language.set(lang);
@@ -77,13 +80,16 @@ public class LanguagePackListComponent
     }
 
     @Override
-    public void onMouseMove(int x, int y, int width, int relativeMouseX, int relativeMouseY) { }
+    public void onMouseMove(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+    }
 
     @Override
-    public void onMouseRelease(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) { }
+    public void onMouseRelease(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+    }
 
     @Override
-    public void onKeyPress(int keyCode, char character) { }
+    public void onKeyPress(int keyCode, char character) {
+    }
 
     @Override
     public boolean matchesSearchTerm(String term) {
@@ -91,7 +97,7 @@ public class LanguagePackListComponent
     }
 
     private static class LanguagePackComponent {
-    	private final Minecraft mc = Minecraft.getMinecraft();
+        private final Minecraft mc = Minecraft.getMinecraft();
         public final int index;
         public final Language languagePack;
         public final int height = BUTTON_HEIGHT;
@@ -102,32 +108,32 @@ public class LanguagePackListComponent
         }
 
         public void render(int x, int y, int width, int mouseX, int mouseY) {
-            Tessellator tessellator = Tessellator.instance;
-
-            if (mc.gameSettings.language.value.equals(languagePack.getId())) {
+            if (this.mc.gameSettings.language.value.equals(this.languagePack.getId())) {
                 // Draw background
-                GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-                GL11.glDisable(GL11.GL_TEXTURE_2D);
+                GLRenderer.pushFrame();
+                GLRenderer.setShader(Shaders.COLOR);
+                GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+                TessellatorGeneral tessellator = GLRenderer.getTessellator();
                 tessellator.startDrawingQuads();
 
-                tessellator.setColorOpaque_I(0x7F808080);
-                tessellator.addVertexWithUV(x - 2, y + height + 2, 0, 0, 1);
-                tessellator.addVertexWithUV(x + width + 2, y + height + 2, 0, 1, 1);
+                tessellator.setColorOpaque1i(0x7F808080);
+                tessellator.addVertexWithUV(x - 2, y + this.height + 2, 0, 0, 1);
+                tessellator.addVertexWithUV(x + width + 2, y + this.height + 2, 0, 1, 1);
                 tessellator.addVertexWithUV(x + width + 2, y - 2, 0, 1, 1);
                 tessellator.addVertexWithUV(x - 2, y - 2, 0, 0, 0);
 
-                tessellator.setColorOpaque_I(0);
-                tessellator.addVertexWithUV(x - 1, y + height + 1, 0, 0, 1);
-                tessellator.addVertexWithUV(x + width + 1, y + height + 1, 0, 1, 1);
+                tessellator.setColorOpaque1i(0);
+                tessellator.addVertexWithUV(x - 1, y + this.height + 1, 0, 0, 1);
+                tessellator.addVertexWithUV(x + width + 1, y + this.height + 1, 0, 1, 1);
                 tessellator.addVertexWithUV(x + width + 1, y - 1, 0, 1, 1);
                 tessellator.addVertexWithUV(x - 1, y - 1, 0, 0, 0);
 
                 tessellator.draw();
-                GL11.glEnable(GL11.GL_TEXTURE_2D);
+                GLRenderer.popFrame();
             }
             StringBuilder sb = new StringBuilder();
-            String name = languagePack.getName();
-            String region = languagePack.getRegion();
+            String name = this.languagePack.getName();
+            String region = this.languagePack.getRegion();
             if (name != null) {
                 sb.append(name);
             } else {
@@ -138,7 +144,7 @@ public class LanguagePackListComponent
             }
             final String fullName = sb.toString();
             final StringBuilder credits = new StringBuilder();
-            final Iterator<String> creditsList = languagePack.getCredits().listIterator();
+            final Iterator<String> creditsList = this.languagePack.getCredits().listIterator();
             boolean empty = true;
             while (creditsList.hasNext()) {
                 credits.append(creditsList.next());
@@ -147,8 +153,8 @@ public class LanguagePackListComponent
                 }
                 empty = false;
             }
-            this.mc.font.renderCentered(Tessellator.instance, fullName, x + (width / 2), y + 1).setShadow().call();
-            this.mc.font.renderCentered(Tessellator.instance, empty ? "Unknown Credits" : credits, x + width / 2, y + 12).setShadow().setColor(0x808080).call();
+            this.mc.font.renderCentered(fullName, x + (width / 2), y + 1).setShadow().call();
+            this.mc.font.renderCentered(empty ? "Unknown Credits" : credits, x + width / 2, y + 12).setShadow().setColor(0x808080).call();
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/OptionsCategory.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/OptionsCategory.java
index 15babdda7..9935b5261 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/OptionsCategory.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/OptionsCategory.java
@@ -2,18 +2,18 @@ package net.minecraft.client.gui.options.components;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ItemElement;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.gui.options.ScreenOptions;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.sound.SoundCategory;
+import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 
 import java.util.ArrayList;
 import java.util.List;
 
 public class OptionsCategory
-    implements OptionsComponent
-{
+    implements OptionsComponent {
     private static final Minecraft mc = Minecraft.getMinecraft();
     private static final ItemElement renderItem = new ItemElement(mc);
     private static final int PADDING = 2;
@@ -32,34 +32,30 @@ public class OptionsCategory
     private final @Nullable String tooltipTranslationKey;
     private @Nullable String shownTooltipTranslationKey = null;
 
-    public OptionsCategory(String translationKey)
-    {
+    public OptionsCategory(String translationKey) {
         this(translationKey, null);
     }
 
-    public OptionsCategory(String translationKey, ItemStack icon)
-    {
+    public OptionsCategory(String translationKey, ItemStack icon) {
         this(translationKey, icon, null);
     }
 
-    public OptionsCategory(String translationKey, ItemStack icon, @Nullable String tooltipTranslationKey)
-    {
+    public OptionsCategory(String translationKey, ItemStack icon, @Nullable String tooltipTranslationKey) {
         this.translationKey = translationKey;
         this.tooltipTranslationKey = tooltipTranslationKey;
         this.icon = icon;
     }
 
-    public OptionsCategory withComponent(OptionsComponent component)
-    {
+    public OptionsCategory withComponent(OptionsComponent component) {
         if (component != null) {
-            components.add(component);
+            this.components.add(component);
         }
         return this;
     }
 
     @Override
     public void init(Minecraft mc) {
-        for (OptionsComponent component : components) {
+        for (OptionsComponent component : this.components) {
             component.init(mc);
         }
     }
@@ -71,19 +67,16 @@ public class OptionsCategory
 
     @Override
     public void tick() {
-        for (OptionsComponent component : components)
-        {
+        for (OptionsComponent component : this.components) {
             component.tick();
         }
     }
 
     @Override
-    public int getHeight()
-    {
+    public int getHeight() {
         int height = TOP_SPACING;
-        if (!collapsed) {
-            for (OptionsComponent component : components)
-            {
+        if (!this.collapsed) {
+            for (OptionsComponent component : this.components) {
                 height += component.getHeight();
             }
         }
@@ -91,31 +84,29 @@ public class OptionsCategory
     }
 
     @Override
-    public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY)
-    {
+    public void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
         I18n i18n = I18n.getInstance();
         int textColor = 0x7F7F7F;
         this.shownTooltipTranslationKey = null;
-        if (relativeMouseX >= 0 && relativeMouseX < width && relativeMouseY >= 0 && relativeMouseY < TOP_SPACING)
-        {
+        if (relativeMouseX >= 0 && relativeMouseX < width && relativeMouseY >= 0 && relativeMouseY < TOP_SPACING) {
             textColor = 0xFFFFA0;
             this.shownTooltipTranslationKey = this.tooltipTranslationKey;
 
         }
-        mc.font.render(Tessellator.instance, (this.collapsed ? "▷" : "▽"), x, y + PADDING + 10).setShadow().setColor(textColor).call();
+        mc.font.render((this.collapsed ? "▷" : "▽"), x, y + PADDING + 10).setShadow().setColor(textColor).call();
 
         int xOffset = 10;
-        if (icon != null)
-        {
-            renderItem.render(icon, x + 11, y + PADDING + 5);
+        if (this.icon != null) {
+            renderItem.render(this.icon, x + 11, y + PADDING + 5);
             xOffset += 20;
         }
-        mc.font.render(Tessellator.instance, i18n.translateKey(this.translationKey), x + xOffset, y + PADDING + 10).setShadow().setColor(textColor).call();
-        if (!collapsed) {
+        mc.font.render(i18n.translateKey(this.translationKey), x + xOffset, y + PADDING + 10).setShadow().setColor(textColor).call();
+        if (!this.collapsed) {
             int componentY = TOP_SPACING;
-            for (OptionsComponent component : components)
-            {
-                component.render(x + COMPONENT_LEFT_MARGIN, y + componentY, width - COMPONENT_LEFT_MARGIN, relativeMouseX - COMPONENT_LEFT_MARGIN, relativeMouseY - componentY);
+            for (OptionsComponent component : this.components) {
+                if (y + componentY + component.getHeight() >= screenOptions.top && y + componentY <= screenOptions.bottom) {
+                    component.render(screenOptions, x + COMPONENT_LEFT_MARGIN, y + componentY, width - COMPONENT_LEFT_MARGIN, relativeMouseX - COMPONENT_LEFT_MARGIN, relativeMouseY - componentY);
+                }
                 componentY += component.getHeight();
 
                 @Nullable String componentTooltipTranslationKey = component.getTooltipTranslationKey();
@@ -127,19 +118,17 @@ public class OptionsCategory
     }
 
     @Override
-    public void onMouseClick(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY)
-    {
-        if (relativeMouseX >= 0 && relativeMouseX < width && relativeMouseY >= 0 && relativeMouseY < TOP_SPACING)
-        {
-            collapsed = !collapsed;
+    public void onMouseClick(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+        if (relativeMouseX >= 0 && relativeMouseX < width && relativeMouseY >= 0 && relativeMouseY < TOP_SPACING) {
+            this.collapsed = !this.collapsed;
             mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
         }
         int componentY = TOP_SPACING;
-        for (OptionsComponent component : components) {
+        for (OptionsComponent component : this.components) {
             if (relativeMouseX >= COMPONENT_LEFT_MARGIN && relativeMouseX < width && relativeMouseY >= componentY && relativeMouseY < componentY + component.getHeight()) {
                 component.onMouseClick(mouseButton, x + COMPONENT_LEFT_MARGIN, componentY, width - COMPONENT_LEFT_MARGIN, relativeMouseX - COMPONENT_LEFT_MARGIN, relativeMouseY - componentY);
-                clickedComponent = component;
-                clickedComponentY = componentY;
+                this.clickedComponent = component;
+                this.clickedComponentY = componentY;
                 return;
             }
             componentY += component.getHeight();
@@ -148,39 +137,33 @@ public class OptionsCategory
 
     @Override
     public void onMouseMove(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        if (clickedComponent != null) {
-            clickedComponent.onMouseMove(x + COMPONENT_LEFT_MARGIN, clickedComponentY, width - COMPONENT_LEFT_MARGIN, relativeMouseX - COMPONENT_LEFT_MARGIN, relativeMouseY - clickedComponentY);
+        if (this.clickedComponent != null) {
+            this.clickedComponent.onMouseMove(x + COMPONENT_LEFT_MARGIN, this.clickedComponentY, width - COMPONENT_LEFT_MARGIN, relativeMouseX - COMPONENT_LEFT_MARGIN, relativeMouseY - this.clickedComponentY);
         }
     }
 
     @Override
     public void onMouseRelease(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        if (clickedComponent != null) {
-            clickedComponent.onMouseRelease(mouseButton, x + COMPONENT_LEFT_MARGIN, clickedComponentY, width - COMPONENT_LEFT_MARGIN, relativeMouseX - COMPONENT_LEFT_MARGIN, relativeMouseY - clickedComponentY);
+        if (this.clickedComponent != null) {
+            this.clickedComponent.onMouseRelease(mouseButton, x + COMPONENT_LEFT_MARGIN, this.clickedComponentY, width - COMPONENT_LEFT_MARGIN, relativeMouseX - COMPONENT_LEFT_MARGIN, relativeMouseY - this.clickedComponentY);
         }
     }
 
     @Override
-    public void onKeyPress(int keyCode, char character)
-    {
-        for (OptionsComponent component : components)
-        {
+    public void onKeyPress(int keyCode, char character) {
+        for (OptionsComponent component : this.components) {
             component.onKeyPress(keyCode, character);
         }
     }
 
-    public OptionsCategory filter(String term)
-    {
-        OptionsCategory category = new OptionsCategory(translationKey);
-        for (OptionsComponent component : components)
-        {
-            if (component.matchesSearchTerm(term))
-            {
+    public OptionsCategory filter(String term) {
+        OptionsCategory category = new OptionsCategory(this.translationKey);
+        for (OptionsComponent component : this.components) {
+            if (component.matchesSearchTerm(term)) {
                 category.withComponent(component);
             }
         }
-        if (category.components.isEmpty())
-        {
+        if (category.components.isEmpty()) {
             return null;
         }
         return category;
@@ -188,14 +171,13 @@ public class OptionsCategory
 
     @Override
     public void onClose() {
-        for (OptionsComponent component : components) {
+        for (OptionsComponent component : this.components) {
             component.onClose();
         }
     }
 
     @Override
-    public boolean matchesSearchTerm(String term)
-    {
+    public boolean matchesSearchTerm(String term) {
         return false;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/OptionsComponent.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/OptionsComponent.java
index 96466a400..e8fd06b19 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/OptionsComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/OptionsComponent.java
@@ -1,6 +1,8 @@
 package net.minecraft.client.gui.options.components;
 
 import net.minecraft.client.Minecraft;
+import net.minecraft.client.gui.options.ScreenOptions;
+import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 
 public interface OptionsComponent
@@ -11,7 +13,7 @@ public interface OptionsComponent
 
     int getHeight();
 
-    void render(int x, int y, int width, int relativeMouseX, int relativeMouseY);
+    void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY);
 
     default void tick() { }
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/SearchFieldComponent.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/SearchFieldComponent.java
index 9c1200fc3..6cd7573c0 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/SearchFieldComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/SearchFieldComponent.java
@@ -3,10 +3,12 @@ package net.minecraft.client.gui.options.components;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ButtonElement;
 import net.minecraft.client.gui.TextFieldElement;
+import net.minecraft.client.gui.options.ScreenOptions;
 import net.minecraft.client.gui.options.data.OptionsPage;
 import net.minecraft.client.gui.options.data.OptionsPageRegistry;
 import net.minecraft.client.gui.text.TextFieldEditor;
 import net.minecraft.core.sound.SoundCategory;
+import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
 
@@ -27,21 +29,21 @@ public class SearchFieldComponent
     private OptionsComponent clickedComponent = null;
     private int clickedComponentY = 0;
 
-    private ButtonElement clearButton;
+    private final ButtonElement clearButton;
 
     public SearchFieldComponent() {
-        textField = new TextFieldElement(mc.currentScreen, mc.font, 0, 0, 150, 18, "", "Search...");
-        textField.setMaxStringLength(20);
-        textField.setTextChangeListener(this);
-        editor = new TextFieldEditor(textField);
-        clearButton = new ButtonElement(0, 0, 0, 12, 20, "")
+        this.textField = new TextFieldElement(mc.currentScreen, mc.font, 0, 0, 150, 18, "", "Search...");
+        this.textField.setMaxStringLength(20);
+        this.textField.setTextChangeListener(this);
+        this.editor = new TextFieldEditor(this.textField);
+        this.clearButton = new ButtonElement(0, 0, 0, 12, 20, "")
             .setTextures("minecraft:gui/screen/options/clear", "minecraft:gui/screen/options/clear_highlighted", null);
     }
 
     @Override
     public void init(final Minecraft mc) {
         OptionsComponent.super.init(mc);
-        textField.parent = mc.currentScreen;
+        this.textField.parent = mc.currentScreen;
     }
 
     @Override
@@ -51,58 +53,60 @@ public class SearchFieldComponent
 
     @Override
     public void tick() {
-        textField.updateCursorCounter();
+        this.textField.updateCursorCounter();
 
-        for (OptionsComponent component : components) {
+        for (OptionsComponent component : this.components) {
             component.tick();
         }
     }
 
     @Override
     public int getHeight() {
-        int height = PADDING + textField.height + PADDING;
-        for (OptionsComponent component : components) {
+        int height = PADDING + this.textField.height + PADDING;
+        for (OptionsComponent component : this.components) {
             height += component.getHeight();
         }
         return height;
     }
 
     @Override
-    public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        textField.xPosition = x + width / 2 - textField.width / 2;
-        textField.yPosition = y + PADDING;
+    public void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+        this.textField.xPosition = x + width / 2 - this.textField.width / 2;
+        this.textField.yPosition = y + PADDING;
 
-        textField.drawTextBox();
-        textField.updateCursor(mc, x + relativeMouseX, y + relativeMouseY);
+        this.textField.drawTextBox();
+        this.textField.updateCursor(mc, x + relativeMouseX, y + relativeMouseY);
 
-        clearButton.xPosition = x + width / 2 + textField.width / 2 + 1;
-        clearButton.yPosition = y + PADDING - 1;
-        clearButton.drawButton(mc, x + relativeMouseX, y + relativeMouseY);
+        this.clearButton.xPosition = x + width / 2 + this.textField.width / 2 + 1;
+        this.clearButton.yPosition = y + PADDING - 1;
+        this.clearButton.drawButton(mc, x + relativeMouseX, y + relativeMouseY);
 
-        int componentY = PADDING + textField.height + PADDING;
-        for (OptionsComponent component : components) {
-            component.render(x, y + componentY, width, relativeMouseX, relativeMouseY - componentY);
+        int componentY = PADDING + this.textField.height + PADDING;
+        for (OptionsComponent component : this.components) {
+            if (y + componentY + component.getHeight() >= screenOptions.top && y + componentY <= screenOptions.bottom) {
+                component.render(screenOptions, x, y + componentY, width, relativeMouseX, relativeMouseY - componentY);
+            }
             componentY += component.getHeight();
         }
     }
 
     @Override
     public void onMouseClick(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        textField.mouseClicked(x + relativeMouseX, y + relativeMouseY, 0);
+        this.textField.mouseClicked(x + relativeMouseX, y + relativeMouseY, 0);
 
-        if (clearButton.mouseClicked(mc, x + relativeMouseX, y + relativeMouseY)) {
+        if (this.clearButton.mouseClicked(mc, x + relativeMouseX, y + relativeMouseY)) {
             mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
-            textField.setText("");
+            this.textField.setText("");
             updateSearchResults("");
             return;
         }
 
-        int componentY = PADDING + textField.height + PADDING;
-        for (OptionsComponent component : components) {
+        int componentY = PADDING + this.textField.height + PADDING;
+        for (OptionsComponent component : this.components) {
             if (relativeMouseX >= 0 && relativeMouseX < width && relativeMouseY >= componentY && relativeMouseY < componentY + component.getHeight()) {
                 component.onMouseClick(mouseButton, x, componentY, width, relativeMouseX, relativeMouseY - componentY);
-                clickedComponent = component;
-                clickedComponentY = componentY;
+                this.clickedComponent = component;
+                this.clickedComponentY = componentY;
                 return;
             }
             componentY += component.getHeight();
@@ -111,26 +115,26 @@ public class SearchFieldComponent
 
     @Override
     public void onMouseMove(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        if (clickedComponent != null) {
-            clickedComponent.onMouseMove(x, clickedComponentY, width, relativeMouseX, relativeMouseY - clickedComponentY);
+        if (this.clickedComponent != null) {
+            this.clickedComponent.onMouseMove(x, this.clickedComponentY, width, relativeMouseX, relativeMouseY - this.clickedComponentY);
         }
     }
 
     @Override
     public void onMouseRelease(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        if (clickedComponent != null) {
-            clickedComponent.onMouseRelease(mouseButton, x, clickedComponentY, width, relativeMouseX, relativeMouseY - clickedComponentY);
+        if (this.clickedComponent != null) {
+            this.clickedComponent.onMouseRelease(mouseButton, x, this.clickedComponentY, width, relativeMouseX, relativeMouseY - this.clickedComponentY);
         }
     }
 
     @Override
     public void onKeyPress(int keyCode, char character) {
-        if (textField.isFocused && keyCode != Keyboard.KEY_ESCAPE) {
-            textField.textboxKeyTyped(character, keyCode);
+        if (this.textField.isFocused && keyCode != Keyboard.KEY_ESCAPE) {
+            this.textField.textboxKeyTyped(character, keyCode);
         } else if (keyCode == Keyboard.KEY_ESCAPE) {
-            textField.setFocused(false);
+            this.textField.setFocused(false);
         } else {
-            for (OptionsComponent component : components) {
+            for (OptionsComponent component : this.components) {
                 component.onKeyPress(keyCode, character);
             }
         }
@@ -147,7 +151,7 @@ public class SearchFieldComponent
     }
 
     private void updateSearchResults(String searchTerm) {
-        components.clear();
+        this.components.clear();
         if (searchTerm.isEmpty()) {
             return;
         }
@@ -158,8 +162,7 @@ public class SearchFieldComponent
             OptionsCategory pageCategory = new OptionsCategory(page.getTranslationKey(), page.getIcon());
             boolean hasComponents = false;
             for (OptionsComponent component : page.getComponents()) {
-                if (component instanceof OptionsCategory) {
-                    OptionsCategory category = (OptionsCategory) component;
+                if (component instanceof OptionsCategory category) {
                     OptionsCategory filtered = category.filter(searchTerm);
                     if (filtered != null) {
                         pageCategory.withComponent(filtered);
@@ -171,7 +174,7 @@ public class SearchFieldComponent
                 }
             }
             if (hasComponents) {
-                components.add(pageCategory);
+                this.components.add(pageCategory);
             }
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/SelectedTexturePackListComponent.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/SelectedTexturePackListComponent.java
index 3c1ae2367..e6e8922d4 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/SelectedTexturePackListComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/SelectedTexturePackListComponent.java
@@ -2,15 +2,18 @@ package net.minecraft.client.gui.options.components;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ButtonElement;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.gui.options.ScreenOptions;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texturepack.TexturePack;
 import net.minecraft.client.util.helper.Colors;
 import net.minecraft.core.Global;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.net.command.TextFormatting;
 import net.minecraft.core.sound.SoundCategory;
+import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -36,8 +39,8 @@ public class SelectedTexturePackListComponent implements OptionsComponent {
 
     @Override
     public void tick() {
-        if (size != mc.texturePackList.selectedPacks.size()){
-            size = mc.texturePackList.selectedPacks.size();
+        if (this.size != mc.texturePackList.selectedPacks.size()) {
+            this.size = mc.texturePackList.selectedPacks.size();
             createTexturePackButtons();
         }
     }
@@ -48,58 +51,58 @@ public class SelectedTexturePackListComponent implements OptionsComponent {
     }
 
     public void createTexturePackButtons() {
-        selectedPacks.clear();
+        this.selectedPacks.clear();
 
-        TexturePackButton prevButton = new TexturePackButton(0, 3,false, mc.texturePackList.getDefaultTexturePack());
-        selectedPacks.add(prevButton);
+        TexturePackButton prevButton = new TexturePackButton(0, 3, false, mc.texturePackList.getDefaultTexturePack());
+        this.selectedPacks.add(prevButton);
 
         List<TexturePack> texturePacks = mc.texturePackList.selectedPacks;
         for (TexturePack texturePack : texturePacks) {
             prevButton = new TexturePackButton(prevButton.xPos, prevButton.yPos + (BUTTON_HEIGHT + 3), true, texturePack);
-            selectedPacks.add(prevButton);
+            this.selectedPacks.add(prevButton);
         }
     }
 
     @Override
     public int getHeight() {
-        if (selectedPacks.isEmpty()) return 20;
-        return 3 + selectedPacks.size() * (BUTTON_HEIGHT + 3);
+        if (this.selectedPacks.isEmpty()) return 20;
+        return 3 + this.selectedPacks.size() * (BUTTON_HEIGHT + 3);
     }
 
     @Override
-    public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        if (selectedPacks.isEmpty()) {
-            mc.font.renderCentered(Tessellator.instance, I18n.getInstance().translateKey("gui.options.page.asset_packs.label.no_packs"), x + width / 2, y + 4)
+    public void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+        if (this.selectedPacks.isEmpty()) {
+            mc.font.renderCentered(I18n.getInstance().translateKey("gui.options.page.asset_packs.label.no_packs"), x + width / 2, y + 4)
                 .setShadow()
                 .setColor(0x5F7F7F7F)
                 .call();
         }
-        for (TexturePackButton button : selectedPacks) {
-            if (button == draggedButton) continue;
+        for (TexturePackButton button : this.selectedPacks) {
+            if (button == this.draggedButton) continue;
             int yOff = 0;
-            if (button.draggable && draggedButton != null && relativeMouseX > 0 && relativeMouseX < width && relativeMouseY > 0 && relativeMouseY < getHeight()){
-                int shiftAmount = draggedButton.shiftAmount(relativeMouseY);
-                if (shiftAmount < 0){
-                    if (button.yPos < draggedButton.yPos && button.yPos >= draggedButton.yPos + (shiftAmount * (BUTTON_HEIGHT + 3))){
+            if (button.draggable && this.draggedButton != null && relativeMouseX > 0 && relativeMouseX < width && relativeMouseY > 0 && relativeMouseY < getHeight()) {
+                int shiftAmount = this.draggedButton.shiftAmount(relativeMouseY);
+                if (shiftAmount < 0) {
+                    if (button.yPos < this.draggedButton.yPos && button.yPos >= this.draggedButton.yPos + (shiftAmount * (BUTTON_HEIGHT + 3))) {
                         yOff += (BUTTON_HEIGHT + 3);
                     }
                 }
                 if (shiftAmount > 0) {
-                    if (button.yPos > draggedButton.yPos && button.yPos <= draggedButton.yPos + (shiftAmount * (BUTTON_HEIGHT + 3))){
+                    if (button.yPos > this.draggedButton.yPos && button.yPos <= this.draggedButton.yPos + (shiftAmount * (BUTTON_HEIGHT + 3))) {
                         yOff -= (BUTTON_HEIGHT + 3);
                     }
                 }
             }
             button.render(this, x, y + yOff, width, relativeMouseX, relativeMouseY);
         }
-        if (draggedButton != null){
-            draggedButton.render(this,x, y, width, relativeMouseX, relativeMouseY);
+        if (this.draggedButton != null) {
+            this.draggedButton.render(this, x, y, width, relativeMouseX, relativeMouseY);
         }
     }
 
     @Override
     public void onMouseClick(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        for (TexturePackButton button : selectedPacks) {
+        for (TexturePackButton button : this.selectedPacks) {
             if (button.isClickable() && button.isHovered(relativeMouseX, relativeMouseY, width)) {
                 if (button.onClick(this, mouseButton, x, y, width, relativeMouseX, relativeMouseY)) {
                     break;
@@ -109,23 +112,25 @@ public class SelectedTexturePackListComponent implements OptionsComponent {
     }
 
     @Override
-    public void onMouseMove(int x, int y, int width, int relativeMouseX, int relativeMouseY) { }
+    public void onMouseMove(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+    }
 
     @Override
     public void onMouseRelease(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        for (TexturePackButton button : selectedPacks) {
-            if (button.onRelease(this, mouseButton, x, y, width, relativeMouseX, relativeMouseY)){
+        for (TexturePackButton button : this.selectedPacks) {
+            if (button.onRelease(this, mouseButton, x, y, width, relativeMouseX, relativeMouseY)) {
                 break;
             }
         }
     }
 
     @Override
-    public void onKeyPress(int keyCode, char character) { }
+    public void onKeyPress(int keyCode, char character) {
+    }
 
     @Override
     public void onClose() {
-        draggedButton = null;
+        this.draggedButton = null;
     }
 
     @Override
@@ -134,7 +139,7 @@ public class SelectedTexturePackListComponent implements OptionsComponent {
     }
 
     private static class TexturePackButton {
-        private ButtonElement button;
+        private final ButtonElement button;
         public boolean draggable;
         public final TexturePack texturePack;
         public final int height = BUTTON_HEIGHT;
@@ -142,88 +147,97 @@ public class SelectedTexturePackListComponent implements OptionsComponent {
         public int yPos;
         private int clickX = -1;
         private int clickY = -1;
+
         public TexturePackButton(int xPos, int yPos, boolean draggable, TexturePack texturePack) {
             this.draggable = draggable;
             this.texturePack = texturePack;
             this.xPos = xPos;
             this.yPos = yPos;
-            button = new ButtonElement(0, 0, 0, 20, 20, "-");
+            this.button = new ButtonElement(0, 0, 0, 20, 20, "-");
         }
 
         public boolean isClickable() {
             return true;
         }
-        public boolean isHovered(int mouseX, int mouseY, int width){
-            if (isDragged()){
-                int dX = mouseX - clickX;
-                int dY = mouseY - clickY;
+
+        public boolean isHovered(int mouseX, int mouseY, int width) {
+            if (isDragged()) {
+                int dX = mouseX - this.clickX;
+                int dY = mouseY - this.clickY;
                 mouseX -= dX;
                 mouseY -= dY;
             }
-            return mouseX >= 0 && mouseX <= width && mouseY >= yPos && mouseY <= yPos + height;
+            return mouseX >= 0 && mouseX <= width && mouseY >= this.yPos && mouseY <= this.yPos + this.height;
         }
-        public boolean isDragged(){
-            return clickX > 0 || clickY > 0;
+
+        public boolean isDragged() {
+            return this.clickX > 0 || this.clickY > 0;
         }
-        public boolean onClick(SelectedTexturePackListComponent component, int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY){
+
+        public boolean onClick(SelectedTexturePackListComponent component, int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
             setupButton(x, y, width, relativeMouseX, relativeMouseY);
-            if (texturePack != mc.texturePackList.getDefaultTexturePack()){
-                if (mouseButton == 0 && button.isHovered(x + relativeMouseX, y + relativeMouseY)){
+            if (this.texturePack != mc.texturePackList.getDefaultTexturePack()) {
+                if (mouseButton == 0 && this.button.isHovered(x + relativeMouseX, y + relativeMouseY)) {
                     unsetPack(component);
                     mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
                     component.draggedButton = null;
                     return true;
                 }
-                if (mouseButton == 1){
+                if (mouseButton == 1) {
                     unsetPack(component);
                     mc.sndManager.playSound("random.click", SoundCategory.GUI_SOUNDS, 1.0F, 1.0F);
                     return true;
                 }
             }
-            if (!draggable) return false;
-            clickX = relativeMouseX;
-            clickY = relativeMouseY;
+            if (!this.draggable) return false;
+            this.clickX = relativeMouseX;
+            this.clickY = relativeMouseY;
             component.draggedButton = this;
             return true;
         }
+
         public boolean onRelease(SelectedTexturePackListComponent component, int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-            if (isDragged()){
-                if (relativeMouseX < 0 || relativeMouseX > x + width || relativeMouseY < 0 || relativeMouseY > y + component.getHeight()){
+            if (isDragged()) {
+                if (relativeMouseX < 0 || relativeMouseX > x + width || relativeMouseY < 0 || relativeMouseY > y + component.getHeight()) {
                     unsetPack(component);
                     return true;
                 }
-                mc.texturePackList.shiftPack(texturePack, shiftAmount(relativeMouseY));
-                clickX = -1;
-                clickY = -1;
+                mc.texturePackList.shiftPack(this.texturePack, shiftAmount(relativeMouseY));
+                this.clickX = -1;
+                this.clickY = -1;
                 component.draggedButton = null;
                 component.createTexturePackButtons();
                 return true;
             }
-            clickX = -1;
-            clickY = -1;
+            this.clickX = -1;
+            this.clickY = -1;
             return false;
         }
-        public void unsetPack(SelectedTexturePackListComponent component){
-            mc.texturePackList.unsetTexturePack(texturePack);
+
+        public void unsetPack(SelectedTexturePackListComponent component) {
+            mc.texturePackList.unsetTexturePack(this.texturePack);
             component.draggedButton = null;
             component.createTexturePackButtons();
         }
-        public int draggedX(int mouseX){
-            return mouseX - clickX;
+
+        public int draggedX(int mouseX) {
+            return mouseX - this.clickX;
         }
-        public int draggedY(int mouseY){
-            return mouseY - clickY;
+
+        public int draggedY(int mouseY) {
+            return mouseY - this.clickY;
         }
-        public int shiftAmount(int mouseY){
-            return draggedY(mouseY)/BUTTON_HEIGHT;
+
+        public int shiftAmount(int mouseY) {
+            return draggedY(mouseY) / BUTTON_HEIGHT;
         }
 
         public void render(SelectedTexturePackListComponent component, int x, int y, int width, int mouseX, int mouseY) {
-            Tessellator tessellator = Tessellator.instance;
+            TessellatorGeneral tessellator = GLRenderer.getTessellator();
 
             setupButton(x, y, width, mouseX, mouseY);
 
-            if (isDragged()){
+            if (isDragged()) {
                 int dX = draggedX(mouseX);
                 int dY = draggedY(mouseY);
                 x += dX;
@@ -232,73 +246,75 @@ public class SelectedTexturePackListComponent implements OptionsComponent {
 
             if (isDragged() || isHovered(mouseX, mouseY, width) && component.draggedButton == null) {
                 // Draw background
-                GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-                GL11.glDisable(GL11.GL_TEXTURE_2D);
+                GLRenderer.pushFrame();
+                GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+                GLRenderer.setShader(Shaders.COLOR);
                 tessellator.startDrawingQuads();
 
-                tessellator.setColorOpaque_I(0x7F808080);
-                tessellator.addVertexWithUV(x + xPos - 2,           y + yPos + height + 2, 0, 0, 1);
-                tessellator.addVertexWithUV(x + xPos + width + 2,   y + yPos + height + 2, 0, 1, 1);
-                tessellator.addVertexWithUV(x + xPos + width + 2,   y + yPos - 2, 0, 1, 1);
-                tessellator.addVertexWithUV(x + xPos - 2,           y + yPos - 2, 0, 0, 0);
+                tessellator.setColorOpaque1i(0x7F808080);
+                tessellator.addVertexWithUV(x + this.xPos - 2, y + this.yPos + this.height + 2, 0, 0, 1);
+                tessellator.addVertexWithUV(x + this.xPos + width + 2, y + this.yPos + this.height + 2, 0, 1, 1);
+                tessellator.addVertexWithUV(x + this.xPos + width + 2, y + this.yPos - 2, 0, 1, 1);
+                tessellator.addVertexWithUV(x + this.xPos - 2, y + this.yPos - 2, 0, 0, 0);
 
-                tessellator.setColorOpaque_I(0);
-                tessellator.addVertexWithUV(x + xPos - 1,           y + yPos + height + 1, 0, 0, 1);
-                tessellator.addVertexWithUV(x + xPos + width + 1,   y + yPos + height + 1, 0, 1, 1);
-                tessellator.addVertexWithUV(x + xPos + width + 1,   y + yPos - 1, 0, 1, 1);
-                tessellator.addVertexWithUV(x + xPos - 1,           y + yPos - 1, 0, 0, 0);
+                tessellator.setColorOpaque1i(0);
+                tessellator.addVertexWithUV(x + this.xPos - 1, y + this.yPos + this.height + 1, 0, 0, 1);
+                tessellator.addVertexWithUV(x + this.xPos + width + 1, y + this.yPos + this.height + 1, 0, 1, 1);
+                tessellator.addVertexWithUV(x + this.xPos + width + 1, y + this.yPos - 1, 0, 1, 1);
+                tessellator.addVertexWithUV(x + this.xPos - 1, y + this.yPos - 1, 0, 0, 0);
 
                 tessellator.draw();
-                GL11.glEnable(GL11.GL_TEXTURE_2D);
+                GLRenderer.popFrame();
             }
 
             // Draw texture pack info
-            texturePack.bindThumbnailTexture(mc);
-            GL11.glColor4f(1, 1, 1, 1);
+            this.texturePack.bindThumbnailTexture(mc);
+            GLRenderer.setColor4f(1, 1, 1, 1);
 
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0xFFFFFF);
-            tessellator.addVertexWithUV(x + xPos,           y + yPos + height, 0, 0, 1);
-            tessellator.addVertexWithUV(x + xPos + height,  y + yPos + height, 0, 1, 1);
-            tessellator.addVertexWithUV(x + xPos + height,  y + yPos, 0, 1, 0);
-            tessellator.addVertexWithUV(x + xPos,           y + yPos, 0, 0, 0);
+            tessellator.setColorOpaque1i(0xFFFFFF);
+            tessellator.addVertexWithUV(x + this.xPos, y + this.yPos + this.height, 0, 0, 1);
+            tessellator.addVertexWithUV(x + this.xPos + this.height, y + this.yPos + this.height, 0, 1, 1);
+            tessellator.addVertexWithUV(x + this.xPos + this.height, y + this.yPos, 0, 1, 0);
+            tessellator.addVertexWithUV(x + this.xPos, y + this.yPos, 0, 0, 0);
             tessellator.draw();
 
             int rgbVersion = 0x808080;
-            int format = texturePack.manifest.getFormat();
+            int format = this.texturePack.manifest.getFormat();
 
-            if(format == Global.ASSET_PACK_FORMAT) {
+            if (format == Global.ASSET_PACK_FORMAT) {
                 // Correct version
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getName(), x + this.xPos + this.height + 2, y + this.yPos + 1).call();
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getDescriptionLine1(), x + this.xPos + this.height + 2, y + this.yPos + 12).setColor(0x808080).call();
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getDescriptionLine2(), x + this.xPos + this.height + 2, y + this.yPos + 22).setColor(0x808080).call();
-            }else if(format == -1) {
+                mc.font.render(this.texturePack.manifest.getName(), x + this.xPos + this.height + 2, y + this.yPos + 1).call();
+                mc.font.render(this.texturePack.manifest.getDescriptionLine1(), x + this.xPos + this.height + 2, y + this.yPos + 12).setColor(0x808080).call();
+                mc.font.render(this.texturePack.manifest.getDescriptionLine2(), x + this.xPos + this.height + 2, y + this.yPos + 22).setColor(0x808080).call();
+            } else if (format == -1) {
                 // Manifest error
-                mc.font.render(Tessellator.instance, TextFormatting.RED + this.texturePack.manifest.getName(), x + this.xPos + this.height + 2, y + this.yPos + 1).call();
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getDescriptionLine1(), x + this.xPos + this.height + 2, y + this.yPos + 12).setColor(0x808080).call();
-                mc.font.render(Tessellator.instance, this.texturePack.manifest.getDescriptionLine2(), x + this.xPos + this.height + 2, y + this.yPos + 22).setColor(0x808080).call();
+                mc.font.render(TextFormatting.RED + this.texturePack.manifest.getName(), x + this.xPos + this.height + 2, y + this.yPos + 1).call();
+                mc.font.render(this.texturePack.manifest.getDescriptionLine1(), x + this.xPos + this.height + 2, y + this.yPos + 12).setColor(0x808080).call();
+                mc.font.render(this.texturePack.manifest.getDescriptionLine2(), x + this.xPos + this.height + 2, y + this.yPos + 22).setColor(0x808080).call();
                 rgbVersion = Colors.allChatColors[TextFormatting.RED.id].getARGB();
-            }else {
+            } else {
                 // Wrong texture pack version
                 I18n i18n = I18n.getInstance();
-                mc.font.render(Tessellator.instance, TextFormatting.RED + this.texturePack.manifest.getName(), x + this.xPos + this.height + 2, y + this.yPos + 1).call();
-                mc.font.render(Tessellator.instance, i18n.translateKey("gui.options.page.asset_packs.label.outdated_pack.1"), x + this.xPos + this.height + 2, y + this.yPos + 12).setColor(0x808080).call();
-                mc.font.render(Tessellator.instance, i18n.translateKey("gui.options.page.asset_packs.label.outdated_pack.2"), x + this.xPos + this.height + 2, y + this.yPos + 22).setColor(0x808080).call();
+                mc.font.render(TextFormatting.RED + this.texturePack.manifest.getName(), x + this.xPos + this.height + 2, y + this.yPos + 1).call();
+                mc.font.render(i18n.translateKey("gui.options.page.asset_packs.label.outdated_pack.1"), x + this.xPos + this.height + 2, y + this.yPos + 12).setColor(0x808080).call();
+                mc.font.render(i18n.translateKey("gui.options.page.asset_packs.label.outdated_pack.2"), x + this.xPos + this.height + 2, y + this.yPos + 22).setColor(0x808080).call();
                 rgbVersion = Colors.allChatColors[TextFormatting.RED.id].getARGB();
             }
 
-            if (isHovered(mouseX, mouseY, width) && component.draggedButton == null && texturePack != mc.texturePackList.getDefaultTexturePack()){
-                button.drawButton(mc, mouseX + x, mouseY + y);
-                x -= button.width + 3;
+            if (isHovered(mouseX, mouseY, width) && component.draggedButton == null && this.texturePack != mc.texturePackList.getDefaultTexturePack()) {
+                this.button.drawButton(mc, mouseX + x, mouseY + y);
+                x -= this.button.width + 3;
             }
 
-            String version = texturePack.manifest.getPackVersion();
+            String version = this.texturePack.manifest.getPackVersion();
             int versionWidth = mc.font.stringWidth(version);
-            mc.font.render(Tessellator.instance, this.texturePack.manifest.getPackVersion(), x + this.xPos + width - versionWidth - 2, y + this.yPos + 1).setColor(rgbVersion).call();
+            mc.font.render(this.texturePack.manifest.getPackVersion(), x + this.xPos + width - versionWidth - 2, y + this.yPos + 1).setColor(rgbVersion).call();
         }
-        public void setupButton(int x, int y, int width, int mouseX, int mouseY){
-            button.setX(x + xPos + width - button.width - 1);
-            button.setY(y + yPos + (height - button.height)/2);
+
+        public void setupButton(int x, int y, int width, int mouseX, int mouseY) {
+            this.button.setX(x + this.xPos + width - this.button.width - 1);
+            this.button.setY(y + this.yPos + (this.height - this.button.height) / 2);
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/ShortcutComponent.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/ShortcutComponent.java
index 32a65fc02..f392a5378 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/ShortcutComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/ShortcutComponent.java
@@ -2,8 +2,10 @@ package net.minecraft.client.gui.options.components;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ButtonElement;
+import net.minecraft.client.gui.options.ScreenOptions;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.sound.SoundCategory;
+import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 
 public class ShortcutComponent
@@ -33,7 +35,7 @@ public class ShortcutComponent
     }
 
     @Override
-    public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+    public void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
         button.xPosition = x + width / 2 - BUTTON_WIDTH / 2;
         button.yPosition = y + COMPONENT_SPACING;
         button.displayString = I18n.getInstance().translateKey(translationKey);
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/components/TooltipPickerComponent.java b/game/client/src/main/java/net/minecraft/client/gui/options/components/TooltipPickerComponent.java
index d9f17af7c..3ae3af48c 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/components/TooltipPickerComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/components/TooltipPickerComponent.java
@@ -2,9 +2,9 @@ package net.minecraft.client.gui.options.components;
 
 import net.minecraft.client.gui.TooltipElement;
 import net.minecraft.client.option.OptionTooltip;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.window.CursorShape;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 public class TooltipPickerComponent
     extends ToggleableOptionComponent<String> {
@@ -28,7 +28,7 @@ public class TooltipPickerComponent
 
         final int stringWidth = mc.font.stringWidth(this.option.getDisplayStringValue());
         final int stringHeight = mc.font.getFont().fontHeight();
-        GL11.glColor4f(1, 1, 1, 1);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
         this.tooltip.render(this.option.getDisplayStringValue(), x + relativeButtonX + buttonWidth/2 - stringWidth/2, y + relativeButtonY + buttonHeight/2 - stringHeight/2, 0, 0, -1, -1, false);
 
         if (relativeMouseX >= relativeButtonX && relativeMouseX < relativeButtonX + buttonWidth && relativeMouseY >= relativeButtonY && relativeButtonY < relativeButtonY + buttonHeight) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/options/data/OptionsPages.java b/game/client/src/main/java/net/minecraft/client/gui/options/data/OptionsPages.java
index f0f811d09..c523ac235 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/options/data/OptionsPages.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/options/data/OptionsPages.java
@@ -4,7 +4,6 @@ import com.mojang.logging.LogUtils;
 import com.mojang.nbt.NbtIo;
 import net.betterthanadventure.utils.DataDumper;
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.enums.EnumGPUVendor;
 import net.minecraft.client.gui.ScreenControllerSetup;
 import net.minecraft.client.gui.ScreenFontTest;
 import net.minecraft.client.gui.ScreenHudDesigner;
@@ -13,8 +12,8 @@ import net.minecraft.client.gui.ScreenTextureViewer;
 import net.minecraft.client.gui.achievements.ScreenAchievements;
 import net.minecraft.client.gui.modelviewer.ScreenModelViewer;
 import net.minecraft.client.gui.nbteditor.ScreenNBTEditor;
+import net.minecraft.client.gui.options.ScreenOptions;
 import net.minecraft.client.gui.options.components.*;
-import net.minecraft.client.option.enums.LightmapStyle;
 import net.minecraft.client.player.controller.PlayerControllerSP;
 import net.minecraft.client.sound.SoundEngine;
 import net.minecraft.client.util.helper.FileOpener;
@@ -27,17 +26,16 @@ import net.minecraft.core.achievement.stat.StatList;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.item.Items;
+import org.jetbrains.annotations.NotNull;
 import org.useless.seedviewer.SeedViewerMain;
 import paulscode.sound.SoundSystem;
 
-import javax.management.RuntimeErrorException;
 import java.io.File;
 import java.io.IOException;
 import java.util.Collections;
 
 
-public abstract class OptionsPages
-{
+public abstract class OptionsPages {
     private static final Minecraft mc = Minecraft.getMinecraft();
     private static boolean hasInit = false;
     public static OptionsPage GENERAL;
@@ -51,14 +49,12 @@ public abstract class OptionsPages
     public static OptionsPage SEARCH;
     public static OptionsPage DEBUG;
 
-    public static OptionsPage register(OptionsPage page)
-    {
+    public static OptionsPage register(OptionsPage page) {
         OptionsPageRegistry.getInstance().register(page);
         return page;
     }
 
-    public static void init()
-    {
+    public static void init() {
         if (hasInit) return;
         hasInit = true;
 
@@ -84,7 +80,7 @@ public abstract class OptionsPages
                 .withComponent(new BooleanOptionComponent(mc.gameSettings.armorDurabilityOverlay))
                 .withComponent(new BooleanOptionComponent(mc.gameSettings.heldItemCountOverlay))
                 .withComponent(new BooleanOptionComponent(mc.gameSettings.heldItemTooltips))
-                .withComponent(new ToggleableOptionComponent(mc.gameSettings.itemDescriptions))
+                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.itemDescriptions))
                 .withComponent(new BooleanOptionComponent(mc.gameSettings.hideUndiscoveredItems))
                 .withComponent(new BooleanOptionComponent(mc.gameSettings.dynamicCursor))
                 .withComponent(new BooleanOptionComponent(mc.gameSettings.musicToasts))
@@ -133,56 +129,48 @@ public abstract class OptionsPages
             )
         );
 
-        final OptionsComponent lightmapComponent = new ToggleableOptionComponent<>(mc.gameSettings.lightmapStyle);
-
         VIDEO = register(new OptionsPage("gui.options.page.video.title", new ItemStack(Items.FLAG))
-            .withComponent(new OptionsCategory("gui.options.page.video.category.graphics")
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.fullscreen))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.borderlessFullscreen))
-                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.renderScale))
-                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.fancyGraphics))
-                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.renderDistance))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.ambientOcclusion))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.connectedGlass))
-                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.mipmapLevels))
-                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.mipmapType))
-                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.colorblindnessFix))
-            )
-            .withComponent(new OptionsCategory("gui.options.page.video.category.performance")
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.enableVsync))
-                .withComponent(new FramerateOptionComponent(mc.gameSettings.customFpsLimit))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.advancedOpenGL))
-            )
-            .withComponent(new OptionsCategory("gui.options.page.video.category.post_processing")
-                .withComponent(new FloatOptionComponent(mc.gameSettings.gamma))
-                .withComponent(new FloatOptionComponent(mc.gameSettings.colorCorrection))
-                .withComponent(new FloatOptionComponent(mc.gameSettings.fxaa))
-                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.bloom))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.heatHaze))
-            )
-            .withComponent(new OptionsCategory("gui.options.page.video.category.visuals")
-                .withComponent(Minecraft.GPU_VENDOR == EnumGPUVendor.INTEL ? null : lightmapComponent)
-                .withComponent(new FloatOptionComponent(mc.gameSettings.brightness){
-                    @Override
-                    public void render(final int x, final int y, final int width, final int relativeMouseX, final int relativeMouseY) {
-                        this.slider.enabled = mc.gameSettings.lightmapStyle.value != LightmapStyle.DISABLED;
-                        super.render(x, y, width, relativeMouseX, relativeMouseY);
-                    }
-                })
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.fovModification))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.screenMotionEffects))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.fog))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.biomeWater))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.treeShadows))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.vignette))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.items3D))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.clouds))
-                .withComponent(new FloatOptionComponent(mc.gameSettings.cloudHeight, -0.5f, 1f))
-                .withComponent(new FloatOptionComponent(mc.gameSettings.entityRenderDistance, 0.1f, 3f))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.aurora))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.slimeParticles))
-                .withComponent(new FloatOptionComponent(mc.gameSettings.blockOutlineWidth))
-            )
+                .withComponent(new OptionsCategory("gui.options.page.video.category.graphics")
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.fullscreen))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.borderlessFullscreen))
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.renderScale))
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.fancyGraphics))
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.renderDistance))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.ambientOcclusion))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.connectedGlass))
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.mipmapLevels))
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.mipmapType))
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.colorblindnessFix))
+                )
+                .withComponent(new OptionsCategory("gui.options.page.video.category.performance")
+                        .withComponent(new BooleanOptionComponent(mc.gameSettings.enableVsync))
+                        .withComponent(new FramerateOptionComponent(mc.gameSettings.customFpsLimit))
+//                .withComponent(new BooleanOptionComponent(mc.gameSettings.advancedOpenGL))
+                )
+                .withComponent(new OptionsCategory("gui.options.page.video.category.post_processing")
+                    .withComponent(new FloatOptionComponent(mc.gameSettings.gamma))
+                    .withComponent(new FloatOptionComponent(mc.gameSettings.colorCorrection))
+                    .withComponent(new FloatOptionComponent(mc.gameSettings.fxaa))
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.bloom))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.heatHaze))
+                )
+                .withComponent(new OptionsCategory("gui.options.page.video.category.visuals")
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.lightmapStyle))
+                    .withComponent(new FloatOptionComponent(mc.gameSettings.brightness))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.fovModification))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.screenMotionEffects))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.fog))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.biomeWater))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.treeShadows))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.vignette))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.items3D))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.clouds))
+                    .withComponent(new FloatOptionComponent(mc.gameSettings.cloudHeight, -0.5f, 1f))
+                    .withComponent(new FloatOptionComponent(mc.gameSettings.entityRenderDistance, 0.1f, 3f))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.aurora))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.slimeParticles))
+                    .withComponent(new FloatOptionComponent(mc.gameSettings.blockOutlineWidth))
+                )
         );
 
         CONTROLS = register(new OptionsPage("gui.options.page.controls.title", new ItemStack(Items.BOAT))
@@ -301,7 +289,7 @@ public abstract class OptionsPages
                 .withComponent(new BooleanOptionComponent(mc.gameSettings.customLightmap))
                 .withComponent(new BooleanOptionComponent(mc.gameSettings.enableHolidayTextures))
             )
-            .withComponent(new ShortcutComponent("gui.options.page.asset_packs.button.apply", () -> mc.texturePackList.refreshIfReady()))
+            .withComponent(new ShortcutComponent("gui.options.page.asset_packs.button.apply", mc.texturePackList::refreshIfReady))
             .withComponent(new OptionsCategory("gui.options.page.asset_packs.category.asset_packs.selected")
                 .withComponent(new SelectedTexturePackListComponent())
             )
@@ -339,38 +327,38 @@ public abstract class OptionsPages
                 .withComponent(new KeyBindingComponent(mc.gameSettings.keyLoadChunksQuickly))
             )
             .withComponent(new OptionsCategory("gui.options.page.debug.category.settings")
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.developerMode))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.playerDevModel))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.viewSupportMode))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.alphaMenu))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.lockCamera))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.showDebugScreen))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.showFrameTimes))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.showChunkBorders))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.showCollisionBoxes))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.showItemDebugInfo))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.disableCrashHandler))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.startInFullscreen))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.disableShaders))
-                .withComponent(Minecraft.GPU_VENDOR == EnumGPUVendor.INTEL ? lightmapComponent : null)
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.loadAllSounds))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.allowSoundOverrides))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.downloadSoundfiles))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.enableDevResourceLoading))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.devModels))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.enableMultiDrawRendering))
-                .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.enableThreadedChunkProvider))
-                .withComponent(new BooleanOptionComponent(mc.gameSettings.doJCECheck))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.developerMode))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.playerDevModel))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.viewSupportMode))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.alphaMenu))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.lockCamera))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.showDebugScreen))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.showFrameTimes))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.showChunkBorders))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.showCollisionBoxes))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.showItemDebugInfo))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.disableCrashHandler))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.startInFullscreen))
+//                .withComponent(new BooleanOptionComponent(mc.gameSettings.disableShaders))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.loadAllSounds))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.allowSoundOverrides))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.downloadSoundfiles))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.enableDevResourceLoading))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.devModels))
+//                .withComponent(new BooleanOptionComponent(mc.gameSettings.enableMultiDrawRendering))
+                    .withComponent(new ToggleableOptionComponent<>(mc.gameSettings.enableThreadedChunkProvider))
+                    .withComponent(new BooleanOptionComponent(mc.gameSettings.doJCECheck))
             )
             .withComponent(new OptionsCategory("gui.options.page.debug.category.utility")
                 .withComponent(new ShortcutComponent("gui.options.page.debug.button.open.model_viewer", () -> {
                                    mc.playerController = new PlayerControllerSP(mc);
                                    mc.changeWorld(WorldClient.EMPTY_WORLD, "Loading Model Viewer");
-                                   mc.displayScreen(new ScreenModelViewer());}) {
+                                   mc.displayScreen(new ScreenModelViewer());
+                               }) {
                                    @Override
-                                   public void render(final int x, final int y, final int width, final int relativeMouseX, final int relativeMouseY) {
+                                   public void render(@NotNull ScreenOptions screenOptions, final int x, final int y, final int width, final int relativeMouseX, final int relativeMouseY) {
                                        this.button.enabled = mc.currentWorld == null;
-                                       super.render(x, y, width, relativeMouseX, relativeMouseY);
+                                       super.render(screenOptions, x, y, width, relativeMouseX, relativeMouseY);
                                    }
                                }
                 )
@@ -394,7 +382,7 @@ public abstract class OptionsPages
                         throw new RuntimeException(e);
                     }
                 }))
-                .withComponent(new ShortcutComponent("gui.options.page.debug.button.open.datadumper", () ->{
+                .withComponent(new ShortcutComponent("gui.options.page.debug.button.open.datadumper", () -> {
                     DataDumper.main(new String[0]);
                     FileOpener.open(new File(mc.getMinecraftDir(), "infodump"));
                     Global.accessor = mc;
@@ -414,23 +402,23 @@ public abstract class OptionsPages
                     mc.currentWorld.getLevelData().setCheatsEnabled(true);
                 }) {
                     @Override
-                    public void render(final int x, final int y, final int width, final int relativeMouseX, final int relativeMouseY) {
+                    public void render(@NotNull ScreenOptions screenOptions, final int x, final int y, final int width, final int relativeMouseX, final int relativeMouseY) {
                         this.button.enabled = (mc.currentWorld != null && !mc.currentWorld.isClientSide);
-                        super.render(x, y, width, relativeMouseX, relativeMouseY);
+                        super.render(screenOptions, x, y, width, relativeMouseX, relativeMouseY);
                     }
                 })
                 .withComponent(new ShortcutComponent("gui.options.page.debug.button.wipestats", () -> {
                     mc.statsCounter.wipe("I want to delete all the saved stats");
                 }))
                 .withComponent(new ShortcutComponent("gui.options.page.debug.button.unlockedall", () -> {
-                    for (final Stat stat : StatList.getAllStats()){
+                    for (final Stat stat : StatList.getAllStats()) {
                         mc.thePlayer.addStat(stat, mc.thePlayer.getStat(stat) == 0 ? 1 : 0);
                     }
                 }) {
                     @Override
-                    public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
+                    public void render(@NotNull ScreenOptions screenOptions, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
                         this.button.enabled = (mc.thePlayer != null);
-                        super.render(x, y, width, relativeMouseX, relativeMouseY);
+                        super.render(screenOptions, x, y, width, relativeMouseX, relativeMouseY);
                     }
                 })
                 .withComponent(new ShortcutComponent("gui.options.page.debug.button.crash.soft", () -> {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/paged/ScreenPaged.java b/game/client/src/main/java/net/minecraft/client/gui/paged/ScreenPaged.java
index a3659c326..4a94b27a9 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/paged/ScreenPaged.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/paged/ScreenPaged.java
@@ -4,16 +4,17 @@ import net.minecraft.client.gui.ButtonElement;
 import net.minecraft.client.gui.ItemElement;
 import net.minecraft.client.gui.Screen;
 import net.minecraft.client.render.Scissor;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.sound.SoundCategory;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
-
-import static org.lwjgl.opengl.GL11.*;
 
 public class ScreenPaged
     extends Screen {
@@ -190,7 +191,7 @@ public class ScreenPaged
     }
 
     public void handleScroll(int mx, int my, float partialTick) {
-        if (mx > this.leftWidth + SEPARATOR_WIDTH + PADDING && mx < this.width - rightOffset) {
+        if (mx > this.leftWidth + SEPARATOR_WIDTH + PADDING && mx < this.width - this.rightOffset) {
             if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL)) {
                 this.scrollRightPanel(Mouse.getDWheel() / -0.01f);
             } else {
@@ -212,7 +213,7 @@ public class ScreenPaged
         handleScroll(mx, my, renderPartialTicks);
 
         this.leftWidth = (int) (this.width * 0.25f);
-        this.pageWidth = this.width - (this.leftWidth + SEPARATOR_WIDTH + (PADDING * 2)) - rightOffset;
+        this.pageWidth = this.width - (this.leftWidth + SEPARATOR_WIDTH + (PADDING * 2)) - this.rightOffset;
         final @NotNull I18n i18n = I18n.getInstance();
 
         this.renderBackground();
@@ -242,37 +243,37 @@ public class ScreenPaged
 
         // Draw shadows
         if (this.mc.currentWorld == null) {
-            final Tessellator tessellator = Tessellator.instance;
-            GL11.glDisable(GL_DEPTH_TEST);
+//            GL11.glDisable(GL_ALPHA_TEST);
+//            GL11.glShadeModel(GL_SMOOTH);
+
+            GLRenderer.pushFrame();
+            GLRenderer.disableState(State.DEPTH_TEST);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.setShader(Shaders.COLOR);
             final int shadowSize = 4;
-            GL11.glEnable(GL_BLEND);
-            GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-            GL11.glDisable(GL_ALPHA_TEST);
-            GL11.glShadeModel(GL_SMOOTH);
-            GL11.glDisable(GL_TEXTURE_2D);
-
+            final TessellatorGeneral tessellator = GLRenderer.getTessellator();
             tessellator.startDrawingQuads();
-            tessellator.setColorRGBA_I(0, 0);
+            tessellator.setColor2i(0, 0);
             tessellator.addVertexWithUV(0, this.top + shadowSize, 0.0D, 0.0D, 1.0D);
             tessellator.addVertexWithUV(this.width, this.top + shadowSize, 0.0D, 1.0D, 1.0D);
-            tessellator.setColorRGBA_I(0, 255);
+            tessellator.setColor2i(0, 255);
             tessellator.addVertexWithUV(this.width, this.top, 0.0D, 1.0D, 0.0D);
             tessellator.addVertexWithUV(0, this.top, 0.0D, 0.0D, 0.0D);
             tessellator.draw();
 
             tessellator.startDrawingQuads();
-            tessellator.setColorRGBA_I(0, 255);
+            tessellator.setColor2i(0, 255);
             tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0.0D, 1.0D);
             tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, 1.0D, 1.0D);
-            tessellator.setColorRGBA_I(0, 0);
+            tessellator.setColor2i(0, 0);
             tessellator.addVertexWithUV(this.width, this.bottom - shadowSize, 0.0D, 1.0D, 0.0D);
             tessellator.addVertexWithUV(0, this.bottom - shadowSize, 0.0D, 0.0D, 0.0D);
             tessellator.draw();
+            GLRenderer.popFrame();
 
-            GL11.glEnable(GL_TEXTURE_2D);
-            GL11.glShadeModel(GL_FLAT);
-            GL11.glEnable(GL_ALPHA_TEST);
-            GL11.glDisable(GL_BLEND);
+//            GL11.glShadeModel(GL_FLAT);
+//            GL11.glEnable(GL_ALPHA_TEST);
         }
 
         this.overlayBackground(this.leftWidth, this.leftWidth + SEPARATOR_WIDTH, this.top, this.bottom);
@@ -291,9 +292,7 @@ public class ScreenPaged
 
         if (scrollBarHeightPercent > 1.0f) return;
 
-        glDisable(GL_TEXTURE_2D);
-
-        final int scrollBarX = this.width - 6 - rightOffset;
+        final int scrollBarX = this.width - 6 - this.rightOffset;
 
         int scrollBarHeightPx = (int) (scrollBarHeightPercent * this.rightScrollRegionHeight);
         if (scrollBarHeightPx < 32) {
@@ -304,18 +303,18 @@ public class ScreenPaged
 
         final int scrollBarY = (int) (this.top + (this.rightScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
 
-        final @NotNull Tessellator t = Tessellator.instance;
-
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        final @NotNull TessellatorGeneral t = GLRenderer.getTessellator();
         t.startDrawingQuads();
-        t.setColorOpaque(0, 0, 0);
+        t.setColorOpaque3i(0, 0, 0);
         t.drawRectangle(scrollBarX, this.top, 6, this.rightScrollRegionHeight);
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(scrollBarX, scrollBarY, 6, scrollBarHeightPx);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(scrollBarX + 1, scrollBarY, 5, scrollBarHeightPx - 1);
         t.draw();
-
-        glEnable(GL_TEXTURE_2D);
+        GLRenderer.popFrame();
 
         if (this.clickX != null && this.clickY != null) {
             if (this.clickX >= scrollBarX && this.clickY >= this.top && this.clickX <= scrollBarX + 6 && this.clickY < this.bottom) {
@@ -336,8 +335,6 @@ public class ScreenPaged
 
         if (scrollBarHeightPercent > 1.0f) return;
 
-        glDisable(GL_TEXTURE_2D);
-
         final int scrollBarX = this.leftWidth - 6;
 
         int scrollBarHeightPx = (int) (scrollBarHeightPercent * this.leftScrollRegionHeight);
@@ -349,18 +346,19 @@ public class ScreenPaged
 
         final int scrollBarY = (int) (this.top + (this.leftScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
 
-        final @NotNull Tessellator t = Tessellator.instance;
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        final @NotNull TessellatorGeneral t = GLRenderer.getTessellator();
 
         t.startDrawingQuads();
-        t.setColorOpaque(0, 0, 0);
+        t.setColorOpaque3i(0, 0, 0);
         t.drawRectangle(scrollBarX, this.top, 6, this.leftScrollRegionHeight);
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(scrollBarX, scrollBarY, 6, scrollBarHeightPx);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(scrollBarX + 1, scrollBarY, 5, scrollBarHeightPx - 1);
         t.draw();
-
-        glEnable(GL_TEXTURE_2D);
+        GLRenderer.popFrame();
 
         if (this.clickX != null && this.clickY != null) {
             if (this.clickX >= scrollBarX && this.clickY >= this.top && this.clickX <= scrollBarX + 6 && this.clickY < this.bottom) {
@@ -447,12 +445,12 @@ public class ScreenPaged
         super.renderBackground();
 
         if (this.mc.currentWorld == null) {
-            final @NotNull Tessellator tessellator = Tessellator.instance;
+            final @NotNull TessellatorGeneral tessellator = GLRenderer.getTessellator();
             this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
             final float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x202020);
+            tessellator.setColorOpaque1i(0x202020);
 
             tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0, (float) (this.bottom + (int) this.rightScrollAmount) / scale);
             tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, (float) this.width / scale, (float) (this.bottom + (int) this.rightScrollAmount) / scale);
@@ -474,15 +472,15 @@ public class ScreenPaged
 
     protected void overlayBackground(final int minX, final int maxX, final int minY, final int maxY) {
         if (this.mc.currentWorld == null) {
-            final @NotNull Tessellator tessellator = Tessellator.instance;
+            final @NotNull TessellatorGeneral tessellator = GLRenderer.getTessellator();
             this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
             final float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x404040);
+            tessellator.setColorOpaque1i(0x404040);
             tessellator.addVertexWithUV(minX, maxY, 0.0D, (float) minX / scale, (float) maxY / scale);
             tessellator.addVertexWithUV(maxX, maxY, 0.0D, (float) maxX / scale, (float) maxY / scale);
-            tessellator.setColorOpaque_I(0x404040);
+            tessellator.setColorOpaque1i(0x404040);
             tessellator.addVertexWithUV(maxX, minY, 0.0D, (float) maxX / scale, (float) minY / scale);
             tessellator.addVertexWithUV(minX, minY, 0.0D, (float) minX / scale, (float) minY / scale);
             tessellator.draw();
diff --git a/game/client/src/main/java/net/minecraft/client/gui/popup/LabelComponent.java b/game/client/src/main/java/net/minecraft/client/gui/popup/LabelComponent.java
index 51724cd09..50072f4f3 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/popup/LabelComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/popup/LabelComponent.java
@@ -2,7 +2,6 @@ package net.minecraft.client.gui.popup;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
 import org.jetbrains.annotations.NotNull;
 
 public class LabelComponent
@@ -26,6 +25,6 @@ public class LabelComponent
     @Override
     public void render(final int x, final int y, final int mouseX, final int mouseY) {
         final int middle = (x - PopupScreen.HORIZONTAL_MARGIN) + this.getWidth() / 2;
-        this.fontRenderer.renderCentered(Tessellator.instance, this.text, middle, y).setShadow().setColor(this.color).call();
+        this.fontRenderer.renderCentered(this.text, middle, y).setShadow().setColor(this.color).call();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/popup/ListComponent.java b/game/client/src/main/java/net/minecraft/client/gui/popup/ListComponent.java
index 1a4d1c1ec..1367f34a7 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/popup/ListComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/popup/ListComponent.java
@@ -1,12 +1,13 @@
 package net.minecraft.client.gui.popup;
 
 import net.minecraft.client.render.Scissor;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.sound.SoundCategory;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ButtonElement;
@@ -100,13 +101,13 @@ public class ListComponent
             if (wheel != 0.0f)
                 this.scroll(wheel / -12.0f);
         }
-
-        GL11.glDisable(GL11.GL_TEXTURE_2D);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
         this.drawBackground(x, y);
         this.drawScrollbar(x, y, mouseY);
 
         Scissor.enable(x + 1, y + 1, this.getWidth() - 2, this.getHeight() - 2);
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
+        GLRenderer.popFrame();
 
         // Draw buttons
         for (int i = 0; i < this.buttons.length; i++) {
@@ -200,16 +201,16 @@ public class ListComponent
     }
 
     private void drawBackground(final int x, final int y) {
-        final @NotNull Tessellator tessellator = Tessellator.instance;
+        final @NotNull TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0xA0A0A0);
+        tessellator.setColorOpaque1i(0xA0A0A0);
         tessellator.addVertex(x, y + this.height, 0.0D);
         tessellator.addVertex(x + this.getWidth(), y + this.height, 0.0D);
         tessellator.addVertex(x + this.getWidth(), y, 0.0D);
         tessellator.addVertex(x, y, 0.0D);
         tessellator.draw();
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0x000000);
+        tessellator.setColorOpaque1i(0x000000);
         tessellator.addVertex(x + 1, y + this.height - 1, 0.0D);
         tessellator.addVertex(x + this.getWidth() - 1, y + this.height - 1, 0.0D);
         tessellator.addVertex(x + this.getWidth() - 1, y + 1, 0.0D);
@@ -238,12 +239,12 @@ public class ListComponent
         this.scrollbarY = y + 1 + (int) (this.scrollAmount * scrollbarDelta);
         this.scrollbarX = x + this.getWidth() - 1 - 6;
 
-        final Tessellator t = Tessellator.instance;
+        final TessellatorGeneral t = GLRenderer.getTessellator();
 
         t.startDrawingQuads();
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(this.scrollbarX, this.scrollbarY, 6, this.scrollbarHeight);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(this.scrollbarX, this.scrollbarY, 5, this.scrollbarHeight - 1);
         t.draw();
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/popup/MessageBoxComponent.java b/game/client/src/main/java/net/minecraft/client/gui/popup/MessageBoxComponent.java
index 22eba8002..1766d8fca 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/popup/MessageBoxComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/popup/MessageBoxComponent.java
@@ -2,12 +2,13 @@ package net.minecraft.client.gui.popup;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.Scissor;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.net.command.TextFormatting;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.Arrays;
@@ -110,16 +111,17 @@ public class MessageBoxComponent
                 this.scroll(wheel / -12.0f);
         }
 
-        GL11.glDisable(GL11.GL_TEXTURE_2D);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
         this.drawBackground(x, y);
         this.drawScrollbar(x, y, mouseX, mouseY);
 
         Scissor.enable(x + 1, y + 1, this.getWidth() - 2, this.getHeight() - 2);
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
+        GLRenderer.popFrame();
 
         // Draw lines
         for (int i = 0; i < this.lines.size(); i++) {
-            this.minecraft.font.render(Tessellator.instance, this.lines.get(i), x + 4, (y + 4) + (i * 12) - this.getScrollPixels()).setShadow().call();
+            this.minecraft.font.render(this.lines.get(i), x + 4, (y + 4) + (i * 12) - this.getScrollPixels()).setShadow().call();
         }
 
         Scissor.disable();
@@ -159,16 +161,16 @@ public class MessageBoxComponent
     }
 
     private void drawBackground(final int x, final int y) {
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0xA0A0A0);
+        tessellator.setColorOpaque1i(0xA0A0A0);
         tessellator.addVertex(x, y + this.height, 0.0D);
         tessellator.addVertex(x + this.getWidth(), y + this.height, 0.0D);
         tessellator.addVertex(x + this.getWidth(), y, 0.0D);
         tessellator.addVertex(x, y, 0.0D);
         tessellator.draw();
         tessellator.startDrawingQuads();
-        tessellator.setColorOpaque_I(0x000000);
+        tessellator.setColorOpaque1i(0x000000);
         tessellator.addVertex(x + 1, y + this.height - 1, 0.0D);
         tessellator.addVertex(x + this.getWidth() - 1, y + this.height - 1, 0.0D);
         tessellator.addVertex(x + this.getWidth() - 1, y + 1, 0.0D);
@@ -192,12 +194,12 @@ public class MessageBoxComponent
         this.scrollbarY = y + 1 + (int) (this.scrollAmount * scrollbarDelta);
         this.scrollbarX = x + this.getWidth() - 1 - 6;
 
-        final @NotNull Tessellator t = Tessellator.instance;
+        final @NotNull TessellatorGeneral t = GLRenderer.getTessellator();
 
         t.startDrawingQuads();
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(this.scrollbarX, this.scrollbarY, 6, this.scrollbarHeight);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(this.scrollbarX, this.scrollbarY, 5, this.scrollbarHeight - 1);
         t.draw();
 
diff --git a/game/client/src/main/java/net/minecraft/client/gui/popup/PopupScreen.java b/game/client/src/main/java/net/minecraft/client/gui/popup/PopupScreen.java
index c6af3e112..d6ba8acd5 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/popup/PopupScreen.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/popup/PopupScreen.java
@@ -2,11 +2,11 @@ package net.minecraft.client.gui.popup;
 
 import it.unimi.dsi.fastutil.ints.IntIntPair;
 import net.minecraft.client.gui.Screen;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
-import org.lwjgl.opengl.GL11;
 
 import java.util.*;
 
@@ -165,10 +165,10 @@ public final class PopupScreen
         final int popupX = this.width / 2 - this.popupWidth / 2;
         final int popupY = this.height / 2 - this.popupHeight / 2;
 
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_FOG);
-        final @NotNull Tessellator tessellator = Tessellator.instance;
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.globalSetLightEnabled(false);
+//        GL11.glDisable(GL11.GL_FOG);
+        final @NotNull TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
 
         if (this.backgroundColor == null) {
             final int color = this.mc.gameSettings.guiBackgroundColor.value.getARGB();
@@ -179,11 +179,10 @@ public final class PopupScreen
 
         this.drawRectWidthHeight(popupX - 1, popupY - 1, this.popupWidth + 2, this.popupHeight + 2, 0xFFA0A0A0);
 
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
         final float f = 32F;
         tessellator.startDrawingQuads();
         this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-        tessellator.setColorOpaque_I(0x404040);
+        tessellator.setColorOpaque1i(0x404040);
         tessellator.addVertexWithUV(popupX, popupY + this.popupHeight, 0.0D, 0.0D, (float) this.popupHeight / f);
         tessellator.addVertexWithUV(popupX + this.popupWidth, popupY + this.popupHeight, 0.0D, (float) this.popupWidth / f, (float) this.popupHeight / f);
         tessellator.addVertexWithUV(popupX + this.popupWidth, popupY, 0.0D, (float) this.popupWidth / f, 0);
diff --git a/game/client/src/main/java/net/minecraft/client/gui/server/ScreenSelectServer.java b/game/client/src/main/java/net/minecraft/client/gui/server/ScreenSelectServer.java
index ee93d2583..50e09f2db 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/server/ScreenSelectServer.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/server/ScreenSelectServer.java
@@ -10,7 +10,9 @@ import net.minecraft.client.gui.paged.ScreenPaged;
 import net.minecraft.client.gui.popup.PopupBuilder;
 import net.minecraft.client.gui.popup.PopupScreen;
 import net.minecraft.client.render.Scissor;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.client.render.texture.TextureBuffered;
 import net.minecraft.core.Global;
@@ -23,7 +25,6 @@ import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
 
 import java.text.DateFormat;
 import java.text.SimpleDateFormat;
@@ -31,20 +32,18 @@ import java.time.Instant;
 import java.util.Date;
 import java.util.UUID;
 
-import static org.lwjgl.opengl.GL11.GL_TEXTURE_2D;
-import static org.lwjgl.opengl.GL11.glDisable;
-import static org.lwjgl.opengl.GL11.glEnable;
-
 public class ScreenSelectServer extends ScreenPaged {
     public static final Texture defaultIcon = Minecraft.getMinecraft().textureManager.loadTexture("/assets/minecraft/textures/gui/unknown_server.png");
     public static final @NotNull PageRegistry CREATE_WORLD_PAGES = new PageRegistry();
     private static final ItemStack MAP = Items.MAP.getDefaultStack();
+
     static {
         MAP.getData().putBoolean("initialized", true);
     }
+
     public static final @NotNull DateFormat timeFormatter = new SimpleDateFormat();
     public static final @NotNull Page PAGE_FAVORITES = CREATE_WORLD_PAGES.register(new Page("gui.select_server.page.favorites.title", Items.FLAG.getDefaultStack()));
-//    public static final @NotNull Page PAGE_INTERNET = CREATE_WORLD_PAGES.register(new Page("gui.select_server.page.internet.title", MAP));
+    //    public static final @NotNull Page PAGE_INTERNET = CREATE_WORLD_PAGES.register(new Page("gui.select_server.page.internet.title", MAP));
     public static final @NotNull Page PAGE_HISTORY = CREATE_WORLD_PAGES.register(new Page("gui.select_server.page.history.title", Items.BOOK.getDefaultStack()));
     public static final @NotNull Page PAGE_LAN = CREATE_WORLD_PAGES.register(new Page("gui.select_server.page.lan.title", Items.DOOR_OAK.getDefaultStack()));
     public static final @NotNull Page PAGE_DIRECT_CONNECT = CREATE_WORLD_PAGES.register(new Page("gui.select_server.page.direct_connect.title", Items.AMMO_ARROW_GOLD.getDefaultStack()));
@@ -56,7 +55,7 @@ public class ScreenSelectServer extends ScreenPaged {
     public @Nullable ServerEntry selectedEntry = null;
 
     public ButtonElement buttonJoin;
-//    public ButtonElement buttonDirectConnect;
+    //    public ButtonElement buttonDirectConnect;
     public ButtonElement buttonAddServer;
     public ButtonElement buttonEdit;
     public ButtonElement buttonDelete;
@@ -73,7 +72,7 @@ public class ScreenSelectServer extends ScreenPaged {
     protected float panelHeight = 100000;
 
     public ScreenSelectServer(@Nullable Screen parent) {
-        super(parent, CREATE_WORLD_PAGES, PAGE_FAVORITES, "gui.select_server.label.title", new String[] {});
+        super(parent, CREATE_WORLD_PAGES, PAGE_FAVORITES, "gui.select_server.label.title", new String[]{});
 
         this.serverManager = ServerManager.getServerManager(this);
         this.listenerThread = new ServerListenerThread(this);
@@ -101,40 +100,40 @@ public class ScreenSelectServer extends ScreenPaged {
         PAGE_DIRECT_CONNECT.clearComponents();
         PAGE_DIRECT_CONNECT.withComponent(new SeverDirectConnectComponent(this));
 
-        serverManager.getFavorites().forEach(e -> PAGE_FAVORITES.withComponent(new ServerEntryComponent(this, e)));
-        serverManager.getLan().forEach(e -> PAGE_LAN.withComponent(new ServerEntryComponent(this, e)));
-        serverManager.getHistory().forEach(e -> PAGE_HISTORY.withComponent(new ServerEntryComponent(this, e)));
+        this.serverManager.getFavorites().forEach(e -> PAGE_FAVORITES.withComponent(new ServerEntryComponent(this, e)));
+        this.serverManager.getLan().forEach(e -> PAGE_LAN.withComponent(new ServerEntryComponent(this, e)));
+        this.serverManager.getHistory().forEach(e -> PAGE_HISTORY.withComponent(new ServerEntryComponent(this, e)));
 //        serverManager.getInternet().forEach(e -> PAGE_INTERNET.withComponent(new ServerEntryComponent(this, e)));
     }
 
     public void setupButtons() {
-        if (selectedPage != PAGE_DIRECT_CONNECT) {
-            this.rightOffset = (int) (width * 0.25f);
+        if (this.selectedPage != PAGE_DIRECT_CONNECT) {
+            this.rightOffset = (int) (this.width * 0.25f);
         } else {
             this.rightOffset = 0;
         }
 
-        buttons.clear();
+        this.buttons.clear();
         I18n trans = I18n.getInstance();
 
-        int x1 = width / 2 - 154;
-        int y1 = height - 52;
-        int y2 = height - 24;
+        int x1 = this.width / 2 - 154;
+        int y1 = this.height - 52;
+        int y2 = this.height - 24;
 
-        int w = width - rightOffset - leftWidth;
+        int w = this.width - this.rightOffset - this.leftWidth;
 
-        buttonJoin = add(new ButtonElement(0, width - rightOffset + 10, bottom - 22 * 3, rightOffset - 12, 20, trans.translateKey("gui.select_server.button.join_server")));
-        buttonEdit = add(new ButtonElement(3, width - rightOffset + 10, bottom - 22 * 2, rightOffset - 12, 20, trans.translateKey("gui.select_server.button.edit")));
-        buttonDelete = add(new ButtonElement(4, width - rightOffset + 10, bottom - 22, rightOffset - 12, 20, trans.translateKey("gui.select_server.button.delete")));
+        this.buttonJoin = add(new ButtonElement(0, this.width - this.rightOffset + 10, this.bottom - 22 * 3, this.rightOffset - 12, 20, trans.translateKey("gui.select_server.button.join_server")));
+        this.buttonEdit = add(new ButtonElement(3, this.width - this.rightOffset + 10, this.bottom - 22 * 2, this.rightOffset - 12, 20, trans.translateKey("gui.select_server.button.edit")));
+        this.buttonDelete = add(new ButtonElement(4, this.width - this.rightOffset + 10, this.bottom - 22, this.rightOffset - 12, 20, trans.translateKey("gui.select_server.button.delete")));
 
-        buttonAddServer = add(new ButtonElement(2, x1 + 208, y2, 100, 20, trans.translateKey("gui.select_server.button.add_server")));
-        buttonRefresh = add(new ButtonElement(5, x1 + 104, y2, 100, 20, trans.translateKey("gui.select_server.button.refresh")));
-        buttonCancel = add(new ButtonElement(6, x1, y2, 100, 20, trans.translateKey("gui.select_server.button.cancel")));
+        this.buttonAddServer = add(new ButtonElement(2, x1 + 208, y2, 100, 20, trans.translateKey("gui.select_server.button.add_server")));
+        this.buttonRefresh = add(new ButtonElement(5, x1 + 104, y2, 100, 20, trans.translateKey("gui.select_server.button.refresh")));
+        this.buttonCancel = add(new ButtonElement(6, x1, y2, 100, 20, trans.translateKey("gui.select_server.button.cancel")));
 
-        if (selectedPage == PAGE_DIRECT_CONNECT) {
-            buttonAddServer.enabled = buttonAddServer.visible = false;
-            buttonRefresh.enabled = buttonRefresh.visible = false;
-            buttonCancel.xPosition = (width - 100) / 2;
+        if (this.selectedPage == PAGE_DIRECT_CONNECT) {
+            this.buttonAddServer.enabled = this.buttonAddServer.visible = false;
+            this.buttonRefresh.enabled = this.buttonRefresh.visible = false;
+            this.buttonCancel.xPosition = (this.width - 100) / 2;
         }
 
         this.panelScrollRegionHeight = this.buttonJoin.yPosition - this.top;
@@ -142,7 +141,7 @@ public class ScreenSelectServer extends ScreenPaged {
 
     @Override
     protected void buttonClicked(@NotNull ButtonElement button) {
-        if (button == buttonCancel) {
+        if (button == this.buttonCancel) {
             this.mc.displayScreen(this.getParentScreen());
             freeResources();
         } /*else if (button == buttonDirectConnect) {
@@ -167,7 +166,7 @@ public class ScreenSelectServer extends ScreenPaged {
                 })
                 .build();
             this.mc.displayScreen(directConnect);
-        }*/ else if (button == buttonAddServer) {
+        }*/ else if (button == this.buttonAddServer) {
             PopupScreen add = new PopupBuilder(this, 160)
                 .withLabel("gui.select_server.popup.add.prompt.name")
                 .withTextField("name", "")
@@ -187,15 +186,15 @@ public class ScreenSelectServer extends ScreenPaged {
                         entry.showIp = (Boolean) results.get("showIp");
                         entry.dirty = true;
                         entry.requestIcon = true;
-                        serverManager.addEntry(entry);
-                        serverManager.addFavorite(entry);
+                        this.serverManager.addEntry(entry);
+                        this.serverManager.addFavorite(entry);
                         refreshPages();
                     }
                 })
                 .build();
             this.mc.displayScreen(add);
-        } else if (button == buttonEdit && selectedEntry != null) {
-            ServerEntry tEntry = selectedEntry;
+        } else if (button == this.buttonEdit && this.selectedEntry != null) {
+            ServerEntry tEntry = this.selectedEntry;
             PopupScreen edit = new PopupBuilder(this, 160)
                 .withLabel("gui.select_server.popup.edit.prompt.name")
                 .withTextField("name", tEntry.overrideName == null ? "" : tEntry.overrideName)
@@ -221,16 +220,16 @@ public class ScreenSelectServer extends ScreenPaged {
                 })
                 .build();
             this.mc.displayScreen(edit);
-        } else if (button == buttonJoin) {
-            if (selectedEntry != null) {
-                needToRefreshPages = true;
-                serverManager.onJoined(selectedEntry);
-                joinServer(selectedEntry.getServerAddress());
+        } else if (button == this.buttonJoin) {
+            if (this.selectedEntry != null) {
+                this.needToRefreshPages = true;
+                this.serverManager.onJoined(this.selectedEntry);
+                joinServer(this.selectedEntry.getServerAddress());
             }
-        } else if (button == buttonRefresh) {
+        } else if (button == this.buttonRefresh) {
             refresh();
-        } else if (button == buttonDelete && selectedEntry != null) {
-            deleteEntry(selectedEntry);
+        } else if (button == this.buttonDelete && this.selectedEntry != null) {
+            deleteEntry(this.selectedEntry);
         }
     }
 
@@ -249,55 +248,55 @@ public class ScreenSelectServer extends ScreenPaged {
     }
 
     private int getTotalPanelHeight() {
-        return (int) panelHeight;
+        return (int) this.panelHeight;
     }
 
     public void joinServer(@NotNull ServerAddress address) {
-        mc.gameSettings.lastServer.value = address.toString().replaceAll(":", "_");
-        mc.gameSettings.saveOptions();
-        mc.displayScreen(new ScreenConnecting(mc, address.getIP(), address.getPort()));
+        this.mc.gameSettings.lastServer.value = address.toString().replaceAll(":", "_");
+        this.mc.gameSettings.saveOptions();
+        this.mc.displayScreen(new ScreenConnecting(this.mc, address.getIP(), address.getPort()));
         freeResources();
     }
 
     public void freeResources() { // Wonder how long until this not being called at the right time causes a memory leak :)
-        serverManager.freeResources();
-        listenerThread.keepAlive = false;
+        this.serverManager.freeResources();
+        this.listenerThread.keepAlive = false;
     }
 
     public void refresh() {
-        serverManager.idToEntryLock.lock();
+        this.serverManager.idToEntryLock.lock();
         try {
-            serverManager.idToEntryMap.forEach((uuid, entry) -> entry.dirty = true);
+            this.serverManager.idToEntryMap.forEach((uuid, entry) -> entry.dirty = true);
         } finally {
-            serverManager.idToEntryLock.unlock();
+            this.serverManager.idToEntryLock.unlock();
         }
     }
 
     @Override
     public void tick() {
-        serverManager.idToEntryLock.lock();
+        this.serverManager.idToEntryLock.lock();
         try {
-            serverManager.idToEntryMap.values().stream().filter(entry -> entry.queuedIcon != null).forEach(entry -> {
+            this.serverManager.idToEntryMap.values().stream().filter(entry -> entry.queuedIcon != null).forEach(entry -> {
                 entry.icon = new TextureBuffered(entry.queuedIcon, false, false, false);
                 entry.queuedIcon = null;
             });
         } finally {
-            serverManager.idToEntryLock.unlock();
+            this.serverManager.idToEntryLock.unlock();
         }
     }
 
     public void deleteEntry(@NotNull ServerEntry entry) {
-        if (selectedPage == PAGE_FAVORITES) {
-            serverManager.removeFavorite(entry);
-        } else if (selectedPage == PAGE_HISTORY) {
-            serverManager.removeHistory(entry);
+        if (this.selectedPage == PAGE_FAVORITES) {
+            this.serverManager.removeFavorite(entry);
+        } else if (this.selectedPage == PAGE_HISTORY) {
+            this.serverManager.removeHistory(entry);
         }
         refreshPages();
     }
 
     @Override
     public void handleScroll(int mx, int my, float partialTick) {
-        if (mx > this.width - rightOffset && mx < this.width) {
+        if (mx > this.width - this.rightOffset && mx < this.width) {
             if (Keyboard.isKeyDown(Keyboard.KEY_LCONTROL) || Keyboard.isKeyDown(Keyboard.KEY_RCONTROL)) {
                 this.scrollPanel(Mouse.getDWheel() / -0.01f);
             } else {
@@ -311,23 +310,23 @@ public class ScreenSelectServer extends ScreenPaged {
 
     @Override
     public void render(int mx, int my, float renderPartialTicks) {
-        if (addressToJoin != null) {
-            joinServer(addressToJoin);
+        if (this.addressToJoin != null) {
+            joinServer(this.addressToJoin);
             return;
         }
-        if (needToRefreshPages) {
-            needToRefreshPages = false;
+        if (this.needToRefreshPages) {
+            this.needToRefreshPages = false;
             refreshPages();
         }
 
-        this.buttonJoin.visible = this.buttonJoin.enabled = selectedEntry != null;
-        this.buttonEdit.visible = this.buttonEdit.enabled = selectedEntry != null;
-        this.buttonDelete.visible = this.buttonDelete.enabled = selectedEntry != null;
+        this.buttonJoin.visible = this.buttonJoin.enabled = this.selectedEntry != null;
+        this.buttonEdit.visible = this.buttonEdit.enabled = this.selectedEntry != null;
+        this.buttonDelete.visible = this.buttonDelete.enabled = this.selectedEntry != null;
 
         super.render(mx, my, renderPartialTicks);
 
-        this.overlayBackground(this.width - rightOffset, this.width - rightOffset + SEPARATOR_WIDTH, this.top, this.bottom);
-        Scissor.enable(this.width - rightOffset, this.top, rightOffset, this.buttonJoin.yPosition - this.top);
+        this.overlayBackground(this.width - this.rightOffset, this.width - this.rightOffset + SEPARATOR_WIDTH, this.top, this.bottom);
+        Scissor.enable(this.width - this.rightOffset, this.top, this.rightOffset, this.buttonJoin.yPosition - this.top);
         renderSelectedEntry(mx, my, renderPartialTicks);
         Scissor.disable();
     }
@@ -338,8 +337,6 @@ public class ScreenSelectServer extends ScreenPaged {
 
         if (scrollBarHeightPercent > 1.0f) return;
 
-        glDisable(GL_TEXTURE_2D);
-
         final int scrollBarX = this.width - 6;
 
         int scrollBarHeightPx = (int) (scrollBarHeightPercent * this.panelScrollRegionHeight);
@@ -351,18 +348,19 @@ public class ScreenSelectServer extends ScreenPaged {
 
         final int scrollBarY = (int) (this.top + (this.panelScrollRegionHeight - scrollBarHeightPx) * scrollPercent);
 
-        final @NotNull Tessellator t = Tessellator.instance;
 
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        final @NotNull TessellatorGeneral t = GLRenderer.getTessellator();
         t.startDrawingQuads();
-        t.setColorOpaque(0, 0, 0);
+        t.setColorOpaque3i(0, 0, 0);
         t.drawRectangle(scrollBarX, this.top, 6, this.panelScrollRegionHeight);
-        t.setColorRGBA_I(0x808080, 255);
+        t.setColor2i(0x808080, 255);
         t.drawRectangle(scrollBarX, scrollBarY, 6, scrollBarHeightPx);
-        t.setColorRGBA_I(0xc0c0c0, 255);
+        t.setColor2i(0xc0c0c0, 255);
         t.drawRectangle(scrollBarX + 1, scrollBarY, 5, scrollBarHeightPx - 1);
         t.draw();
-
-        glEnable(GL_TEXTURE_2D);
+        GLRenderer.popFrame();
 
         if (this.clickX != null && this.clickY != null) {
             if (this.clickX >= scrollBarX && this.clickY >= this.top && this.clickX <= scrollBarX + 6 && this.clickY < this.bottom) {
@@ -378,50 +376,50 @@ public class ScreenSelectServer extends ScreenPaged {
     }
 
     public void renderSelectedEntry(int mx, int my, float partialTick) {
-        if (selectedEntry != null) {
+        if (this.selectedEntry != null) {
             int totalPanelHeight = getTotalPanelHeight();
             final float scrollBarHeightPercent = (float) this.panelScrollRegionHeight / totalPanelHeight;
 
-            Tessellator t = Tessellator.instance;
-            int minX = this.width - rightOffset + SEPARATOR_WIDTH;
+            TessellatorGeneral t = GLRenderer.getTessellator();
+            int minX = this.width - this.rightOffset + SEPARATOR_WIDTH;
             int maxX = this.width;
-            int y = (int) (top + 4 - panelScrollAmount);
+            int y = (int) (this.top + 4 - this.panelScrollAmount);
             int startY = y;
-            if (selectedEntry.icon != null) {
-                selectedEntry.icon.bind();
+            if (this.selectedEntry.icon != null) {
+                this.selectedEntry.icon.bind();
                 t.startDrawingQuads();
-                t.drawRectangleWithUV(minX + (maxX - minX - 64)/2, y, 64, 64, 0, 0, 1, 1);
+                t.drawRectangleWithUV(minX + (maxX - minX - 64) / 2, y, 64, 64, 0, 0, 1, 1);
                 y += 64 + 2;
                 t.draw();
             }
 
             stringBuilder.setLength(0);
-            if (selectedEntry.showIp) {
-                stringBuilder.append(TextFormatting.GRAY).append(selectedEntry.getServerAddress().getIP()).append(":").append(selectedEntry.getServerAddress().getPort()).append(TextFormatting.RESET).append("\n");
+            if (this.selectedEntry.showIp) {
+                stringBuilder.append(TextFormatting.GRAY).append(this.selectedEntry.getServerAddress().getIP()).append(":").append(this.selectedEntry.getServerAddress().getPort()).append(TextFormatting.RESET).append("\n");
             }
 //            builder.append(TextFormatting.GRAY);
-            stringBuilder.append(selectedEntry.getName("Unknown"));
-            if (selectedEntry.version != null) {
+            stringBuilder.append(this.selectedEntry.getName("Unknown"));
+            if (this.selectedEntry.version != null) {
                 stringBuilder.append(TextFormatting.RESET).append("\n\n");
-                stringBuilder.append(selectedEntry.protocolVersion == Global.MP_PROTOCOL_VERSION ? TextFormatting.YELLOW : TextFormatting.RED).append(selectedEntry.version);
+                stringBuilder.append(this.selectedEntry.protocolVersion == Global.MP_PROTOCOL_VERSION ? TextFormatting.YELLOW : TextFormatting.RED).append(this.selectedEntry.version);
             }
             stringBuilder.append(TextFormatting.RESET).append("\n\n");
-            if (selectedEntry.motd != null) {
-                stringBuilder.append(selectedEntry.motd);
+            if (this.selectedEntry.motd != null) {
+                stringBuilder.append(this.selectedEntry.motd);
             }
-            if (!selectedEntry.players.isEmpty()) {
+            if (!this.selectedEntry.players.isEmpty()) {
                 stringBuilder.append(TextFormatting.RESET).append("\n\n");
                 stringBuilder.append("Players:\n");
-                for (int i = 0; i < selectedEntry.players.size(); i++) {
-                    stringBuilder.append(" - ").append(TextFormatting.GRAY).append(selectedEntry.players.get(i)).append(TextFormatting.RESET).append("\n");
+                for (int i = 0; i < this.selectedEntry.players.size(); i++) {
+                    stringBuilder.append(" - ").append(TextFormatting.GRAY).append(this.selectedEntry.players.get(i)).append(TextFormatting.RESET).append("\n");
                 }
             }
-            if (selectedEntry.lastPlayedTime >= 0) {
+            if (this.selectedEntry.lastPlayedTime >= 0) {
                 stringBuilder.append(TextFormatting.RESET).append("\n\n");
-                stringBuilder.append("Last Played: ").append(timeFormatter.format(Date.from(Instant.ofEpochMilli(selectedEntry.lastPlayedTime))));
+                stringBuilder.append("Last Played: ").append(timeFormatter.format(Date.from(Instant.ofEpochMilli(this.selectedEntry.lastPlayedTime))));
             }
-            mc.font.renderWidthConstrained(t, stringBuilder, minX + 2, y, maxX - minX - 4 - ((scrollBarHeightPercent > 1.0f) ? 0 : 6)).setShadow().call();
-            panelHeight = (float) (mc.font.getLastEndingY() - startY) + 8;
+            this.mc.font.renderWidthConstrained(stringBuilder, minX + 2, y, maxX - minX - 4 - ((scrollBarHeightPercent > 1.0f) ? 0 : 6)).setShadow().call();
+            this.panelHeight = (float) (this.mc.font.getLastEndingY() - startY) + 8;
 
             drawPanelScrollBar(mx, my);
         }
@@ -444,22 +442,22 @@ public class ScreenSelectServer extends ScreenPaged {
     public void renderBackground() {
         if (this.mc.currentWorld == null) {
             this.renderTexturedBackground();
-            final @NotNull Tessellator tessellator = Tessellator.instance;
+            final @NotNull TessellatorGeneral tessellator = GLRenderer.getTessellator();
             this.mc.textureManager.loadTexture("/assets/minecraft/textures/gui/background.png").bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
             final float scale = 32F;
             tessellator.startDrawingQuads();
-            tessellator.setColorOpaque_I(0x202020);
+            tessellator.setColorOpaque1i(0x202020);
 
             tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0, (float) (this.bottom + (int) this.rightScrollAmount) / scale);
-            tessellator.addVertexWithUV(this.width - rightOffset, this.bottom, 0.0D, (float) (this.width - rightOffset) / scale, (this.bottom + this.rightScrollAmount) / scale);
-            tessellator.addVertexWithUV(this.width - rightOffset, this.top, 0.0D, (float) (this.width - rightOffset) / scale, (this.top + this.rightScrollAmount) / scale);
+            tessellator.addVertexWithUV(this.width - this.rightOffset, this.bottom, 0.0D, (float) (this.width - this.rightOffset) / scale, (this.bottom + this.rightScrollAmount) / scale);
+            tessellator.addVertexWithUV(this.width - this.rightOffset, this.top, 0.0D, (float) (this.width - this.rightOffset) / scale, (this.top + this.rightScrollAmount) / scale);
             tessellator.addVertexWithUV(0, this.top, 0.0D, 0, (float) (this.top + (int) this.rightScrollAmount) / scale);
 
-            tessellator.addVertexWithUV(this.width - rightOffset, this.bottom, 0.0D, (this.width - rightOffset) / scale, (this.bottom + this.panelScrollAmount) / scale);
+            tessellator.addVertexWithUV(this.width - this.rightOffset, this.bottom, 0.0D, (this.width - this.rightOffset) / scale, (this.bottom + this.panelScrollAmount) / scale);
             tessellator.addVertexWithUV(this.width, this.bottom, 0.0D, (float) (this.width) / scale, (this.bottom + this.panelScrollAmount) / scale);
             tessellator.addVertexWithUV(this.width, this.top, 0.0D, (float) (this.width) / scale, (this.top + this.panelScrollAmount) / scale);
-            tessellator.addVertexWithUV(this.width - rightOffset, this.top, 0.0D, (this.width - rightOffset) / scale, (this.top + this.panelScrollAmount) / scale);
+            tessellator.addVertexWithUV(this.width - this.rightOffset, this.top, 0.0D, (this.width - this.rightOffset) / scale, (this.top + this.panelScrollAmount) / scale);
 
             tessellator.addVertexWithUV(0, this.bottom, 0.0D, 0, (this.bottom + this.leftScrollAmount) / scale);
             tessellator.addVertexWithUV(this.leftWidth, this.bottom, 0.0D, (float) this.leftWidth / scale, (this.bottom + this.leftScrollAmount) / scale);
@@ -479,7 +477,7 @@ public class ScreenSelectServer extends ScreenPaged {
     @Override
     public void removed() {
         super.removed();
-        ServerManager.saveServerManager(serverManager);
+        ServerManager.saveServerManager(this.serverManager);
     }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/server/ServerEntry.java b/game/client/src/main/java/net/minecraft/client/gui/server/ServerEntry.java
index aa505df8b..288271d77 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/server/ServerEntry.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/server/ServerEntry.java
@@ -45,22 +45,22 @@ public class ServerEntry {
     }
 
     public @NotNull String getName(@NotNull String defaultName) {
-        if (overrideName != null && !overrideName.isBlank()) return overrideName;
-        if (baseName != null && !baseName.isBlank()) return baseName;
+        if (this.overrideName != null && !this.overrideName.isBlank()) return this.overrideName;
+        if (this.baseName != null && !this.baseName.isBlank()) return this.baseName;
         return defaultName;
     }
 
     public void free() {
-        if (icon != null && icon != ScreenSelectServer.defaultIcon) {
-            icon.delete();
-            icon = null;
+        if (this.icon != null && this.icon != ScreenSelectServer.defaultIcon) {
+            this.icon.delete();
+            this.icon = null;
         }
     }
 
     public @NotNull ServerAddress getServerAddress() {
-        if (addressResolved == null) {
+        if (this.addressResolved == null) {
             this.addressResolved = Objects.requireNonNull(ServerAddress.resolveServerIP(this.address));
         }
-        return addressResolved;
+        return this.addressResolved;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/server/ServerEntryComponent.java b/game/client/src/main/java/net/minecraft/client/gui/server/ServerEntryComponent.java
index 6a905276a..d2ef59c6b 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/server/ServerEntryComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/server/ServerEntryComponent.java
@@ -3,7 +3,8 @@ package net.minecraft.client.gui.server;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.paged.PageComponent;
 import net.minecraft.client.render.font.Alignment;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.Global;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.net.command.TextFormatting;
@@ -27,50 +28,50 @@ public class ServerEntryComponent implements PageComponent {
 
     @Override
     public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        Tessellator t = Tessellator.instance;
-        if (entry.icon != null) {
-            entry.icon.bind();
+        TessellatorGeneral t = GLRenderer.getTessellator();
+        if (this.entry.icon != null) {
+            this.entry.icon.bind();
             t.startDrawingQuads();
             t.drawRectangleWithUV(x + 1, y + 1, 24, 24, 0, 0, 1, 1);
             t.draw();
         }
 
-        mc.font.render(t, entry.getName("Unknown"), x + 24 + 3, y + 2).setShadow().call();
-        if (entry.motd != null) {
+        this.mc.font.render(this.entry.getName("Unknown"), x + 24 + 3, y + 2).setShadow().call();
+        if (this.entry.motd != null) {
             stringBuilder.setLength(0);
-            stringBuilder.append(TextFormatting.GRAY).append(entry.motd);
-            stringBuilder.setLength(Math.max((width - 16), 0) / mc.font.getFont().charWidth('m'));
-            mc.font.renderWidthConstrained(t, stringBuilder, x + 24 + 3, mc.font.getLastEndingY(), width).setShadow().call();
+            stringBuilder.append(TextFormatting.GRAY).append(this.entry.motd);
+            stringBuilder.setLength(Math.max((width - 16), 0) / this.mc.font.getFont().charWidth('m'));
+            this.mc.font.renderWidthConstrained(stringBuilder, x + 24 + 3, this.mc.font.getLastEndingY(), width).setShadow().call();
         }
 
-        if (!entry.isUp) {
+        if (!this.entry.isUp) {
             stringBuilder.setLength(0);
             stringBuilder.append(I18n.getInstance().translateKey("gui.select_server.label.down"));
-            mc.font.renderWidthConstrained(t, stringBuilder, x, y + 2, width - 2).setShadow().setColor(0xFF0000).setAlignment(Alignment.RIGHT).call();
-        } else if (entry.protocolVersion != Global.MP_PROTOCOL_VERSION) {
+            this.mc.font.renderWidthConstrained(stringBuilder, x, y + 2, width - 2).setShadow().setColor(0xFF0000).setAlignment(Alignment.RIGHT).call();
+        } else if (this.entry.protocolVersion != Global.MP_PROTOCOL_VERSION) {
             stringBuilder.setLength(0);
             stringBuilder.append(I18n.getInstance().translateKey("gui.select_server.label.outdated"));
-            mc.font.renderWidthConstrained(t, stringBuilder, x, y + 2, width - 2).setShadow().setColor(0xFF0000).setAlignment(Alignment.RIGHT).call();
+            this.mc.font.renderWidthConstrained(stringBuilder, x, y + 2, width - 2).setShadow().setColor(0xFF0000).setAlignment(Alignment.RIGHT).call();
 //            stringBuilder.setLength(0);
 //            stringBuilder.append(entry.version);
 //            mc.font.renderWidthConstrained(t, stringBuilder, x, mc.font.getLastEndingY(), width - 2).setShadow().setColor(0xFF0000).setAlignment(Alignment.RIGHT).call();
-        } else if (!entry.dirty) {
+        } else if (!this.entry.dirty) {
             stringBuilder.setLength(0);
-            stringBuilder.append(entry.playerCount).append("/").append(entry.playerCap);
-            mc.font.renderWidthConstrained(t, stringBuilder, x, y + 2, width - 2).setShadow().setColor(0xFFFF00).setAlignment(Alignment.RIGHT).call();
+            stringBuilder.append(this.entry.playerCount).append("/").append(this.entry.playerCap);
+            this.mc.font.renderWidthConstrained(stringBuilder, x, y + 2, width - 2).setShadow().setColor(0xFFFF00).setAlignment(Alignment.RIGHT).call();
             stringBuilder.setLength(0);
-            stringBuilder.append(entry.ping).append(" ms");
-            mc.font.renderWidthConstrained(t, stringBuilder, x, mc.font.getLastEndingY(), width - 2).setShadow().setColor(0xFFFF00).setAlignment(Alignment.RIGHT).call();
+            stringBuilder.append(this.entry.ping).append(" ms");
+            this.mc.font.renderWidthConstrained(stringBuilder, x, this.mc.font.getLastEndingY(), width - 2).setShadow().setColor(0xFFFF00).setAlignment(Alignment.RIGHT).call();
         }
 
-        if (entry == attachedScreen.selectedEntry) {
-            attachedScreen.drawBox(x, y, x + width, y + getHeight(), 0xFFFFFFFF, 1);
+        if (this.entry == this.attachedScreen.selectedEntry) {
+            this.attachedScreen.drawBox(x, y, x + width, y + getHeight(), 0xFFFFFFFF, 1);
         }
     }
 
     @Override
     public void onMouseClick(int mouseButton, int x, int y, int width, int relativeMouseX, int relativeMouseY) {
-        attachedScreen.setSelectedEntry(entry);
+        this.attachedScreen.setSelectedEntry(this.entry);
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/gui/server/ServerListenerThread.java b/game/client/src/main/java/net/minecraft/client/gui/server/ServerListenerThread.java
index 7010e1a4c..49057feb8 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/server/ServerListenerThread.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/server/ServerListenerThread.java
@@ -12,7 +12,7 @@ import java.net.MulticastSocket;
 import java.util.HashMap;
 import java.util.Map;
 
-public class ServerListenerThread extends Thread{
+public class ServerListenerThread extends Thread {
     private static final Logger LOGGER = LogUtils.getLogger();
     public final @NotNull ScreenSelectServer attachedScreen;
     public final @NotNull ServerManager serverManager;
@@ -32,34 +32,34 @@ public class ServerListenerThread extends Thread{
         boolean multiCastAlive = false;
         InetAddress group = null;
         try {
-            multicastSocket = new MulticastSocket(4445);
+            this.multicastSocket = new MulticastSocket(4445);
             group = InetAddress.getByName("224.0.2.61");
-            multicastSocket.joinGroup(group);
+            this.multicastSocket.joinGroup(group);
             multiCastAlive = true;
         } catch (IOException e) {
             LOGGER.error("", e);
         }
-        while (keepAlive) {
+        while (this.keepAlive) {
             try {
-                serverManager.idToEntryLock.lock();
+                this.serverManager.idToEntryLock.lock();
                 try {
-                    for (ServerEntry entry : serverManager.idToEntryMap.values()) {
-                        if (entry.dirty && !pingThreads.containsKey(entry)) {
+                    for (ServerEntry entry : this.serverManager.idToEntryMap.values()) {
+                        if (entry.dirty && !this.pingThreads.containsKey(entry)) {
                             entry.dirty = false;
-                            synchronized (pingThreads) {
+                            synchronized (this.pingThreads) {
                                 ThreadPingServer threadPingServer2 = new ThreadPingServer(this, entry);
-                                pingThreads.put(entry, threadPingServer2);
+                                this.pingThreads.put(entry, threadPingServer2);
                                 threadPingServer2.start();
                             }
                         }
                     }
                 } finally {
-                    serverManager.idToEntryLock.unlock();
+                    this.serverManager.idToEntryLock.unlock();
                 }
                 if (multiCastAlive) {
                     try {
-                        DatagramPacket packet = new DatagramPacket(buf, buf.length);
-                        multicastSocket.receive(packet);
+                        DatagramPacket packet = new DatagramPacket(this.buf, this.buf.length);
+                        this.multicastSocket.receive(packet);
                         String received = new String(packet.getData(), 0, packet.getLength());
                         if ("end".equals(received)) {
                             multiCastAlive = false;
@@ -76,11 +76,11 @@ public class ServerListenerThread extends Thread{
             }
         }
         try {
-            if (group != null) multicastSocket.leaveGroup(group);
+            if (group != null) this.multicastSocket.leaveGroup(group);
         } catch (IOException e) {
             LOGGER.error("", e);
         }
-        if (multicastSocket != null) multicastSocket.close();
+        if (this.multicastSocket != null) this.multicastSocket.close();
     }
 
     public void receivedLocalServer(DatagramPacket packet, String localServerBroadcast) {
@@ -116,13 +116,13 @@ public class ServerListenerThread extends Thread{
             } catch (Exception e) {
                 return;
             }
-            serverManager.onLocalScanned(ip, portInt, motd, name);
+            this.serverManager.onLocalScanned(ip, portInt, motd, name);
         }
     }
 
     public void handleIncomingServerInfo(ServerEntry server) {
-        synchronized (pingThreads) {
-            ThreadPingServer pingServer = pingThreads.remove(server);
+        synchronized (this.pingThreads) {
+            ThreadPingServer pingServer = this.pingThreads.remove(server);
             if (pingServer != null) {
                 pingServer.interrupt();
             }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/server/ServerManager.java b/game/client/src/main/java/net/minecraft/client/gui/server/ServerManager.java
index e4a81f47e..47078dcd5 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/server/ServerManager.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/server/ServerManager.java
@@ -73,6 +73,7 @@ public class ServerManager {
     }
 
     private final @NotNull ScreenSelectServer attachedScreen;
+
     private ServerManager(@NotNull ScreenSelectServer attachedScreen, @NotNull CompoundTag compoundTag) {
         this.attachedScreen = attachedScreen;
 
@@ -102,14 +103,14 @@ public class ServerManager {
             UUID uuid = UUID.fromString(e.getKey());
             if (this.idToEntryMap.containsKey(uuid)) {
                 ServerEntry entry = this.idToEntryMap.get(uuid);
-                entry.lastPlayedTime = ((LongTag)e.getValue()).getValue();
+                entry.lastPlayedTime = ((LongTag) e.getValue()).getValue();
                 if (!this.historyMap.containsKey(entry.uuid)) {
                     this.historyMap.put(entry.uuid, entry);
                     this.history.add(entry);
                 }
             }
         }
-        history.sort((o1, o2) -> Long.compare(o2.lastPlayedTime, o1.lastPlayedTime));
+        this.history.sort((o1, o2) -> Long.compare(o2.lastPlayedTime, o1.lastPlayedTime));
 
     }
 
@@ -149,35 +150,35 @@ public class ServerManager {
     }
 
     public void addEntry(@NotNull ServerEntry entry) {
-        idToEntryLock.lock();
+        this.idToEntryLock.lock();
         try {
-            idToEntryMap.put(entry.uuid, entry);
+            this.idToEntryMap.put(entry.uuid, entry);
         } finally {
-            idToEntryLock.unlock();
+            this.idToEntryLock.unlock();
         }
     }
 
     public void addFavorite(@NotNull ServerEntry entry) {
         addEntry(entry);
-        if (!favoritesMap.containsKey(entry.uuid)) {
-            favoritesMap.put(entry.uuid, entry);
-            favorites.add(entry);
+        if (!this.favoritesMap.containsKey(entry.uuid)) {
+            this.favoritesMap.put(entry.uuid, entry);
+            this.favorites.add(entry);
         }
     }
 
     public void onJoined(@NotNull ServerEntry entry) {
         addEntry(entry);
         entry.lastPlayedTime = System.currentTimeMillis();
-        if (!historyMap.containsKey(entry.uuid)) {
-            historyMap.put(entry.uuid, entry);
-            history.add(entry);
+        if (!this.historyMap.containsKey(entry.uuid)) {
+            this.historyMap.put(entry.uuid, entry);
+            this.history.add(entry);
         }
-        history.sort((o1, o2) -> Long.compare(o2.lastPlayedTime, o1.lastPlayedTime));
+        this.history.sort((o1, o2) -> Long.compare(o2.lastPlayedTime, o1.lastPlayedTime));
     }
 
     public void onLocalScanned(@NotNull String ip, int port, @Nullable String motd, @Nullable String name) {
         ServerAddress address = ServerAddress.resolveServerIP(String.format("%s:%s", ip, port));
-        if (!lanAddressMap.containsKey(address)) {
+        if (!this.lanAddressMap.containsKey(address)) {
             ServerEntry entry = new ServerEntry(UUID.randomUUID(), String.format("%s:%s", ip, port));
             if (name == null || name.isBlank()) {
                 entry.baseName = "Lan Server";
@@ -190,58 +191,58 @@ public class ServerManager {
             entry.dirty = true;
             entry.requestIcon = true;
             addEntry(entry);
-            lan.add(entry);
-            lanMap.put(entry.uuid, entry);
-            lanAddressMap.put(address, entry);
-            attachedScreen.needToRefreshPages = true;
+            this.lan.add(entry);
+            this.lanMap.put(entry.uuid, entry);
+            this.lanAddressMap.put(address, entry);
+            this.attachedScreen.needToRefreshPages = true;
         }
     }
 
     public void removeFavorite(@NotNull ServerEntry entry) {
-        favorites.remove(entry);
-        favoritesMap.remove(entry.uuid);
+        this.favorites.remove(entry);
+        this.favoritesMap.remove(entry.uuid);
         checkValid(entry);
     }
 
     public void removeHistory(@NotNull ServerEntry entry) {
-        history.remove(entry);
-        historyMap.remove(entry.uuid);
+        this.history.remove(entry);
+        this.historyMap.remove(entry.uuid);
         checkValid(entry);
     }
 
     public void checkValid(@NotNull ServerEntry entry) {
         if (
-            !favoritesMap.containsKey(entry.uuid) &&
-            !internetMap.containsKey(entry.uuid) &&
-            !historyMap.containsKey(entry.uuid) &&
-            !lanMap.containsKey(entry.uuid)
+            !this.favoritesMap.containsKey(entry.uuid) &&
+                !this.internetMap.containsKey(entry.uuid) &&
+                !this.historyMap.containsKey(entry.uuid) &&
+                !this.lanMap.containsKey(entry.uuid)
         ) {
-            idToEntryMap.remove(entry.uuid);
+            this.idToEntryMap.remove(entry.uuid);
         }
     }
 
     public void freeResources() {
-        idToEntryLock.lock();
+        this.idToEntryLock.lock();
         try {
-            idToEntryMap.forEach((uuid, entry) -> entry.free());
+            this.idToEntryMap.forEach((uuid, entry) -> entry.free());
         } finally {
-            idToEntryLock.unlock();
+            this.idToEntryLock.unlock();
         }
     }
 
     public @NotNull Collection<ServerEntry> getFavorites() {
-        return favorites;
+        return this.favorites;
     }
 
     public @NotNull Collection<ServerEntry> getInternet() {
-        return internet;
+        return this.internet;
     }
 
     public @NotNull Collection<ServerEntry> getHistory() {
-        return history;
+        return this.history;
     }
 
     public @NotNull Collection<ServerEntry> getLan() {
-        return lan;
+        return this.lan;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/server/SeverDirectConnectComponent.java b/game/client/src/main/java/net/minecraft/client/gui/server/SeverDirectConnectComponent.java
index 99ea59d47..e3134975e 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/server/SeverDirectConnectComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/server/SeverDirectConnectComponent.java
@@ -3,15 +3,11 @@ package net.minecraft.client.gui.server;
 import net.minecraft.client.gui.ButtonElement;
 import net.minecraft.client.gui.TextFieldElement;
 import net.minecraft.client.gui.paged.PageComponent;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.net.ServerAddress;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.input.Keyboard;
 
-import java.util.Map;
-import java.util.UUID;
-
 public class SeverDirectConnectComponent implements PageComponent {
     public final ScreenSelectServer attachedScreen;
     public TextFieldElement ipField;
@@ -23,24 +19,24 @@ public class SeverDirectConnectComponent implements PageComponent {
     }
     @Override
     public int getHeight() {
-        return attachedScreen.height / 2;
+        return this.attachedScreen.height / 2;
     }
 
     @Override
     public void render(int x, int y, int width, int relativeMouseX, int relativeMouseY) {
         int _x = x + width / 2 - this.ipField.width / 2;
-        int _y = attachedScreen.height / 2 - 40;
+        int _y = this.attachedScreen.height / 2 - 40;
 
-        attachedScreen.mc.font.render(Tessellator.instance, I18n.getInstance().translateKey("gui.select_server.popup.add.prompt.ip"), _x, _y).setShadow().call();
+        this.attachedScreen.mc.font.render(I18n.getInstance().translateKey("gui.select_server.popup.add.prompt.ip"), _x, _y).setShadow().call();
         this.ipField.xPosition = _x;
-        this.ipField.yPosition = attachedScreen.mc.font.getLastEndingY() + 1;
+        this.ipField.yPosition = this.attachedScreen.mc.font.getLastEndingY() + 1;
 
         this.ipField.drawTextBox();
-        this.ipField.updateCursor(attachedScreen.mc, x + relativeMouseX, y + relativeMouseY);
+        this.ipField.updateCursor(this.attachedScreen.mc, x + relativeMouseX, y + relativeMouseY);
 
         this.connectButton.xPosition = _x;
         this.connectButton.yPosition = this.ipField.yPosition + this.ipField.height + 2;
-        this.connectButton.drawButton(attachedScreen.mc, x + relativeMouseX, y + relativeMouseY);
+        this.connectButton.drawButton(this.attachedScreen.mc, x + relativeMouseX, y + relativeMouseY);
     }
 
     @Override
@@ -81,7 +77,7 @@ public class SeverDirectConnectComponent implements PageComponent {
         String ip = this.ipField.getText();
         ServerAddress address = ServerAddress.resolveServerIP(ip);
         if (address != null) {
-            attachedScreen.addressToJoin = address;
+            this.attachedScreen.addressToJoin = address;
 //            attachedScreen.serverManager.idToEntryLock.lock();
 //            try {
 //                for (Map.Entry<UUID, ServerEntry> entry : attachedScreen.serverManager.idToEntryMap.entrySet()) {
diff --git a/game/client/src/main/java/net/minecraft/client/gui/toasts/GuiElementToastsHud.java b/game/client/src/main/java/net/minecraft/client/gui/toasts/GuiElementToastsHud.java
index 8ff9ba60e..aa83e367f 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/toasts/GuiElementToastsHud.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/toasts/GuiElementToastsHud.java
@@ -2,16 +2,18 @@ package net.minecraft.client.gui.toasts;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.Gui;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.Scissor;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.Global;
 import net.minecraft.client.render.Lighting;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.lang.I18n;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.opengl.GL41;
 
 import java.util.ArrayList;
 import java.util.Comparator;
@@ -28,11 +30,11 @@ public class GuiElementToastsHud extends Gui {
     private final Minecraft mc;
 
     public GuiElementToastsHud(Minecraft minecraft) {
-        mc = minecraft;
+        this.mc = minecraft;
     }
 
     public boolean isDisplayingToast(IToastable toast) {
-        for (ToastEntry entry : activeEntries){
+        for (ToastEntry entry : this.activeEntries){
             if (entry.toast.isEquivalentToast(toast)){
                 return true;
             }
@@ -41,20 +43,20 @@ public class GuiElementToastsHud extends Gui {
     }
 
     public void addToast(IToastable toast) {
-        if (activeEntries.size() >= MAX_SHOWN_ENTRIES){
-            overflowEntries.add(toast);
+        if (this.activeEntries.size() >= MAX_SHOWN_ENTRIES){
+            this.overflowEntries.add(toast);
             return;
         }
-        activeEntries.add(new ToastEntry(toast, System.currentTimeMillis()));
+        this.activeEntries.add(new ToastEntry(toast, System.currentTimeMillis()));
         toast.onToastStart();
         sortList();
     }
 
     public void endToast(IToastable toast){
-        for (int i = 0; i < activeEntries.size(); i++) {
-            ToastEntry entry = activeEntries.get(i);
+        for (int i = 0; i < this.activeEntries.size(); i++) {
+            ToastEntry entry = this.activeEntries.get(i);
             if (entry.toast.isEquivalentToast(toast)){
-                activeEntries.remove(i);
+                this.activeEntries.remove(i);
                 entry.toast.onToastEnd();
                 sortList();
                 return;
@@ -63,52 +65,45 @@ public class GuiElementToastsHud extends Gui {
     }
 
     protected void sortList(){
-        activeEntries.sort(ToastEntry.TOAST_SORTER);
+        this.activeEntries.sort(ToastEntry.TOAST_SORTER);
     }
 
     private void updateScale() {
-        GL11.glViewport(0, 0, mc.gameWindow.getWidthPixels(), mc.gameWindow.getHeightPixels());
-        GL11.glMatrixMode(GL11.GL_PROJECTION);
-        GL11.glLoadIdentity();
-        GL11.glMatrixMode(GL11.GL_MODELVIEW);
-        GL11.glLoadIdentity();
-        GL11.glClear(256);
-        GL11.glMatrixMode(GL11.GL_PROJECTION);
-        GL11.glLoadIdentity();
-        GL11.glOrtho(0.0D, mc.resolution.getExactScaledWidthScreenCoords(), mc.resolution.getExactScaledHeightScreenCoords(), 0.0D, 1000D, 3000D);
-        GL11.glMatrixMode(GL11.GL_MODELVIEW);
-        GL11.glLoadIdentity();
-        GL11.glTranslatef(0.0F, 0.0F, -2000F);
+        GL41.glViewport(0, 0, this.mc.gameWindow.getWidthPixels(), this.mc.gameWindow.getHeightPixels());
+        GL41.glClear(GL41.GL_DEPTH_BUFFER_BIT);
+        GLRenderer.projectionM4f().identity().ortho(0.0f, (float) this.mc.resolution.getExactScaledWidthScreenCoords(), (float) this.mc.resolution.getExactScaledHeightScreenCoords(), 0.0f, 1000f, 3000f);
+        GLRenderer.viewM4f().identity().translate(0.0f, 0.0f, -2000f);
+        GLRenderer.modelM4f().identity();
     }
 
     public void render(float partialTick)
     {
         if(Minecraft.hasPaidCheckTime > 0L) { // Puts unlicensed copy message at top left of screen
-            GL11.glDisable(GL11.GL_DEPTH_TEST);
-            GL11.glDepthMask(false);
+            GLRenderer.disableState(State.DEPTH_TEST);
+            GLRenderer.setDepthMask(false);
             Lighting.disable();
             String s = I18n.getInstance().translateKeyAndFormat("gui.achievement.label.unlicensed.1", Global.VERSION);
             String s1 = I18n.getInstance().translateKey("gui.achievement.label.unlicensed.2");
             String s2 = I18n.getInstance().translateKey("gui.achievement.label.unlicensed.3");
-            drawStringShadow(mc.font, s, 2, 2, 0xffffff);
-            drawStringShadow(mc.font, s1, 2, 11, 0xffffff);
-            drawStringShadow(mc.font, s2, 2, 20, 0xffffff);
-            GL11.glDepthMask(true);
-            GL11.glEnable(GL11.GL_DEPTH_TEST);
+            drawStringShadow(this.mc.font, s, 2, 2, 0xffffff);
+            drawStringShadow(this.mc.font, s1, 2, 11, 0xffffff);
+            drawStringShadow(this.mc.font, s2, 2, 20, 0xffffff);
+            GLRenderer.setDepthMask(true);
+            GLRenderer.enableState(State.DEPTH_TEST);
         }
 
-        if (!overflowEntries.isEmpty()){
-            while (activeEntries.size() < MAX_SHOWN_ENTRIES && !overflowEntries.isEmpty()){
-                IToastable toast = overflowEntries.get(0);
-                overflowEntries.remove(0);
-                activeEntries.add(new ToastEntry(toast, System.currentTimeMillis() + 1));
+        if (!this.overflowEntries.isEmpty()){
+            while (this.activeEntries.size() < MAX_SHOWN_ENTRIES && !this.overflowEntries.isEmpty()){
+                IToastable toast = this.overflowEntries.get(0);
+                this.overflowEntries.remove(0);
+                this.activeEntries.add(new ToastEntry(toast, System.currentTimeMillis() + 1));
                 toast.onToastStart();
                 sortList();
             }
         }
 
         // Remove finished entries
-        List<ToastEntry> entriesCopy = new ArrayList<>(activeEntries);
+        List<ToastEntry> entriesCopy = new ArrayList<>(this.activeEntries);
         for (ToastEntry entry : entriesCopy){
             long duration = System.currentTimeMillis() - entry.startTime;
             double animProgress = entry.toast.getAnimationProgress(duration);
@@ -117,18 +112,18 @@ public class GuiElementToastsHud extends Gui {
             }
         }
 
-        if(activeEntries.isEmpty() || mc.thePlayer == null) {
+        if(this.activeEntries.isEmpty() || this.mc.thePlayer == null) {
             return;
         }
         updateScale();
 
 
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
-        GL11.glDepthMask(false);
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.setDepthMask(false);
 
         int yOff = 0;
-        GL11.glEnable(GL11.GL_BLEND);
-        for (ToastEntry entry : activeEntries){ // Render all entries
+        GLRenderer.enableState(State.BLEND);
+        for (ToastEntry entry : this.activeEntries){ // Render all entries
             long duration = System.currentTimeMillis() - entry.startTime;
 
             double animProgress = entry.toast.getAnimationProgress(duration);
@@ -145,7 +140,7 @@ public class GuiElementToastsHud extends Gui {
             }
             hideAmount *= hideAmount;
             hideAmount *= hideAmount;
-            int toastLeft = mc.resolution.getScaledWidthScreenCoords() - TOAST_WIDTH;
+            int toastLeft = this.mc.resolution.getScaledWidthScreenCoords() - TOAST_WIDTH;
             int toastTop = (int) (-hideAmount * TOAST_HEIGHT);
             if (toastTop < 0) {
                 Scissor.enable(toastLeft, yOff, TOAST_WIDTH, TOAST_HEIGHT);
@@ -154,45 +149,38 @@ public class GuiElementToastsHud extends Gui {
             Scissor.disable();
             yOff += TOAST_HEIGHT + toastTop;
         }
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.disableState(State.BLEND);
 
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
         Lighting.disable();
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.disableState(State.DEPTH_TEST);
     }
     protected void renderToast(IToastable toast, long duration, int x, int y){
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
-        GL11.glDisable(GL11.GL_LIGHTING);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.globalSetLightEnabled(false);
 
         drawGuiIcon(x, y, TOAST_WIDTH, TOAST_HEIGHT, TextureRegistry.getTexture(toast.getTexture(duration)));
         if(toast.messageOnly(duration)) {
-            drawStringConstrained(mc.font, toast.getMessage(duration), x + 30, y + 7, 120, toast.messageColor(duration));
+            drawStringConstrained(this.mc.font, toast.getMessage(duration), x + 30, y + 7, 120, toast.messageColor(duration));
         } else {
-            drawStringNoShadow(mc.font, toast.getTitle(duration), x + 30, y + 7, toast.titleColor(duration));
-            drawStringNoShadow(mc.font, toast.getMessage(duration), x + 30, y + 18, toast.messageColor(duration));
+            drawStringNoShadow(this.mc.font, toast.getTitle(duration), x + 30, y + 7, toast.titleColor(duration));
+            drawStringNoShadow(this.mc.font, toast.getMessage(duration), x + 30, y + 18, toast.messageColor(duration));
         }
 
-        GL11.glDepthMask(true);
+        GLRenderer.setDepthMask(true);
         Lighting.enableInventoryLight();
-        GL11.glColor4f(1, 1, 1, 1);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.setColor4f(1, 1, 1, 1);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
 
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
+        GLRenderer.enableState(State.DEPTH_TEST);
         ItemStack icon = toast.getIcon(duration);
-//        ItemModelDispatcher.getInstance().getDispatch(icon).renderItemIntoGui(Tessellator.instance, mc.font, mc.textureManager, icon, x + 8, y + 8, 1.0f);
-        if (icon != null) ItemModelDispatcher.getInstance().getDispatch(icon).renderGui(Tessellator.instance, null, icon, x + 8, y + 8, 1f, 1f, 1.0f);
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
+//        ItemModelDispatcher.getInstance().getDispatch(icon).renderItemIntoGui(GLRenderer.getTessellator(), mc.font, mc.textureManager, icon, x + 8, y + 8, 1.0f);
+        if (icon != null) ItemModelDispatcher.getInstance().getDispatch(icon).renderGui(GLRenderer.getTessellator(), null, icon, x + 8, y + 8, LightmapHelper.getLightmapCoord(15, 15), 1.0f);
+        GLRenderer.disableState(State.DEPTH_TEST);
     }
 
-    static class ToastEntry {
-        public static final Comparator<ToastEntry> TOAST_SORTER = (o1, o2) -> (int) (o1.startTime - o2.startTime);
-        public final long startTime;
-        public final IToastable toast;
-        public ToastEntry(IToastable toast, long startTime){
-            this.toast = toast;
-            this.startTime = startTime;
-        }
+    record ToastEntry(@NotNull IToastable toast, long startTime) {
+            public static final Comparator<ToastEntry> TOAST_SORTER = (o1, o2) -> (int) (o1.startTime - o2.startTime);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/gui/worldsettings/ButtonComponent.java b/game/client/src/main/java/net/minecraft/client/gui/worldsettings/ButtonComponent.java
index daf0493d4..fd96114d7 100644
--- a/game/client/src/main/java/net/minecraft/client/gui/worldsettings/ButtonComponent.java
+++ b/game/client/src/main/java/net/minecraft/client/gui/worldsettings/ButtonComponent.java
@@ -3,16 +3,16 @@ package net.minecraft.client.gui.worldsettings;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ButtonElement;
 import net.minecraft.client.gui.paged.PageComponent;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.window.CursorShape;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.sound.SoundCategory;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
-
-import static org.lwjgl.opengl.GL11.*;
-import static org.lwjgl.opengl.GL11.GL_BLEND;
 
 public abstract class ButtonComponent
     implements PageComponent {
@@ -49,7 +49,7 @@ public abstract class ButtonComponent
             textColor = 0xFFFFFFA0;
         }
 
-        mc.font.render(Tessellator.instance, translated, x, y + (this.getHeight() / 2) - 4).setShadow().setColor(textColor).call();
+        mc.font.render(translated, x, y + (this.getHeight() / 2) - 4).setShadow().setColor(textColor).call();
         this.resetButton.enabled = !this.isDefault();
         this.renderButton(x, y, width - BUTTON_WIDTH, COMPONENT_SPACING, BUTTON_WIDTH, 20, relativeMouseX, relativeMouseY);
         final int stringWidth = mc.font.stringWidth(translated);
@@ -110,19 +110,19 @@ public abstract class ButtonComponent
     }
 
     protected void drawRect(final int minX, final int minY, final int maxX, final int maxY, final int argb) {
-        final Tessellator tessellator = Tessellator.instance;
-        GL11.glEnable(GL_BLEND);
-        GL11.glDisable(GL_TEXTURE_2D);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_I(argb & 0x00FFFFFF, argb >> 24 & 0xff);
+        tessellator.setColor2i(argb & 0x00FFFFFF, argb >> 24 & 0xff);
         tessellator.addVertex(minX, maxY, 0.0D);
         tessellator.addVertex(maxX, maxY, 0.0D);
         tessellator.addVertex(maxX, minY, 0.0D);
         tessellator.addVertex(minX, minY, 0.0D);
         tessellator.draw();
-        GL11.glEnable(GL_TEXTURE_2D);
-        GL11.glDisable(GL_BLEND);
+        GLRenderer.popFrame();
     }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/option/GameSettings.java b/game/client/src/main/java/net/minecraft/client/option/GameSettings.java
index d7cf32df4..b0262b031 100644
--- a/game/client/src/main/java/net/minecraft/client/option/GameSettings.java
+++ b/game/client/src/main/java/net/minecraft/client/option/GameSettings.java
@@ -78,7 +78,7 @@ public class GameSettings {
 	public @NotNull OptionBoolean invertMouse = new OptionBoolean(this, "invertYMouse", false);
 	public @NotNull OptionBoolean rawMouseInput = new OptionBoolean(this, "rawMouseInput", false);
 	public @NotNull OptionBoolean viewBobbing = new OptionBoolean(this, "bobView", true);
-	public @NotNull OptionBoolean advancedOpenGL = new OptionBoolean(this, "advancedOpengl", false);
+//	public @NotNull OptionBoolean advancedOpenGL = new OptionBoolean(this, "advancedOpengl", false);
 	public @NotNull OptionRange fancyGraphics = new OptionRange(this, "fancyGraphics", 1, 2);
 	public @NotNull OptionBoolean treeShadows = new OptionBoolean(this, "treeShadows", true);
 	public @NotNull OptionBoolean connectedGlass = new OptionBoolean(this, "connectedGlass", false);
@@ -90,7 +90,7 @@ public class GameSettings {
 	public @NotNull OptionBoolean vignette = new OptionBoolean(this, "vignette", true);
 	public @NotNull OptionBoolean showPlayerList = new OptionBoolean(this, "showPlayerList", false);
 	public @NotNull OptionBoolean slimeParticles = new OptionBoolean(this, "slimeParticles", true);
-	public @NotNull OptionBoolean disableShaders = new OptionBoolean(this, "disableShaders", false);
+//	public @NotNull OptionBoolean disableShaders = new OptionBoolean(this, "disableShaders", false);
 	public @NotNull OptionString shaderOverride = new OptionString(this, "shaderOverride", "");
 	public @NotNull OptionBoolean autoHit = new OptionBoolean(this, "autoHit", true);
 	public @NotNull OptionBoolean easyBridge = new OptionBoolean(this, "easyBridge", true);
@@ -123,7 +123,7 @@ public class GameSettings {
 	public @NotNull OptionRange renderDistance = new OptionRange(this, "renderDistance", 12, 2, 32);
 	public @NotNull OptionBoolean enableVsync = new OptionBoolean(this, "enableVsync", false);
 	public @NotNull OptionEnum<ChatVisibility> chatVisibility = new OptionEnum<>(this, "chatVisibility", ChatVisibility.class, ChatVisibility.SHOW_ALL);
-	public @NotNull OptionRange customFpsLimit = new OptionRange(this,"customFpsLimit",0,241);
+	public @NotNull OptionRange customFpsLimit = new OptionRange(this,"customFpsLimit",165,301);
 	public @NotNull OptionInteger guiScale = new OptionInteger(this, "guiScale", 0);
 	public @NotNull OptionInteger overlayMode = new OptionInteger(this, "overlayMode", 0);
 	public @NotNull OptionInteger rotationOverlayMode = new OptionInteger(this, "rotationOverlayMode", 0);
@@ -143,7 +143,7 @@ public class GameSettings {
 	public @NotNull OptionEnum<DescriptionPromptEnum> itemDescriptions = new OptionEnum<>(this, "itemDescriptions", DescriptionPromptEnum.class, DescriptionPromptEnum.PROMPT);
 	public @NotNull OptionBoolean turnWithVehicle = new OptionBoolean(this, "turnWithVehicle", true);
 	public @NotNull OptionBoolean disableCrashHandler = new OptionBoolean(this, "disableCrashHandler", false);
-	public @NotNull OptionBoolean enableMultiDrawRendering = new OptionBoolean(this, "enableMultiDrawRendering", true);
+//	public @NotNull OptionBoolean enableMultiDrawRendering = new OptionBoolean(this, "enableMultiDrawRendering", true);
 	public @NotNull OptionEnum<SelectedProvider> enableThreadedChunkProvider = new OptionEnum<>(this, "enableThreadedChunkProvider", SelectedProvider.class, SelectedProvider.THREADED);
 	public @NotNull OptionBoolean musicToasts = new OptionBoolean(this, "musicToasts", true);
 	public @NotNull OptionEnum<MusicFrequency> musicFrequency = new OptionEnum<>(this, "musicFrequency", MusicFrequency.class, MusicFrequency.DEFAULT);
@@ -405,7 +405,7 @@ public class GameSettings {
 		}
 		if(option == customFpsLimit){
 			int value = customFpsLimit.value;
-			int maxValue = 240;
+			int maxValue = 300;
 			if (enableVsync.value){
 				return String.valueOf(mc.gameWindow.getFrequency());
 			}
@@ -505,7 +505,7 @@ public class GameSettings {
 		if(option == fancyGraphics) mc.renderGlobal.allChanged();
 		if(option == ambientOcclusion) mc.renderGlobal.allChanged();
 		if(option == connectedGlass) mc.renderGlobal.allChanged();
-		if(option == advancedOpenGL) mc.renderGlobal.allChanged();
+//		if(option == advancedOpenGL) mc.renderGlobal.allChanged();
 		if(option == biomeWater) {
 			mc.renderGlobal.allChanged();
 			mc.textureManager.updateDynamicTextures(false);
@@ -548,11 +548,6 @@ public class GameSettings {
 				mc.currentScreen.opened(mc.resolution.getScaledWidthScreenCoords(), mc.resolution.getScaledHeightScreenCoords());
 			}
 		}
-		if(option == lightmapStyle) {
-			if (mc.renderGlobal != null) {
-				mc.renderGlobal.allChanged();
-			}
-		}
 		if(option == customLightmap) {
 			mc.worldRenderer.lightmapHelper.setup();
 		}
diff --git a/game/client/src/main/java/net/minecraft/client/option/OptionFloat.java b/game/client/src/main/java/net/minecraft/client/option/OptionFloat.java
index 61be56932..20b5cde37 100644
--- a/game/client/src/main/java/net/minecraft/client/option/OptionFloat.java
+++ b/game/client/src/main/java/net/minecraft/client/option/OptionFloat.java
@@ -7,9 +7,10 @@ public class OptionFloat extends Option<Float>{
 	public OptionFloat(GameSettings gameSettings, String name, float value) {
 		super(gameSettings, name, value);
 	}
-	
+
+
 	public float get() {
-		return value;
+		return this.value;
 	}
 	
 	public boolean isFloat() {
diff --git a/game/client/src/main/java/net/minecraft/client/option/OptionRange.java b/game/client/src/main/java/net/minecraft/client/option/OptionRange.java
index aeb1244b9..e4f3a3299 100644
--- a/game/client/src/main/java/net/minecraft/client/option/OptionRange.java
+++ b/game/client/src/main/java/net/minecraft/client/option/OptionRange.java
@@ -7,13 +7,13 @@ public class OptionRange extends OptionToggleable<Integer> {
 	public final int lowest;
     public OptionRange(GameSettings gameSettings, String name, int defaultValue, int values) {
         super(gameSettings, name, defaultValue, getValueArray(values));
-		highest = this.values[this.values.length - 1];
-		lowest = this.values[0];
+        this.highest = this.values[this.values.length - 1];
+        this.lowest = this.values[0];
     }
 	public OptionRange(GameSettings gameSettings, String name, int defaultValue, int lowest, int highest) {
 		super(gameSettings, name, defaultValue, getValueArray(lowest, highest));
-		this.highest = this.values[this.values.length - 1];
-		this.lowest = this.values[0];
+		this.highest = highest;
+		this.lowest = lowest;
 	}
 
 	@Override
diff --git a/game/client/src/main/java/net/minecraft/client/option/enums/LightmapStyle.java b/game/client/src/main/java/net/minecraft/client/option/enums/LightmapStyle.java
index 2126ba431..0013af6d8 100644
--- a/game/client/src/main/java/net/minecraft/client/option/enums/LightmapStyle.java
+++ b/game/client/src/main/java/net/minecraft/client/option/enums/LightmapStyle.java
@@ -3,7 +3,7 @@ package net.minecraft.client.option.enums;
 public enum LightmapStyle {
     GRAY("options.lightmapStyle.gray"),
     COLORIZED("options.lightmapStyle.colorized"),
-    DISABLED("options.lightmapStyle.disabled");
+    /*DISABLED("options.lightmapStyle.disabled")*/;
 
     private final String translationKey;
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/DisplayList.java b/game/client/src/main/java/net/minecraft/client/render/DisplayList.java
deleted file mode 100644
index 7da023f78..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/DisplayList.java
+++ /dev/null
@@ -1,86 +0,0 @@
-package net.minecraft.client.render;
-
-import java.nio.IntBuffer;
-
-import net.minecraft.client.GLAllocation;
-import org.lwjgl.opengl.GL11;
-
-public class DisplayList
-{
-
-    public DisplayList()
-    {
-        callList = GLAllocation.createDirectIntBuffer(0x10000);
-        initialized = false;
-        isFlipped = false;
-    }
-
-    public void setToPos(int blockX, int blockY, int blockZ, double offsetX, double offsetY,
-                         double offsetZ)
-    {
-        initialized = true;
-        callList.clear();
-        this.posX = blockX;
-        this.posY = blockY;
-        this.posZ = blockZ;
-        this.offsetX = offsetX;
-        this.offsetY = offsetY;
-        this.offsetZ = offsetZ;
-    }
-
-    public boolean isSetToPos(int posX, int posY, int posZ)
-    {
-        if(!initialized)
-        {
-            return false;
-        } else
-        {
-            return posX == this.posX && posY == this.posY && posZ == this.posZ;
-        }
-    }
-
-    public void addCallToList(int i)
-    {
-        callList.put(i);
-        if(callList.remaining() == 0)
-        {
-            call();
-        }
-    }
-
-    public void call()
-    {
-        if(!initialized)
-        {
-            return;
-        }
-        if(!isFlipped)
-        {
-            callList.flip();
-            isFlipped = true;
-        }
-        if(callList.remaining() > 0)
-        {
-            GL11.glPushMatrix();
-            GL11.glTranslated(posX - offsetX, posY - offsetY, posZ - offsetZ);
-            GL11.glCallLists(callList);
-            GL11.glPopMatrix();
-        }
-    }
-
-    public void clear()
-    {
-        initialized = false;
-        isFlipped = false;
-    }
-
-    private int posX;
-    private int posY;
-    private int posZ;
-    private double offsetX;
-    private double offsetY;
-    private double offsetZ;
-    private final IntBuffer callList;
-    private boolean initialized;
-    private boolean isFlipped;
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/EntityRenderDispatcher.java b/game/client/src/main/java/net/minecraft/client/render/EntityRendererDispatcher.java
similarity index 86%
rename from game/client/src/main/java/net/minecraft/client/render/EntityRenderDispatcher.java
rename to game/client/src/main/java/net/minecraft/client/render/EntityRendererDispatcher.java
index b716ba3cb..3ac8e1ae0 100644
--- a/game/client/src/main/java/net/minecraft/client/render/EntityRenderDispatcher.java
+++ b/game/client/src/main/java/net/minecraft/client/render/EntityRendererDispatcher.java
@@ -6,6 +6,7 @@ import java.util.Map;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.entity.*;
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texturepack.TexturePackList;
 import net.minecraft.core.entity.EntityItem;
 import net.minecraft.core.entity.EntityLightning;
@@ -22,11 +23,9 @@ import net.minecraft.core.item.Items;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import net.minecraft.client.option.GameSettings;
 import net.minecraft.client.render.camera.ICamera;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.core.Global;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.entity.EntityFishingBobber;
 import net.minecraft.core.entity.EntityFallingBlock;
@@ -36,9 +35,8 @@ import net.minecraft.core.entity.projectile.ProjectileArrow;
 import net.minecraft.core.entity.projectile.ProjectilePebble;
 import net.minecraft.core.entity.vehicle.EntityMinecart;
 
-public final class EntityRenderDispatcher
-{
-    public static final @NotNull EntityRenderDispatcher instance = new EntityRenderDispatcher();
+public final class EntityRendererDispatcher {
+    public static final @NotNull EntityRendererDispatcher instance = new EntityRendererDispatcher();
     public static double renderPosX = 0;
     public static double renderPosY = 0;
     public static double renderPosZ = 0;
@@ -56,7 +54,7 @@ public final class EntityRenderDispatcher
     public double viewLerpPosY = 0;
     public double viewLerpPosZ = 0;
 
-    private EntityRenderDispatcher() {
+    private EntityRendererDispatcher() {
         final Minecraft mc = Minecraft.getMinecraft();
         this.textureManager = mc.textureManager;
         this.packList = mc.texturePackList;
@@ -117,7 +115,7 @@ public final class EntityRenderDispatcher
     @SuppressWarnings("unchecked") // trust me this is safe, Notch did it first
     public <T extends Entity> EntityRenderer<T> getRenderer(final @NotNull Class<T> e) {
         EntityRenderer<? extends Entity> r = this.renderers.get(e);
-        if(r == null && e != Entity.class) {
+        if (r == null && e != Entity.class) {
             r = getRenderer((Class<? extends Entity>) e.getSuperclass());
             this.renderers.put(e, r);
         }
@@ -129,9 +127,8 @@ public final class EntityRenderDispatcher
         return (EntityRenderer<T>) getRenderer(entity.getClass());
     }
 
-    public void cacheActiveRenderInfo(final @NotNull World world, final @NotNull ICamera camera, final float partialTick)
-    {
-        if(this.world != world) {
+    public void cacheActiveRenderInfo(final @NotNull World world, final @NotNull ICamera camera, final float partialTick) {
+        if (this.world != world) {
             for (final @Nullable EntityRenderer<?> renderer : this.renderers.values()) {
                 if (renderer == null) continue;
                 renderer.onWorldChanged(world);
@@ -146,40 +143,28 @@ public final class EntityRenderDispatcher
         this.viewLerpPosZ = camera.getZ(partialTick);
     }
 
-    public <T extends Entity> void renderEntity(final Tessellator tessellator, final T entity, final float partialTick) {
-        final double lerpPosX = entity.xo + (entity.x - entity.xo) * (double)partialTick;
-        final double lerpPosY = entity.yo + (entity.y - entity.yo) * (double)partialTick;
-        final double lerpPosZ = entity.zo + (entity.z - entity.zo) * (double)partialTick;
+    public <T extends Entity> void renderEntity(final TessellatorGeneral tessellator, final T entity, final float partialTick) {
+        final double lerpPosX = entity.xo + (entity.x - entity.xo) * (double) partialTick;
+        final double lerpPosY = entity.yo + (entity.y - entity.yo) * (double) partialTick;
+        final double lerpPosZ = entity.zo + (entity.z - entity.zo) * (double) partialTick;
         final float lerpYaw = entity.yRotO + (entity.yRot - entity.yRotO) * partialTick;
-        float brightness;
-
-        if(LightmapHelper.isLightmapEnabled()) {
-        	brightness = 1.0f;
-
-        	LightmapHelper.setLightmapCoord(entity.getLightmap(partialTick));
-        } else if(Global.accessor.isFullbrightEnabled()) {
-        	brightness = 1.0f;
-        } else {
-        	brightness = entity.getBrightness(partialTick);
-        }
-
-        if (Global.accessor.isFullbrightEnabled()) brightness = 1.0f;
-        GL11.glColor3f(brightness, brightness, brightness);
 
+        GLRenderer.setLightmapCoord1i(entity.getLightmap(partialTick));
+        GLRenderer.setColor3f(1f, 1f, 1f);
         renderEntityWithPosYaw(tessellator, entity, lerpPosX - renderPosX, lerpPosY - renderPosY, lerpPosZ - renderPosZ, lerpYaw, partialTick);
     }
 
-    public <T extends Entity> void renderEntityWithPosYaw(final @NotNull Tessellator tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+    public <T extends Entity> void renderEntityWithPosYaw(final @NotNull TessellatorGeneral tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
         final EntityRenderer<T> renderer = getRenderer(entity);
-        if(renderer != null) {
+        if (renderer != null) {
             renderer.render(tessellator, entity, x, y, z, yaw, partialTick);
             renderer.postRender(tessellator, entity, x, y, z, yaw, partialTick);
         }
     }
 
-    public <T extends Entity> void renderEntityPreviewWithPosYaw(final @NotNull Tessellator tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+    public <T extends Entity> void renderEntityPreviewWithPosYaw(final @NotNull TessellatorGeneral tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
         final EntityRenderer<T> renderer = getRenderer(entity);
-        if(renderer != null) {
+        if (renderer != null) {
             renderer.renderPreview(tessellator, entity, x, y, z, yaw, partialTick);
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/render/FallbackRenderer.java b/game/client/src/main/java/net/minecraft/client/render/FallbackRenderer.java
index 3361df714..b10f9b691 100644
--- a/game/client/src/main/java/net/minecraft/client/render/FallbackRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/FallbackRenderer.java
@@ -1,16 +1,13 @@
 package net.minecraft.client.render;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
-import net.minecraft.client.render.tessellator.Tessellator;
-import org.jetbrains.annotations.NotNull;
 
 public class FallbackRenderer implements Renderer {
 
 	public Minecraft mc;
 	
 	public FallbackRenderer(Minecraft minecraft) {
-		mc = minecraft;
+        this.mc = minecraft;
 	}
 
 	@Override
@@ -33,12 +30,7 @@ public class FallbackRenderer implements Renderer {
 
 	}
 
-	@Override
-	public @NotNull ParticleTessellator getParticleTessellator() {
-		return Tessellator.instance;
-	}
-
-	@Override
+    @Override
 	public void endRenderClouds(float partialTicks) {
 		
 	}
@@ -75,12 +67,12 @@ public class FallbackRenderer implements Renderer {
 
 	@Override
 	public int getRenderWidth() {
-		return mc.gameWindow.getWidthPixels();
+		return this.mc.gameWindow.getWidthPixels();
 	}
 
 	@Override
 	public int getRenderHeight() {
-		return mc.gameWindow.getHeightPixels();
+		return this.mc.gameWindow.getHeightPixels();
 	}
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/FogManager.java b/game/client/src/main/java/net/minecraft/client/render/FogManager.java
index 10ab8e7ab..803b2f89a 100644
--- a/game/client/src/main/java/net/minecraft/client/render/FogManager.java
+++ b/game/client/src/main/java/net/minecraft/client/render/FogManager.java
@@ -2,16 +2,13 @@ package net.minecraft.client.render;
 
 import static org.lwjgl.opengl.GL11.*;
 
-import java.nio.FloatBuffer;
-
 import net.minecraft.client.world.WorldClient;
 import net.minecraft.core.block.material.Materials;
 import net.minecraft.core.world.pos.TilePos;
 import org.jetbrains.annotations.NotNull;
 import org.joml.Vector3fc;
-import org.lwjgl.opengl.NVFogDistance;
+import org.joml.Vector4f;
 
-import net.minecraft.client.GLAllocation;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.ScreenPhotoMode;
 import net.minecraft.client.gui.modelviewer.ScreenModelViewer;
@@ -33,8 +30,6 @@ public class FogManager {
     public float fogBrightnessOld;
     public float fogBrightness;
 
-    private final @NotNull FloatBuffer fogColorBuffer = GLAllocation.createDirectFloatBuffer(16);
-
     public FogManager(@NotNull Minecraft mc) {
         this.mc = mc;
     }
@@ -54,57 +49,60 @@ public class FogManager {
         this.fogBrightness += (newBrightness - this.fogBrightness) * 0.1F;
     }
 
-    public void setupFog(int fogMode, float farPlaneDistance, float partialTick) {
-        glFogfv(GL_FOG_COLOR, buffer(this.fogRed, this.fogGreen, this.fogBlue, 0.5F));
-        glNormal3f(0.0F, -1F, 0.0F);
-        glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        if (!this.mc.gameSettings.fog.value && fogMode != FOG_MODE_SKY) {
-            glFogi(GL_FOG_MODE, GL_EXP);
-            glFogf(GL_FOG_DENSITY, 0.0F);
-            float maxFogDistance = this.mc.gameSettings.renderDistance.highest * 16;
-            glFogf(GL_FOG_START, maxFogDistance * 0.25F);
-            glFogf(GL_FOG_END, maxFogDistance);
-            glEnable(GL_COLOR_MATERIAL);
-            glColorMaterial(GL_FRONT, GL_AMBIENT);
-            return;
-        }
+    public @NotNull FogState setupFog(int fogMode, float farPlaneDistance, float partialTick, @NotNull FogState dest) {
+        dest.fogColor.set(this.fogRed, this.fogGreen, this.fogBlue, 0.5f);
 
+        byte cameraState;
         if (CameraUtil.isUnderLiquid(this.mc.activeCamera, this.mc.currentWorld, Materials.WATER, partialTick)) {
-            glFogi(GL_FOG_MODE, GL_EXP);
-            glFogf(GL_FOG_DENSITY, 0.1F);
+            cameraState = 1;
         } else if (CameraUtil.isUnderLiquid(this.mc.activeCamera, this.mc.currentWorld, Materials.LAVA, partialTick)) {
-            glFogi(GL_FOG_MODE, GL_EXP);
-            glFogf(GL_FOG_DENSITY, 2.0F);
+            cameraState = 2;
         } else {
-            float fogDistance = farPlaneDistance;
-            float maxFogDistance = this.mc.gameSettings.renderDistance.highest * 16;
-
-            float fogModifier = this.mc.currentWorld.getCurrentWeather() != null ? this.mc.currentWorld.getCurrentWeather().getFogDistanceMultiplier() : 1.0f;
-            fogModifier = (1.0f - ((1.0f - fogModifier) * this.mc.currentWorld.weatherManager.getWeatherIntensity() * this.mc.currentWorld.weatherManager.getWeatherPower()));
-
-            if (fogDistance > maxFogDistance * fogModifier) fogDistance = maxFogDistance * fogModifier;
+            cameraState = 0;
+        }
 
-            if (this.mc.currentScreen instanceof ScreenPhotoMode) {
-                fogDistance = farPlaneDistance * ((ScreenPhotoMode) this.mc.currentScreen).getFog(partialTick);
-            }
+        if (!this.mc.gameSettings.fog.value && fogMode != FOG_MODE_SKY && cameraState == 0) {
+            return dest.disable();
+        }
 
-            glFogi(GL_FOG_MODE, GL_LINEAR);
-            glFogf(GL_FOG_START, (fogDistance * 0.25F) * fogModifier);
-            glFogf(GL_FOG_END, fogDistance);
-            glFogf(GL_FOG_DENSITY, 1);
-            if (fogMode == FOG_MODE_SKY) {
-                glFogf(GL_FOG_START, 0.0F);
-                glFogf(GL_FOG_END, fogDistance * 0.8F);
+        switch (cameraState) {
+            case 1: {
+                dest.fogMode = FogState.Mode.EXP;
+                dest.fogDensity = 0.1F;
+                break;
             }
-            if (OpenGLHelper.enableSphericalFog) {
-                glFogi(NVFogDistance.GL_FOG_DISTANCE_MODE_NV, NVFogDistance.GL_EYE_RADIAL_NV);
+            case 2: {
+                dest.fogMode = FogState.Mode.EXP;
+                dest.fogDensity = 2.0f;
+                break;
             }
-            if (this.mc.currentWorld.dimension == Dimension.NETHER) {
-                glFogf(GL_FOG_START, 0.0F);
+            default: {
+                float fogDistance = farPlaneDistance;
+                float maxFogDistance = this.mc.gameSettings.renderDistance.highest * 16;
+
+                float fogModifier = this.mc.currentWorld.getCurrentWeather() != null ? this.mc.currentWorld.getCurrentWeather().getFogDistanceMultiplier() : 1.0f;
+                fogModifier = (1.0f - ((1.0f - fogModifier) * this.mc.currentWorld.weatherManager.getWeatherIntensity() * this.mc.currentWorld.weatherManager.getWeatherPower()));
+
+                if (fogDistance > maxFogDistance * fogModifier) fogDistance = maxFogDistance * fogModifier;
+
+                if (this.mc.currentScreen instanceof ScreenPhotoMode screenPhotoMode) {
+                    fogDistance = farPlaneDistance * screenPhotoMode.getFog(partialTick);
+                }
+
+                dest.fogMode = FogState.Mode.LINEAR;
+                dest.fogStart = (fogDistance * 0.25F) * fogModifier;
+                dest.fogEnd = fogDistance;
+                dest.fogDensity = 1F;
+                if (fogMode == FOG_MODE_SKY) {
+                    dest.fogStart = 0.0F;
+                    dest.fogEnd = fogDistance * 0.8F;
+                }
+                if (this.mc.currentWorld.dimension == Dimension.NETHER) {
+                    dest.fogStart = 0.0F;
+                }
             }
         }
-        glEnable(GL_COLOR_MATERIAL);
-        glColorMaterial(GL_FRONT, GL_AMBIENT);
+        return dest;
     }
 
     public void updateFogColor(float partialTick) {
@@ -174,10 +172,49 @@ public class FogManager {
         glClearColor(this.fogRed, this.fogGreen, this.fogBlue, 0.0F);
     }
 
-    private @NotNull FloatBuffer buffer(float r, float g, float b, float a) {
-        this.fogColorBuffer.clear();
-        this.fogColorBuffer.put(r).put(g).put(b).put(a);
-        this.fogColorBuffer.flip();
-        return this.fogColorBuffer;
+    public static class FogState {
+        public final @NotNull Vector4f fogColor = new Vector4f(0, 0, 0, 0);
+        public @NotNull Mode fogMode = Mode.EXP;
+        public float fogStart = 0f;
+        public float fogEnd = 1f;
+        public float fogDensity = 1f;
+
+        public FogState() {
+            reset();
+        }
+
+        public @NotNull FogState reset() {
+            this.fogColor.set(0, 0, 0, 0);
+            this.fogMode = Mode.EXP;
+            this.fogStart = 0f;
+            this.fogEnd = 1f;
+            this.fogDensity = 1f;
+            return this;
+        }
+
+        public @NotNull FogState disable() {
+            this.fogMode = FogState.Mode.EXP;
+            this.fogDensity = 0.0F;
+            float maxFogDistance = Minecraft.getMinecraft().gameSettings.renderDistance.highest * 16;
+            this.fogStart = maxFogDistance * 0.25f;
+            this.fogEnd = maxFogDistance;
+            return this;
+        }
+
+        public @NotNull FogState copy() {
+            FogState newState = new FogState();
+            newState.fogColor.set(this.fogColor);
+            newState.fogMode = this.fogMode;
+            newState.fogStart = this.fogStart;
+            newState.fogEnd = this.fogEnd;
+            newState.fogDensity = this.fogDensity;
+            return newState;
+        }
+
+        public enum Mode {
+            LINEAR,
+            EXP,
+            EXP2
+        }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/Framebuffer.java b/game/client/src/main/java/net/minecraft/client/render/FrameBuffer.java
similarity index 96%
rename from game/client/src/main/java/net/minecraft/client/render/Framebuffer.java
rename to game/client/src/main/java/net/minecraft/client/render/FrameBuffer.java
index 597e1ea88..bdfdae08f 100644
--- a/game/client/src/main/java/net/minecraft/client/render/Framebuffer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/FrameBuffer.java
@@ -2,7 +2,7 @@ package net.minecraft.client.render;
 
 import static org.lwjgl.opengl.ARBFramebufferObject.*;
 
-public class Framebuffer {
+public class FrameBuffer {
 	
 	private int id;
 	
diff --git a/game/client/src/main/java/net/minecraft/client/render/ItemRenderer.java b/game/client/src/main/java/net/minecraft/client/render/ItemRenderer.java
index d37c4bc33..aaede56bb 100644
--- a/game/client/src/main/java/net/minecraft/client/render/ItemRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/ItemRenderer.java
@@ -2,9 +2,12 @@ package net.minecraft.client.render;
 
 import net.minecraft.client.entity.player.PlayerLocal;
 import net.minecraft.client.render.entity.MobRendererPlayer;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.CompareFunc;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.block.material.Materials;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.block.model.BlockModel;
@@ -13,72 +16,54 @@ import net.minecraft.client.render.entity.EntityRenderer;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.util.helper.MathHelper;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 
-import static org.lwjgl.opengl.GL11.GL_ALPHA_TEST;
-import static org.lwjgl.opengl.GL11.GL_BLEND;
-import static org.lwjgl.opengl.GL11.GL_DEPTH_TEST;
-import static org.lwjgl.opengl.GL11.glColor4f;
-import static org.lwjgl.opengl.GL11.glDisable;
-import static org.lwjgl.opengl.GL11.glEnable;
-import static org.lwjgl.opengl.GL11.glPopMatrix;
-import static org.lwjgl.opengl.GL11.glPushMatrix;
+public class ItemRenderer {
 
-public class ItemRenderer
-{
-
-    public ItemRenderer(Minecraft minecraft)
-    {
-        itemToRender = null;
-        height = 0.0F;
-        oHeight = 0.0F;
-        lastSlot = -1;
-        mc = minecraft;
+    public ItemRenderer(Minecraft minecraft) {
+        this.itemToRender = null;
+        this.height = 0.0F;
+        this.oHeight = 0.0F;
+        this.lastSlot = -1;
+        this.mc = minecraft;
     }
-    public float getEquippedProgress(float partialTick){
-        return oHeight + (height - oHeight) * partialTick;
+
+    public float getEquippedProgress(float partialTick) {
+        return this.oHeight + (this.height - this.oHeight) * partialTick;
     }
 
-    public void renderItemInFirstPerson(float partialTick)
-    {
+    public void renderItemInFirstPerson(float partialTick) {
         float equipProgress = getEquippedProgress(partialTick);
-        PlayerLocal player = mc.thePlayer;
+        PlayerLocal player = this.mc.thePlayer;
         float rotationPitch = player.xRotO + (player.xRot - player.xRotO) * partialTick;
-        GL11.glPushMatrix();
-        GL11.glRotatef(rotationPitch, 1.0F, 0.0F, 0.0F);
-        GL11.glRotatef(player.yRotO + (player.yRot - player.yRotO) * partialTick, 0.0F, 1.0F, 0.0F);
         Lighting.enableLight();
-        GL11.glPopMatrix();
-        ItemStack itemstack = itemToRender;
-        if(itemstack != null)
-        {
-            float brightness = 1.0f;
-            if(LightmapHelper.isLightmapEnabled() || mc.fullbright) {
-                LightmapHelper.setLightmapCoord(mc.thePlayer.getLightmap(partialTick));
-            }else {
-                brightness = mc.currentWorld.getLightBrightness(MathHelper.floor(player.x), MathHelper.floor(player.y), MathHelper.floor(player.z));
-            }
-            ItemModelDispatcher.getInstance().getDispatch(itemstack.getItem()).renderFirstPerson(Tessellator.instance, this,player, itemstack, brightness, 1f, partialTick);
+        GLRenderer.globalGetNormalTransformMatrix()
+            .rotateX(Math.toRadians(rotationPitch))
+            .rotateY(Math.toRadians(player.yRotO + (player.yRot - player.yRotO) * partialTick))
+            .invert();
+        ItemStack itemstack = this.itemToRender;
+        if (itemstack != null) {
+            GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+            GLRenderer.setLightmapCoord1i(this.mc.thePlayer.getLightmap(partialTick));
+            ItemModelDispatcher.getInstance().getDispatch(itemstack.getItem()).renderFirstPerson(GLRenderer.getTessellator(), this, player, itemstack, player.getLightmap(partialTick), partialTick);
         } else {
 
-            GL11.glPushMatrix();
-            GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        	float brightness = 1.0f;
-        	if(LightmapHelper.isLightmapEnabled() || mc.fullbright) {
-        		LightmapHelper.setLightmapCoord(mc.thePlayer.getLightmap(partialTick));
-        	}else if(mc.fullbright) {
-
-        	}else {
-        		brightness = mc.currentWorld.getLightBrightness(MathHelper.floor(player.x), MathHelper.floor(player.y), MathHelper.floor(player.z));
-        	}
-            GL11.glColor4f(brightness, brightness, brightness, 1.0f);
-            EntityRenderer<? extends Entity> render = EntityRenderDispatcher.instance.getRenderer(mc.thePlayer);
-            MobRendererPlayer playerRenderer = (MobRendererPlayer)render;
+            GLRenderer.pushFrame();
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.enableState(State.DEPTH_TEST);
+            GLRenderer.setDepthFunc(CompareFunc.LESS);
+//            GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+            float brightness = 1.0f;
+            GLRenderer.setLightmapCoord1i(this.mc.thePlayer.getLightmap(partialTick));
+            GLRenderer.setColor4f(brightness, brightness, brightness, 1.0f);
+            EntityRenderer<? extends Entity> render = EntityRendererDispatcher.instance.getRenderer(this.mc.thePlayer);
+            MobRendererPlayer playerRenderer = (MobRendererPlayer) render;
             if (player.getHeldObject() == null) {
                 if (player.isLeftHanded()) {
                     float f6 = 0.8F;
@@ -86,202 +71,191 @@ public class ItemRenderer
                     float f14 = MathHelper.sin(swingProgress * MathHelper.PI);
                     float f18 = MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI);
 
-                    GL11.glScalef(-1, 1, 1);
-                    GL11.glTranslatef(-f18 * 0.3F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.4F, -f14 * 0.4F);
-                    GL11.glTranslatef(0.8F * f6, -0.75F * f6 - (1.0F - equipProgress) * 0.6F, -0.9F * f6);
-                    GL11.glRotatef(45F, 0.0F, 1.0F, 0.0F);
+                    GLRenderer.modelM4f().scale(-1, 1, 1);
+                    GLRenderer.modelM4f().translate(-f18 * 0.3F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.4F, -f14 * 0.4F);
+                    GLRenderer.modelM4f().translate(0.8F * f6, -0.75F * f6 - (1.0F - equipProgress) * 0.6F, -0.9F * f6);
+                    GLRenderer.modelM4f().rotateY(Math.toRadians(45F));
                     f14 = MathHelper.sin(swingProgress * swingProgress * MathHelper.PI);
                     f18 = MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI);
 
-                    GL11.glRotatef(f18 * 70F, 0.0F, 1.0F, 0.0F);
-                    GL11.glRotatef(-f14 * 20F, 0.0F, 0.0F, 1.0F);
-                    mc.textureManager.bindDownloadableTexture(mc.thePlayer.skinURL, mc.thePlayer.getEntityTexture(), mc.thePlayer.slimModel ? PlayerSkinParser.instanceAlex : PlayerSkinParser.instanceSteve);
+                    GLRenderer.modelM4f().rotateY(Math.toRadians(f18 * 70F));
+                    GLRenderer.modelM4f().rotateZ(Math.toRadians(-f14 * 20F));
+                    this.mc.textureManager.bindDownloadableTexture(this.mc.thePlayer.skinURL, this.mc.thePlayer.getEntityTexture(), this.mc.thePlayer.slimModel ? PlayerSkinParser.instanceAlex : PlayerSkinParser.instanceSteve);
 
-                    GL11.glTranslatef(-1F, 3.6F, 3.5F);
-                    GL11.glRotatef(120F, 0.0F, 0.0F, 1.0F);
-                    GL11.glRotatef(200F, 1.0F, 0.0F, 0.0F);
-                    GL11.glRotatef(-135F, 0.0F, 1.0F, 0.0F);
-                    GL11.glTranslatef(5.6F, 0.0F, 0.0F);
+                    GLRenderer.modelM4f().translate(-1F, 3.6F, 3.5F);
+                    GLRenderer.modelM4f().rotateZ(Math.toRadians(120F));
+                    GLRenderer.modelM4f().rotateX(Math.toRadians(200F));
+                    GLRenderer.modelM4f().rotateY(Math.toRadians(-135F));
+                    GLRenderer.modelM4f().translate(5.6F, 0.0F, 0.0F);
 
-                    GL11.glPushMatrix();
-                    GL11.glScalef(-1, 1, 1);
-                    GL11.glPushMatrix();
-                    GL11.glScalef(1/16f, 1/16f, -1/16f);
-                    GL11.glTranslatef(0, 16, 0);
-                    GL11.glRotatef(180, 1, 0, 0);
-                    GL11.glTranslatef(0, -16, 0);
-                    GL11.glTranslatef(0, 8, 0);
-                    playerRenderer.drawFirstPersonHand(Tessellator.instance, mc.thePlayer, true);
-                    GL11.glPopMatrix();
-                    GL11.glPopMatrix();
+                    GLRenderer.pushFrame();
+                    GLRenderer.modelM4f().scale(-1, 1, 1);
+                    GLRenderer.modelM4f().scale(1 / 16f, 1 / 16f, -1 / 16f);
+                    GLRenderer.modelM4f().translate(0, 16, 0);
+                    GLRenderer.modelM4f().rotateX(Math.toRadians(180));
+                    GLRenderer.modelM4f().translate(0, -16, 0);
+                    GLRenderer.modelM4f().translate(0, 8, 0);
+                    playerRenderer.drawFirstPersonHand(GLRenderer.getTessellator(), this.mc.thePlayer, true);
+                    GLRenderer.popFrame();
                 } else {
                     float f6 = 0.8F;
                     float swingProgress = player.getSwingProgress(partialTick);
                     float f14 = MathHelper.sin(swingProgress * MathHelper.PI);
                     float f18 = MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI);
-                    GL11.glTranslatef(-f18 * 0.3F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.4F, -f14 * 0.4F);
-                    GL11.glTranslatef(0.8F * f6, -0.75F * f6 - (1.0F - equipProgress) * 0.6F, -0.9F * f6);
-                    GL11.glRotatef(45F, 0.0F, 1.0F, 0.0F);
+                    GLRenderer.modelM4f().translate(-f18 * 0.3F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.4F, -f14 * 0.4F);
+                    GLRenderer.modelM4f().translate(0.8F * f6, -0.75F * f6 - (1.0F - equipProgress) * 0.6F, -0.9F * f6);
+                    GLRenderer.modelM4f().rotateY(Math.toRadians(45F));
                     f14 = MathHelper.sin(swingProgress * swingProgress * MathHelper.PI);
                     f18 = MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI);
-                    GL11.glRotatef(f18 * 70F, 0.0F, 1.0F, 0.0F);
-                    GL11.glRotatef(-f14 * 20F, 0.0F, 0.0F, 1.0F);
-                    mc.textureManager.bindDownloadableTexture(mc.thePlayer.skinURL, mc.thePlayer.getEntityTexture(), mc.thePlayer.slimModel ? PlayerSkinParser.instanceAlex : PlayerSkinParser.instanceSteve);
-                    GL11.glTranslatef(-1F, 3.6F, 3.5F);
-                    GL11.glRotatef(120F, 0.0F, 0.0F, 1.0F);
-                    GL11.glRotatef(200F, 1.0F, 0.0F, 0.0F);
-                    GL11.glRotatef(-135F, 0.0F, 1.0F, 0.0F);
-                    GL11.glTranslatef(5.6F, 0.0F, 0.0F);
-                    GL11.glPushMatrix();
-                    GL11.glScalef(1/16f, 1/16f, -1/16f);
-                    GL11.glTranslatef(0, 16, 0);
-                    GL11.glRotatef(180, 1, 0, 0);
-                    GL11.glTranslatef(0, -16, 0);
-                    GL11.glTranslatef(0, 8, 0);
-                    playerRenderer.drawFirstPersonHand(Tessellator.instance, mc.thePlayer, false);
-                    GL11.glPopMatrix();
+                    GLRenderer.modelM4f().rotateY(Math.toRadians(f18 * 70F));
+                    GLRenderer.modelM4f().rotateZ(Math.toRadians(-f14 * 20F));
+                    this.mc.textureManager.bindDownloadableTexture(this.mc.thePlayer.skinURL, this.mc.thePlayer.getEntityTexture(), this.mc.thePlayer.slimModel ? PlayerSkinParser.instanceAlex : PlayerSkinParser.instanceSteve);
+                    GLRenderer.modelM4f().translate(-1F, 3.6F, 3.5F);
+                    GLRenderer.modelM4f().rotateZ(Math.toRadians(120F));
+                    GLRenderer.modelM4f().rotateX(Math.toRadians(200F));
+                    GLRenderer.modelM4f().rotateY(Math.toRadians(-135F));
+                    GLRenderer.modelM4f().translate(5.6F, 0.0F, 0.0F);
+                    GLRenderer.pushFrame();
+                    GLRenderer.modelM4f().scale(1 / 16f, 1 / 16f, -1 / 16f);
+                    GLRenderer.modelM4f().translate(0, 16, 0);
+                    GLRenderer.modelM4f().rotateX(Math.toRadians(180));
+                    GLRenderer.modelM4f().translate(0, -16, 0);
+                    GLRenderer.modelM4f().translate(0, 8, 0);
+                    playerRenderer.drawFirstPersonHand(GLRenderer.getTessellator(), this.mc.thePlayer, false);
+                    GLRenderer.popFrame();
                 }
             } else {
-                GL11.glPushMatrix();
+                GLRenderer.pushFrame();
                 float swingProgress = player.getSwingProgress(partialTick);
-                GL11.glTranslatef(0, MathHelper.sin(swingProgress * MathHelper.PI * 2 - MathHelper.PI/2)/33f, 0); // Bounces the held object up on swing
-                GL11.glScalef(1, -1f, 1); // Flips y axis because entities are flipped vertically ig
-                GL11.glRotatef(-MathHelper.sin(swingProgress * MathHelper.PI * 2) * 5f, 1, 0, 0); // Slightly rotates the object when swung
-                playerRenderer.drawHeldObject(mc.thePlayer, partialTick);
-                GL11.glPopMatrix();
+                GLRenderer.modelM4f().translate(0, MathHelper.sin(swingProgress * MathHelper.PI * 2 - MathHelper.PI / 2) / 33f, 0); // Bounces the held object up on swing
+                GLRenderer.modelM4f().scale(1, -1f, 1); // Flips y axis because entities are flipped vertically ig
+                GLRenderer.modelM4f().rotateX(Math.toRadians(-MathHelper.sin(swingProgress * MathHelper.PI * 2) * 5f)); // Slightly rotates the object when swung
+                playerRenderer.drawHeldObject(this.mc.thePlayer, partialTick);
+                GLRenderer.popFrame();
             }
-            GL11.glPopMatrix();
-            GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+            GLRenderer.popFrame();
+//            GL11.glDisable(GL12.GL_RESCALE_NORMAL);
         }
         Lighting.disable();
     }
 
-	public void renderOverlays(float partialTicks) {
-    	glDisable(GL_DEPTH_TEST);
-		glDisable(GL_ALPHA_TEST);
-		
-		if(mc.thePlayer.isOnFire()) {
-            TextureRegistry.blockAtlas.bind();
-			renderFireInFirstPerson(partialTicks);
-		}
-		
-		if(mc.thePlayer.isInWall() && !mc.thePlayer.noPhysics) {
-			int blockX = MathHelper.floor(mc.thePlayer.x);
-			int blockY = MathHelper.floor(mc.thePlayer.y);
-			int blockZ = MathHelper.floor(mc.thePlayer.z);
+    public void renderOverlays(float partialTicks) {
+        GLRenderer.disableState(State.DEPTH_TEST);
+//        glDisable(GL_ALPHA_TEST);
 
-            TextureRegistry.blockAtlas.bind();
-			
-			int id = mc.currentWorld.getBlockId(blockX, blockY, blockZ);
-            int meta = mc.currentWorld.getBlockMetadata(blockX, blockY, blockZ);
+        if (this.mc.thePlayer.isOnFire()) {
+            TextureRegistry.worldAtlas.bind();
+            renderFireInFirstPerson(partialTicks);
+        }
+
+        if (this.mc.thePlayer.isInWall() && !this.mc.thePlayer.noPhysics) {
+            int blockX = MathHelper.floor(this.mc.thePlayer.x);
+            int blockY = MathHelper.floor(this.mc.thePlayer.y);
+            int blockZ = MathHelper.floor(this.mc.thePlayer.z);
+
+            TextureRegistry.worldAtlas.bind();
+
+            int id = this.mc.currentWorld.getBlockId(blockX, blockY, blockZ);
+            int meta = this.mc.currentWorld.getBlockMetadata(blockX, blockY, blockZ);
             Block<?> block = Blocks.blocksList[id];
             BlockModel<?> model = BlockModelDispatcher.getInstance().getDispatch(block);
-			if(mc.currentWorld.isBlockNormalCube(blockX, blockY, blockZ)) {
-				renderInsideOfBlock(partialTicks, model.getOverlayTexture(meta));
-			} else {
+            if (this.mc.currentWorld.isBlockNormalCube(blockX, blockY, blockZ)) {
+                renderInsideOfBlock(partialTicks, model.getOverlayTexture(meta));
+            } else {
                 id = 0;
-				for (int i = 0; i < 8; i++) {
-					float x0 = ((float) ((i >> 0) % 2) - 0.5F) * mc.thePlayer.bbWidth * 0.9F;
-					float y0 = ((float) ((i >> 1) % 2) - 0.5F) * mc.thePlayer.bbHeight * 0.2F;
-					float z0 = ((float) ((i >> 2) % 2) - 0.5F) * mc.thePlayer.bbWidth * 0.9F;
-					
-					int x1 = MathHelper.floor_float(blockX + x0);
-					int y1 = MathHelper.floor_float(blockY + y0);
-					int z1 = MathHelper.floor_float(blockZ + z0);
-					
-					if(mc.currentWorld.isBlockNormalCube(x1, y1, z1)) {
-						id = mc.currentWorld.getBlockId(x1, y1, z1);
-                        meta = mc.currentWorld.getBlockMetadata(x1, y1, z1);
+                for (int i = 0; i < 8; i++) {
+                    float x0 = ((float) ((i >> 0) % 2) - 0.5F) * this.mc.thePlayer.bbWidth * 0.9F;
+                    float y0 = ((float) ((i >> 1) % 2) - 0.5F) * this.mc.thePlayer.bbHeight * 0.2F;
+                    float z0 = ((float) ((i >> 2) % 2) - 0.5F) * this.mc.thePlayer.bbWidth * 0.9F;
+
+                    int x1 = MathHelper.floor_float(blockX + x0);
+                    int y1 = MathHelper.floor_float(blockY + y0);
+                    int z1 = MathHelper.floor_float(blockZ + z0);
+
+                    if (this.mc.currentWorld.isBlockNormalCube(x1, y1, z1)) {
+                        id = this.mc.currentWorld.getBlockId(x1, y1, z1);
+                        meta = this.mc.currentWorld.getBlockMetadata(x1, y1, z1);
                         break;
-					}
-				}
-                if(Blocks.blocksList[id] != null) {
+                    }
+                }
+                if (Blocks.blocksList[id] != null) {
                     model = BlockModelDispatcher.getInstance().getDispatch(Blocks.blocksList[id]);
                     renderInsideOfBlock(partialTicks, model.getOverlayTexture(meta));
                 }
-			}
-
-		}
-		if(mc.thePlayer.isUnderLiquid(Materials.WATER)) {
-            mc.textureManager.loadTexture("/assets/minecraft/textures/misc/water.png").bind();
-			renderWarpedTextureOverlay(partialTicks);
-		}
-		glEnable(GL_ALPHA_TEST);
-		glEnable(GL_DEPTH_TEST);
-	}
+            }
+        }
+        if (this.mc.thePlayer.isUnderLiquid(Materials.WATER)) {
+            this.mc.textureManager.loadTexture("/assets/minecraft/textures/misc/water.png").bind();
+            renderWarpedTextureOverlay(partialTicks);
+        }
+//        glEnable(GL_ALPHA_TEST);
+        GLRenderer.enableState(State.DEPTH_TEST);
+    }
 
-	private void renderInsideOfBlock(float partialTicks, IconCoordinate texture) {
+    private void renderInsideOfBlock(float partialTicks, IconCoordinate texture) {
         if (texture == null) return;
-		Tessellator tessellator = Tessellator.instance;
-		
-		float brightness = 0.1f;
-		if(mc.fullbright) {
-			brightness = 1.0f;
-		}
-		glColor4f(brightness, brightness, brightness, 0.5f);
-		glPushMatrix();
-		
-		final float x0 = -1F;
-		final float x1 = 1.0F;
-		final float y0 = -1F;
-		final float y1 = 1.0F;
-		
-		final float z = -0.5F;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+
+        float brightness = 0.1f;
+        if (this.mc.fullbright) {
+            brightness = 1.0f;
+        }
+        GLRenderer.pushFrame();
+        GLRenderer.setColor4f(brightness, brightness, brightness, 0.5f);
+        final float x0 = -1F;
+        final float x1 = 1.0F;
+        final float y0 = -1F;
+        final float y1 = 1.0F;
+
+        final float z = -0.5F;
 
         float u0 = (float) texture.getIconUMin();
-		float v0 = (float) texture.getIconVMin();
-		float u1 = (float) texture.getIconUMax();
-		float v1 = (float) texture.getIconVMax();
-		
-		tessellator.startDrawingQuads();
-		tessellator.addVertexWithUV(x0, y0, z, u1, v1);
-		tessellator.addVertexWithUV(x1, y0, z, u0, v1);
-		tessellator.addVertexWithUV(x1, y1, z, u0, v0);
-		tessellator.addVertexWithUV(x0, y1, z, u1, v0);
-		tessellator.draw();
-		
-		glPopMatrix();
-		glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
-	}
+        float v0 = (float) texture.getIconVMin();
+        float u1 = (float) texture.getIconUMax();
+        float v1 = (float) texture.getIconVMax();
+
+        tessellator.startDrawingQuads();
+        tessellator.addVertexWithUV(x0, y0, z, u1, v1);
+        tessellator.addVertexWithUV(x1, y0, z, u0, v1);
+        tessellator.addVertexWithUV(x1, y1, z, u0, v0);
+        tessellator.addVertexWithUV(x0, y1, z, u1, v0);
+        tessellator.draw();
+        GLRenderer.popFrame();
+    }
 
-    private void renderWarpedTextureOverlay(float f)
-    {
-        Tessellator tessellator = Tessellator.instance;
-        float f1 = mc.thePlayer.getBrightness(f);
-        if (mc.fullbright) f1 = 1.0f;
-        GL11.glColor4f(f1, f1, f1, 0.5F);
-        GL11.glEnable(GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glPushMatrix();
+    private void renderWarpedTextureOverlay(float f) {
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        float f1 = this.mc.thePlayer.getBrightness(f);
+        if (this.mc.fullbright) f1 = 1.0f;
+        GLRenderer.setColor4f(f1, f1, f1, 0.5F);
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         float f2 = 4F;
         float f3 = -1F;
         float f4 = 1.0F;
         float f5 = -1F;
         float f6 = 1.0F;
         float f7 = -0.5F;
-        float f8 = -mc.thePlayer.yRot / 64F;
-        float f9 = mc.thePlayer.xRot / 64F;
+        float f8 = -this.mc.thePlayer.yRot / 64F;
+        float f9 = this.mc.thePlayer.xRot / 64F;
         tessellator.startDrawingQuads();
         tessellator.addVertexWithUV(f3, f5, f7, f2 + f8, f2 + f9);
         tessellator.addVertexWithUV(f4, f5, f7, 0.0F + f8, f2 + f9);
         tessellator.addVertexWithUV(f4, f6, f7, 0.0F + f8, 0.0F + f9);
         tessellator.addVertexWithUV(f3, f6, f7, f2 + f8, 0.0F + f9);
         tessellator.draw();
-        GL11.glPopMatrix();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glDisable(GL_BLEND);
+        GLRenderer.popFrame();
     }
 
-    private void renderFireInFirstPerson(float f)
-    {
-        Tessellator tessellator = Tessellator.instance;
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 0.85F);
-        GL11.glEnable(GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+    private void renderFireInFirstPerson(float f) {
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 0.85F);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         float scale = 1.5f;
-        for(int i = 0; i < 2; i++)
-        {
-            GL11.glPushMatrix();
+        for (int i = 0; i < 2; i++) {
+            GLRenderer.pushFrame();
             IconCoordinate texture = TextureRegistry.getTexture("minecraft:block/fire");
             float uMin = (float) texture.getIconUMin();
             float uMax = (float) texture.getIconUMax();
@@ -292,58 +266,51 @@ public class ItemRenderer
             float yMin = 0.0F - scale / 2.0F;
             float yMax = yMin + scale;
             float f10 = -0.5F;
-            GL11.glTranslatef((float)(-(i * 2 - 1)) * 0.4F, -0.3F, 0.0F);
-            GL11.glRotatef((float)(i * 2 - 1) * 10F, 0.0F, 1.0F, 0.0F);
+            GLRenderer.modelM4f().translate((float) (-(i * 2 - 1)) * 0.4F, -0.3F, 0.0F);
+            GLRenderer.modelM4f().rotateY(Math.toRadians((float) (i * 2 - 1) * 10F));
             tessellator.startDrawingQuads();
             tessellator.addVertexWithUV(xMin, yMin - 0.5, f10, uMax, vMax);
             tessellator.addVertexWithUV(xMax, yMin - 0.5, f10, uMin, vMax);
             tessellator.addVertexWithUV(xMax, yMax, f10, uMin, vMin);
             tessellator.addVertexWithUV(xMin, yMax, f10, uMax, vMin);
             tessellator.draw();
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         }
 
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.disableState(State.BLEND);
     }
 
-    public void updateEquippedItem()
-    {
-        oHeight = height;
-        PlayerLocal entityplayersp = mc.thePlayer;
-        ItemStack itemstack = entityplayersp.inventory.getCurrentItem();
-        boolean flag = lastSlot == entityplayersp.inventory.getCurrentItemIndex() && itemstack == itemToRender;
-        if(itemToRender == null && itemstack == null)
-        {
+    public void updateEquippedItem() {
+        this.oHeight = this.height;
+        PlayerLocal playerLocal = this.mc.thePlayer;
+        ItemStack itemstack = playerLocal.inventory.getCurrentItem();
+        boolean flag = this.lastSlot == playerLocal.inventory.getCurrentItemIndex() && itemstack == this.itemToRender;
+        if (this.itemToRender == null && itemstack == null) {
             flag = true;
         }
-        if(itemstack != null && itemToRender != null && itemstack != itemToRender && itemstack.itemID == itemToRender.itemID && itemstack.getMetadata() == itemToRender.getMetadata())
-        {
-            itemToRender = itemstack;
+        if (itemstack != null && this.itemToRender != null && itemstack != this.itemToRender && itemstack.itemID == this.itemToRender.itemID && itemstack.getMetadata() == this.itemToRender.getMetadata()) {
+            this.itemToRender = itemstack;
             flag = true;
         }
         float f = 0.4F;
         float f1 = flag ? 1.0F : 0.0F;
-        float f2 = f1 - height;
-        if(f2 < -f)
-        {
+        float f2 = f1 - this.height;
+        if (f2 < -f) {
             f2 = -f;
         }
-        if(f2 > f)
-        {
+        if (f2 > f) {
             f2 = f;
         }
-        height += f2;
-        if(height < 0.1F)
-        {
-            itemToRender = itemstack;
-            lastSlot = entityplayersp.inventory.getCurrentItemIndex();
+        this.height += f2;
+        if (this.height < 0.1F) {
+            this.itemToRender = itemstack;
+            this.lastSlot = playerLocal.inventory.getCurrentItemIndex();
         }
     }
 
-    public void resetEquippedProgress()
-    {
-        height = 0.0F;
+    public void resetEquippedProgress() {
+        this.height = 0.0F;
     }
 
     private final Minecraft mc;
diff --git a/game/client/src/main/java/net/minecraft/client/render/Lighting.java b/game/client/src/main/java/net/minecraft/client/render/Lighting.java
index 206bd726c..71754b6de 100644
--- a/game/client/src/main/java/net/minecraft/client/render/Lighting.java
+++ b/game/client/src/main/java/net/minecraft/client/render/Lighting.java
@@ -1,33 +1,28 @@
 package net.minecraft.client.render;
 
-import static org.lwjgl.opengl.GL11.*;
-
-import java.nio.FloatBuffer;
-
-import net.minecraft.client.GLAllocation;
+import net.minecraft.client.render.renderer.GLRenderer;
 import org.jetbrains.annotations.NotNull;
+import org.joml.Math;
 import org.joml.Vector3f;
+import org.joml.Vector4f;
 
-public class Lighting {
-    private static final @NotNull FloatBuffer buffer = GLAllocation.createDirectFloatBuffer(16);
-    private static final @NotNull Vector3f vec = new Vector3f();
-
-    public Lighting() {
+public final class Lighting {
+    private Lighting() {
     }
 
     public static void disable() {
-        glDisable(GL_LIGHTING);
-        glDisable(GL_LIGHT0);
-        glDisable(GL_LIGHT1);
-        glDisable(GL_COLOR_MATERIAL);
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.globalGetLight0().enabled = false;
+        GLRenderer.globalGetLight1().enabled = false;
+//        glDisable(GL_COLOR_MATERIAL);
     }
 
     public static void enableInventoryLight() {
-        glPushMatrix();
-        glRotatef(-30.0f, 0.0F, 1.0F, 0.0F);
-        glRotatef(155.0f, 1.0F, 0.0F, 0.0F);
         enableLight(0.4f, 0.5f);
-        glPopMatrix();
+        GLRenderer.globalGetNormalTransformMatrix()
+            .rotateY(Math.toRadians(-30.0f))
+            .rotateX(Math.toRadians(155.0f))
+            .invert();
     }
 
     public static void enableLight() {
@@ -35,37 +30,55 @@ public class Lighting {
     }
 
     public static void enableLight(float ambientBrightness, float lightBrightness) {
-        glEnable(GL_LIGHTING);
-        glEnable(GL_LIGHT0);
-        glEnable(GL_LIGHT1);
-        glEnable(GL_COLOR_MATERIAL);
-        glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE);
-
-        vec.set(0.2f, 1.0f, -0.7f).normalize();
-        glLightfv(GL_LIGHT0, GL_POSITION, getBuffer(vec.x, vec.y, vec.z, 0.0f));
-        glLightfv(GL_LIGHT0, GL_DIFFUSE, getBuffer(lightBrightness, lightBrightness, lightBrightness, 1.0F));
-        glLightfv(GL_LIGHT0, GL_AMBIENT, getBuffer(0.0F, 0.0F, 0.0F, 1.0F));
-        glLightfv(GL_LIGHT0, GL_SPECULAR, getBuffer(0.0F, 0.0F, 0.0F, 1.0F));
+        GLRenderer.globalGetNormalTransformMatrix().identity();
+        GLRenderer.globalSetLightEnabled(true);
+        GLRenderer.globalGetLight0().enabled = true;
+        GLRenderer.globalGetLight1().enabled = true;
+//        glEnable(GL_COLOR_MATERIAL);
+//        glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE);
 
-        vec.set(-0.2f, 1.0f, 0.7f).normalize();
-        glLightfv(GL_LIGHT1, GL_POSITION, getBuffer(vec.x, vec.y, vec.z, 0.0f));
-        glLightfv(GL_LIGHT1, GL_DIFFUSE, getBuffer(lightBrightness, lightBrightness, lightBrightness, 1.0F));
-        glLightfv(GL_LIGHT1, GL_AMBIENT, getBuffer(0.0F, 0.0F, 0.0F, 1.0F));
-        glLightfv(GL_LIGHT1, GL_SPECULAR, getBuffer(0.0F, 0.0F, 0.0F, 1.0F));
+        GLRenderer.globalGetLight0().position.set(0.2f, 1.0f, -0.7f).normalize();
+        GLRenderer.globalGetLight0().diffuse.set(lightBrightness, lightBrightness, lightBrightness, 1f);
+        GLRenderer.globalGetLight0().ambient.set(0, 0, 0, 1f);
+        GLRenderer.globalGetLight0().specular.set(0, 0, 0, 1f);
 
-        glShadeModel(GL_FLAT);
-        glLightModelfv(GL_LIGHT_MODEL_AMBIENT, getBuffer(ambientBrightness, ambientBrightness, ambientBrightness, 1.0F));
+        GLRenderer.globalGetLight1().position.set(-0.2f, 1f, 0.7f).normalize();
+        GLRenderer.globalGetLight1().diffuse.set(lightBrightness, lightBrightness, lightBrightness, 1f);
+        GLRenderer.globalGetLight1().ambient.set(0, 0, 0, 1f);
+        GLRenderer.globalGetLight1().specular.set(0, 0, 0, 1f);
+//
+//        glShadeModel(GL_FLAT);
+        GLRenderer.globalGetLightModelAmbient().set(ambientBrightness, ambientBrightness, ambientBrightness, 1.0F);
     }
 
-    private static @NotNull FloatBuffer getBuffer(double d1, double d2, double d3, double d4) {
-        return getBuffer((float) d1, (float) d2, (float) d3, (float) d4);
-    }
+    public static class LightSource {
+        public boolean enabled = false;
+        public final @NotNull Vector4f ambient = new Vector4f(0, 0, 0, 1);
+        public final @NotNull Vector4f diffuse = new Vector4f(0, 0, 0, 1);
+        public final @NotNull Vector4f specular = new Vector4f(0, 0, 0, 1);
+        public final @NotNull Vector4f position = new Vector4f(0, 0, 1, 0);
+        public final @NotNull Vector3f spotDirection = new Vector3f(0, 0, -1);
+        public float spotExponent = 0; // [0, 128]
+        public float spotCutoff = 180; // [0, 90] U [180]
+        public float constantAttenuation = 1f;
+        public float linearAttenuation = 0f;
+        public float quadraticAttenuation = 0f;
 
-    private static @NotNull FloatBuffer getBuffer(float f1, float f2, float f3, float f4) {
-        buffer.clear();
-        buffer.put(f1).put(f2).put(f3).put(f4);
-        buffer.flip();
-        return buffer;
-    }
+        public LightSource() {
+            reset();
+        }
 
+        public void reset() {
+            this.ambient.set(0, 0, 0, 1);
+            this.diffuse.set(0, 0, 0, 1);
+            this.specular.set(0, 0, 0, 1);
+            this.position.set(0, 0, 1, 0);
+            this.spotDirection.set(0, 0, -1);
+            this.spotExponent = 0;
+            this.spotCutoff = 180;
+            this.constantAttenuation = 1f;
+            this.linearAttenuation = 0f;
+            this.quadraticAttenuation = 0f;
+        }
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/LightingCache.java b/game/client/src/main/java/net/minecraft/client/render/LightingCache.java
index 13ec0ce71..acfee9305 100644
--- a/game/client/src/main/java/net/minecraft/client/render/LightingCache.java
+++ b/game/client/src/main/java/net/minecraft/client/render/LightingCache.java
@@ -29,6 +29,7 @@ final public class LightingCache {
 
     private Block<?> block;
     private WorldSource access;
+    private final @NotNull TilePos queryPos = new TilePos();
 
     @Deprecated
     public void setupCache(@NotNull Block<?> block, @NotNull WorldSource source, int x, int y, int z) {
@@ -50,29 +51,23 @@ final public class LightingCache {
         final int blockId = this.access.getBlockId(tilePos);
         final Block<?> block = Blocks.getBlock(blockId);
 
-        if (LightmapHelper.isLightmapEnabled() || this.mc.fullbright) {
-            if (this.block.emission >= 15) {
-                return 1.0f;
-            }
-            if (!this.mc.isAmbientOcclusionEnabled()) {
-                return 1.0f;
-            }
-            if (block == null) {
-                return 1.0f;
-            }
-            return 1.0f - block.getAmbientOcclusionStrength(this.access, tilePos);
+        if (this.block.emission >= 15) {
+            return 1.0f;
         }
-        final int emission = Blocks.lightEmission[blockId];
-        final float brightness = this.access.getBrightness(tilePos, emission);
-
-        return Math.min(brightness, (this.mc.isAmbientOcclusionEnabled() && block != null) ? (1 - block.getAmbientOcclusionStrength(this.access, tilePos)) : 1);
+        if (!this.mc.isAmbientOcclusionEnabled()) {
+            return 1.0f;
+        }
+        if (block == null) {
+            return 1.0f;
+        }
+        return 1.0f - block.getAmbientOcclusionStrength(this.access, tilePos);
     }
 
     public float getBrightness(int relX, int relY, int relZ) {
         int index = (relX + CACHE_RANGE) * CACHE_SIZE * CACHE_SIZE + (relY + CACHE_RANGE) * CACHE_SIZE + (relZ + CACHE_RANGE);
 
         if (!this.brightnessCached[index]) {
-            this.brightnessValue[index] = calcBrightness(this.offset.add(relX, relY, relZ, new TilePos()));
+            this.brightnessValue[index] = calcBrightness(this.offset.add(relX, relY, relZ, this.queryPos));
             this.brightnessCached[index] = true;
         }
 
@@ -82,7 +77,7 @@ final public class LightingCache {
     public boolean getOpacity(int relX, int relY, int relZ) {
         int index = (relX + CACHE_RANGE) * CACHE_SIZE * CACHE_SIZE + (relY + CACHE_RANGE) * CACHE_SIZE + (relZ + CACHE_RANGE);
         if (!this.opacityCached[index]) {
-            this.opacityValue[index] = Blocks.solid[this.access.getBlockId(this.offset.add(relX, relY, relZ, new TilePos()))];
+            this.opacityValue[index] = Blocks.solid[this.access.getBlockId(this.offset.add(relX, relY, relZ, this.queryPos))];
             this.opacityCached[index] = true;
         }
         return this.opacityValue[index];
@@ -92,7 +87,7 @@ final public class LightingCache {
         int index = (relX + CACHE_RANGE) * CACHE_SIZE * CACHE_SIZE + (relY + CACHE_RANGE) * CACHE_SIZE + (relZ + CACHE_RANGE);
         if (!this.lightmapCoordCached[index]) {
             int lightEmission = this.block.emission;
-            this.lightmapCoordValue[index] = this.access.getLightmapCoord(this.offset.add(relX, relY, relZ, new TilePos()), lightEmission);
+            this.lightmapCoordValue[index] = this.access.getLightmapCoord(this.offset.add(relX, relY, relZ, this.queryPos), lightEmission);
             this.lightmapCoordCached[index] = true;
         }
         return this.lightmapCoordValue[index];
diff --git a/game/client/src/main/java/net/minecraft/client/render/LightmapHelper.java b/game/client/src/main/java/net/minecraft/client/render/LightmapHelper.java
index b8f4c115d..a7cf0ac3b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/LightmapHelper.java
+++ b/game/client/src/main/java/net/minecraft/client/render/LightmapHelper.java
@@ -1,7 +1,5 @@
 package net.minecraft.client.render;
 
-import static org.lwjgl.opengl.GL13.*;
-
 import java.awt.image.BufferedImage;
 import java.nio.ByteBuffer;
 import java.util.Arrays;
@@ -13,21 +11,15 @@ import net.minecraft.client.gui.ScreenPhotoMode;
 import net.minecraft.client.option.enums.LightmapStyle;
 import net.minecraft.client.util.helper.Textures;
 import net.minecraft.core.util.helper.Buffer;
+import net.minecraft.core.util.helper.Color;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
+import org.lwjgl.opengl.GL41;
 import org.slf4j.Logger;
 
 public class LightmapHelper {
 	private static final Logger LOGGER = LogUtils.getLogger();
 	public static LightmapHelper instance = null;
-	private static int currentSkyCoord = 0;
-	private static int currentBlockCoord = 0;
-	private static int lastSkyCoord = 0;
-	private static int lastBlockCoord = 0;
-
-	public static boolean isLightmapEnabled() {
-		return instance != null && instance.isEnabled();
-	}
 
 	public final Minecraft mc;
 	public final WorldRenderer worldRenderer;
@@ -40,70 +32,69 @@ public class LightmapHelper {
 	public float skyDarkenSmooth;
 
 	public LightmapHelper(Minecraft mc, WorldRenderer worldRenderer) {
+		instance = this;
 		this.mc = mc;
 		this.worldRenderer = worldRenderer;
-		instance = this;
+		Arrays.fill(this.lightmapData, 0xFFFFFFFF);
+		setLightmapTextureData(this.lightmapData);
+		enableLightmapRendering();
 	}
 	
 	public void setup() {
-		World world = mc.currentWorld;
-		if(mc.gameSettings.customLightmap.value && world != null) {
+		World world = this.mc.currentWorld;
+		if(this.mc.gameSettings.customLightmap.value && world != null) {
 			int dimension = world.dimension.id;
 			
 			String path = "/assets/minecraft/textures/environment/lightmap" + dimension + ".png";
 
             LOGGER.info("Attempting to load custom lightmap '{}'", path);
-			customLightmap = mc.textureManager.getImage(path);
+            this.customLightmap = this.mc.textureManager.getImage(path);
 			
-			if(customLightmap == Textures.missingTexture) {
-				customLightmap = null;
+			if(this.customLightmap == Textures.missingTexture) {
+                this.customLightmap = null;
 			}
 			
-			if(customLightmap != null) {
+			if(this.customLightmap != null) {
 				LOGGER.info("Loaded custom lightmap!");
 			}else {
-				LOGGER.warn("No custom lightmap found.");
+				LOGGER.info("No custom lightmap found.");
 			}
 		}else {
-			customLightmap = null;
+            this.customLightmap = null;
 		}
 	}
 
-	public boolean isEnabled() {
-		return mc.gameSettings.lightmapStyle.value != LightmapStyle.DISABLED;
-	}
-	
 	public void tick() {
-		World world = mc.currentWorld;
+		World world = this.mc.currentWorld;
 		if(world == null) {
 			return;
 		}
-		
-		prevSkyDarken = skyDarkenSmooth;
+
+        this.prevSkyDarken = this.skyDarkenSmooth;
 		
 		float skyDarken = world.skyDarken;
 		
 		if(Math.abs(this.skyDarkenSmooth - skyDarken) > 1.5f) {
 			this.skyDarkenSmooth = this.prevSkyDarken = skyDarken;
 		}else {
-			skyDarkenSmooth = MathHelper.lerp(skyDarken, skyDarkenSmooth, 0.99f);
+            this.skyDarkenSmooth = MathHelper.lerp(skyDarken, this.skyDarkenSmooth, 0.99f);
 		}
 	}
 
 	public void update(float partialTicks) {
-		World world = mc.currentWorld;
+		World world = this.mc.currentWorld;
 
-		if(!isEnabled() || world == null) {
+		if(world == null) {
 			return;
 		}
 
-		if(mc.fullbright) {
-            Arrays.fill(lightmapData, 0xFFFFFFFF);
+		if(this.mc.fullbright) {
+            Arrays.fill(this.lightmapData, 0xFFFFFFFF);
 		} else {
-			if(mc.gameSettings.customLightmap.value && customLightmap != null) {
+			if(this.mc.gameSettings.customLightmap.value && this.customLightmap != null) {
 				generateCustomLightmap(world);
 			}else {
-				LightmapStyle lightmapStyle = mc.gameSettings.lightmapStyle.value;
+				LightmapStyle lightmapStyle = this.mc.gameSettings.lightmapStyle.value;
 				
 				if(lightmapStyle == LightmapStyle.COLORIZED) {
 					generateColorizedLightmap(world, partialTicks);
@@ -114,55 +105,28 @@ public class LightmapHelper {
 		}
 
 		OpenGLHelper.checkError("pre generate lightmap");
-		setLightmapTextureData(lightmapData);
+		setLightmapTextureData(this.lightmapData);
 		OpenGLHelper.checkError("generate lightmap");
 	}
 
 	public void disableLightmapRendering() {
-		glClientActiveTexture(GL_TEXTURE1);
-		glActiveTexture(GL_TEXTURE1);
-
-		glDisable(GL_TEXTURE_2D);
-
-		glClientActiveTexture(GL_TEXTURE0);
-		glActiveTexture(GL_TEXTURE0);
+//		glClientActiveTexture(GL_TEXTURE1);
+//		glActiveTexture(GL_TEXTURE1);
+//
+//		glDisable(GL_TEXTURE_2D);
+//
+//		glClientActiveTexture(GL_TEXTURE0);
+//		glActiveTexture(GL_TEXTURE0);
 	}
 
 	public void enableLightmapRendering() {
-		if(!isEnabled()) {
-			return;
-		}
-
-		OpenGLHelper.checkError("pre enable lightmap");
-
-		// Switch active texture
-		glClientActiveTexture(GL_TEXTURE1);
-		glActiveTexture(GL_TEXTURE1);
-
-		// Setup texture matrix
-		glMatrixMode(GL_TEXTURE);
-		glLoadIdentity();
-
-		float scale = 1.0f / 256.0f;
-		glScalef(scale, scale, scale);
-		glTranslatef(8.0f, 8.0f, 8.0f);
-
-		glMatrixMode(GL_MODELVIEW);
-
-		// Bind texture
-		glBindTexture(GL_TEXTURE_2D, lightmapTexture);
-
-		// Back to default texture
-		glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
-		glEnable(GL_TEXTURE_2D);
-		glClientActiveTexture(GL_TEXTURE0);
-		glActiveTexture(GL_TEXTURE0);
-
-		OpenGLHelper.checkError("enable lightmap");
+		GL41.glActiveTexture(GL41.GL_TEXTURE1);
+		GL41.glBindTexture(GL41.GL_TEXTURE_2D, LightmapHelper.instance.lightmapTexture);
+		GL41.glActiveTexture(GL41.GL_TEXTURE0);
 	}
 
 	public void generateGrayLightmap(World world, float partialTicks) {
-		boolean smooth = mc.gameSettings.ambientOcclusion.value;
+		boolean smooth = this.mc.gameSettings.ambientOcclusion.value;
 		
 		for(int i = 0; i < 256; i++) {
 			final int skyLightLevel = i / 16;
@@ -170,9 +134,9 @@ public class LightmapHelper {
 
 			float brightness;
 			
-			if(smooth) {
-				float skyDarken = prevSkyDarken + (skyDarkenSmooth - prevSkyDarken) * partialTicks;
-				if(mc.currentScreen instanceof ScreenPhotoMode) {
+			if(smooth ) {
+				float skyDarken = this.prevSkyDarken + (this.skyDarkenSmooth - this.prevSkyDarken) * partialTicks;
+				if(this.mc.currentScreen instanceof ScreenPhotoMode) {
 					skyDarken = world.skyDarken;
 				}
 				float modifiedSkylight = Math.max(0, skyLightLevel - skyDarken);
@@ -184,20 +148,20 @@ public class LightmapHelper {
 				brightness = world.worldType.getBrightnessRamp()[light];
 			}
 			
-			brightness = applyGamma(brightness, mc.gameSettings.brightness.value - 0.5f);
+			brightness = applyGamma(brightness, this.mc.gameSettings.brightness.value - 0.5f);
 			brightness = MathHelper.clamp(brightness, 0.0f, 1.0f);
 
 			int brightnessI = (int) (brightness * 255);
 
 			int color = 0xFF000000 | brightnessI << 16 | brightnessI << 8 | brightnessI;
 
-			lightmapData[i] = color;
+            this.lightmapData[i] = color;
 		}
 	}
 	
 	public void generateColorizedLightmap(World world, float partialTicks) {
 		float ambientBrightness = world.getAmbientBrightness(partialTicks);
-		float brightness = mc.gameSettings.brightness.value - 0.5f;
+		float brightness = this.mc.gameSettings.brightness.value - 0.5f;
 
 		for(int i = 0; i < 256; i++) {
 			float skyLight = getBrightnessRemoveMinLight(world, i / 16) * (ambientBrightness * 0.95f + 0.05f);
@@ -235,22 +199,22 @@ public class LightmapHelper {
 			green = MathHelper.clamp(green, 0.0f, 1.0f);
 			blue = MathHelper.clamp(blue, 0.0f, 1.0f);
 
-			lightmapData[i] = toIntARGB(red, green, blue);
+            this.lightmapData[i] = Color.floatToIntARGB(1, red, green, blue);
 		}
 	}
 	
 	public void generateCustomLightmap(World world) {
 		float ambientBrightness = (world.getAmbientBrightness(1.0f) - 0.2f) / 0.8f;
-		float brightness = mc.gameSettings.brightness.value;
+		float brightness = this.mc.gameSettings.brightness.value;
 		
-		int skylightX = MathHelper.floor_float(ambientBrightness * (customLightmap.getWidth() - 2));
+		int skylightX = MathHelper.floor_float(ambientBrightness * (this.customLightmap.getWidth() - 2));
 		
 		for(int i=0; i < 256; i++) {
 			int blockLightIndex = i % 16;
 			int skyLightIndex = i / 16;
 			
-			int torchColor = customLightmap.getRGB(0, 16 + blockLightIndex);
-			int skyColor = customLightmap.getRGB(skylightX, skyLightIndex);
+			int torchColor = this.customLightmap.getRGB(0, 16 + blockLightIndex);
+			int skyColor = this.customLightmap.getRGB(skylightX, skyLightIndex);
 			
 			float torchRed   = ((torchColor >> 16) & 0xFF) / 255.0f;
 			float torchGreen = ((torchColor >>  8) & 0xFF) / 255.0f;
@@ -275,8 +239,8 @@ public class LightmapHelper {
 			red = MathHelper.clamp(red, 0.0f, 1.0f);
 			green = MathHelper.clamp(green, 0.0f, 1.0f);
 			blue = MathHelper.clamp(blue, 0.0f, 1.0f);
-			
-			lightmapData[i] = toIntARGB(red, green, blue);
+
+            this.lightmapData[i] = Color.floatToIntARGB(1f, red, green, blue);
 		}
 //		for(int i=0; i < 256; i++) {
 //			lightmapData[i] = 0xFFFF0000;
@@ -293,7 +257,7 @@ public class LightmapHelper {
 		for(int i = 0; i < data.length; i++) {
 			int color = data[i];
 
-			int a = color >> 24;
+			int a = (color >> 24) & 0xFF;
 			int r = (color >> 16) & 0xFF;
 			int g = (color >> 8) & 0xFF;
 			int b = color & 0xFF;
@@ -307,32 +271,24 @@ public class LightmapHelper {
 		buffer.position(0);
 		buffer.limit(16 * 16 * 4);
 
-		if(lightmapTexture == 0) {
-			lightmapTexture = GLAllocation.generateTexture();
-			glBindTexture(GL_TEXTURE_2D, lightmapTexture);
-			glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 16, 16, 0, GL_RGBA, GL_UNSIGNED_BYTE, (ByteBuffer) null);
+		if(this.lightmapTexture == 0) {
+            this.lightmapTexture = GLAllocation.generateTexture();
+			GL41.glBindTexture(GL41.GL_TEXTURE_2D, this.lightmapTexture);
+			GL41.glTexImage2D(GL41.GL_TEXTURE_2D, 0, GL41.GL_RGBA, 16, 16, 0, GL41.GL_RGBA, GL41.GL_UNSIGNED_BYTE, 0);
 		}
 
-		glBindTexture(GL_TEXTURE_2D, lightmapTexture);
-		glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 16, 16, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
+		GL41.glBindTexture(GL41.GL_TEXTURE_2D, this.lightmapTexture);
+		GL41.glTexSubImage2D(GL41.GL_TEXTURE_2D, 0, 0, 0, 16, 16, GL41.GL_RGBA, GL41.GL_UNSIGNED_BYTE, buffer);
 
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
+		GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MIN_FILTER, GL41.GL_LINEAR);
+		GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MAG_FILTER, GL41.GL_LINEAR);
 
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
+		GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_S, GL41.GL_CLAMP_TO_EDGE);
+		GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_T, GL41.GL_CLAMP_TO_EDGE);
 
 		OpenGLHelper.checkError("set lightmap data");
 	}
 
-	public int toIntARGB(float red, float green, float blue) {
-		int a = 255;
-		int r = (int) (red * 255);
-		int g = (int) (green * 255);
-		int b = (int) (blue * 255);
-		return (a << 24) | (r << 16) | (g << 8) | b;
-	}
-
 	public float applyGamma(float color, float gamma) {
 		float color2 = 1.0f - color;
 		color2 = 1.0f - color2 * color2 * color2 * color2;
@@ -388,39 +344,6 @@ public class LightmapHelper {
 		return avg(avg(lmc0, lmc1), avg(lmc2, lmc3));
 	}
 	
-	public static void setLightmapCoord(int skylight, int blocklight) {
-		glMultiTexCoord2f(GL_TEXTURE1, blocklight * 16.0f, skylight * 16.0f);
-
-		lastBlockCoord = currentBlockCoord;
-		lastSkyCoord = currentSkyCoord;
-		currentBlockCoord = blocklight * 16;
-		currentSkyCoord = skylight * 16;
-	}
-	
-	public static void setLightmapCoord(int lightmapCoord) {
-		int sky = lightmapCoord >> 16;
-		int block = lightmapCoord & 0xFFFF;
-		
-		glMultiTexCoord2f(GL_TEXTURE1, block, sky);
-
-		lastBlockCoord = currentBlockCoord;
-		lastSkyCoord = currentSkyCoord;
-		currentBlockCoord = block;
-		currentSkyCoord = sky;
-	}
-
-	public static void setLastLightmapCoord() {
-		int sky = lastSkyCoord;
-		int block = lastBlockCoord;
-
-		glMultiTexCoord2f(GL_TEXTURE1, block, sky);
-
-		lastBlockCoord = currentBlockCoord;
-		lastSkyCoord = currentSkyCoord;
-		currentBlockCoord = block;
-		currentSkyCoord = sky;
-	}
-	
 	public static int setBlocklightValue(int lightmapCoord, int blocklight) {
 		return lightmapCoord & 0xFFFF0000 | blocklight << 4;
 	}
diff --git a/game/client/src/main/java/net/minecraft/client/render/LoadingScreenRenderer.java b/game/client/src/main/java/net/minecraft/client/render/LoadingScreenRenderer.java
index 3614e14aa..01fa9f477 100644
--- a/game/client/src/main/java/net/minecraft/client/render/LoadingScreenRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/LoadingScreenRenderer.java
@@ -1,26 +1,27 @@
 package net.minecraft.client.render;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.util.List;
 import java.util.Random;
 
-import org.lwjgl.opengl.GL11;
+import net.minecraft.client.option.GameSettings;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.option.KeyBinding;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.MinecraftError;
 import net.minecraft.core.lang.I18n;
 import net.minecraft.core.net.command.TextFormatting;
 import net.minecraft.core.world.Dimension;
 import net.minecraft.core.world.ProgressListener;
+import org.lwjgl.opengl.GL41;
 
 public class LoadingScreenRenderer
-    implements ProgressListener
-{
+    implements ProgressListener {
     private String stage = "";
-    private Minecraft minecraft;
+    private final Minecraft minecraft;
     private String title = "";
     private long startTime = System.currentTimeMillis();
     private boolean canStop = false;
@@ -28,30 +29,26 @@ public class LoadingScreenRenderer
     private int startStackDepth = 0;
     private String tip = "";
 
-    public LoadingScreenRenderer(Minecraft minecraft)
-    {
+    public LoadingScreenRenderer(Minecraft minecraft) {
         this.minecraft = minecraft;
     }
 
-    public void progressStartNoAbort(String title)
-    {
-        startStackDepth++;
-        canStop = false;
+    public void progressStartNoAbort(String title) {
+        this.startStackDepth++;
+        this.canStop = false;
         initialize(title);
     }
 
     @Override
-    public void progressStart(String title)
-    {
-        startStackDepth++;
-        canStop = true;
+    public void progressStart(String title) {
+        this.startStackDepth++;
+        this.canStop = true;
         initialize(title);
     }
 
     @Override
-    public void progressStop()
-    {
-        startStackDepth--;
+    public void progressStop() {
+        this.startStackDepth--;
     }
 
     private String parseTip(String tip) {
@@ -60,7 +57,7 @@ public class LoadingScreenRenderer
             if (s.startsWith("%")) {
                 KeyBinding binding = null;
                 String sub = s.substring(1);
-                for (KeyBinding b : minecraft.gameSettings.keys) {
+                for (KeyBinding b : GameSettings.keys) {
                     if (b.getId().equals(sub)) {
                         binding = b;
                         break;
@@ -75,143 +72,116 @@ public class LoadingScreenRenderer
         return tip;
     }
 
-    private void initialize(String title)
-    {
-        if(!minecraft.running)
-        {
-            if(!canStop)
-            {
+    private void initialize(String title) {
+        if (!this.minecraft.running) {
+            if (!this.canStop) {
                 throw new MinecraftError();
             }
-        }
-        else
-        {
+        } else {
             this.title = title;
-            if (startStackDepth <= 1)
-            {
+            if (this.startStackDepth <= 1) {
                 List<String> tips = I18n.getInstance().getCurrentLanguage().getTips();
                 String tipPre = TextFormatting.YELLOW + I18n.getInstance().translateKey("progress.tip");
                 String tipText = parseTip(tips.get(new Random().nextInt(tips.size())));
                 String tipMain = TextFormatting.WHITE + tipText;
-                tip = tipPre.replace("%s", tipMain);
+                this.tip = tipPre.replace("%s", tipMain);
             }
-            GL11.glClear(GL_DEPTH_BUFFER_BIT);
-            GL11.glMatrixMode(GL_PROJECTION);
-            GL11.glLoadIdentity();
-            GL11.glOrtho(0.0D, minecraft.resolution.getExactScaledWidthScreenCoords(), minecraft.resolution.getExactScaledHeightScreenCoords(), 0.0D, 100D, 300D);
-            GL11.glMatrixMode(GL_MODELVIEW);
-            GL11.glLoadIdentity();
-            GL11.glTranslatef(0.0F, 0.0F, -200F);
+            GL41.glClear(GL41.GL_DEPTH_BUFFER_BIT);
+            GLRenderer.projectionM4f().identity().ortho(0.0f, (float) this.minecraft.resolution.getExactScaledWidthScreenCoords(), (float) this.minecraft.resolution.getExactScaledHeightScreenCoords(), 0.0f, 100f, 300f);
+            GLRenderer.viewM4f().identity().translate(0.0F, 0.0F, -200F);
         }
     }
 
-    public void updateLoadingBackground(Dimension dimension)
-    {
-        if (dimension == Dimension.NETHER)
-        {
-            backgroundPath = "/assets/minecraft/textures/gui/background-loading-nether.png";
-        }
-        else if (dimension == Dimension.DRIFT)
-        {
-            backgroundPath = "/assets/minecraft/textures/gui/background-loading-drift.png";
-        }
-        else
-        {
-            backgroundPath = "/assets/minecraft/textures/gui/background.png";
+    public void updateLoadingBackground(Dimension dimension) {
+        if (dimension == Dimension.NETHER) {
+            this.backgroundPath = "/assets/minecraft/textures/gui/background-loading-nether.png";
+        } else if (dimension == Dimension.DRIFT) {
+            this.backgroundPath = "/assets/minecraft/textures/gui/background-loading-drift.png";
+        } else {
+            this.backgroundPath = "/assets/minecraft/textures/gui/background.png";
         }
     }
 
     @Override
-    public void progressStage(String stage)
-    {
-        if(!minecraft.running)
-        {
-            if(!canStop)
-            {
+    public void progressStage(String stage) {
+        if (!this.minecraft.running) {
+            if (!this.canStop) {
                 throw new MinecraftError();
             }
-        }
-        else
-        {
-            startTime = 0L;
+        } else {
+            this.startTime = 0L;
             this.stage = stage;
             progressStagePercentage(-1);
-            startTime = 0L;
+            this.startTime = 0L;
         }
     }
 
     @Override
-    public void progressStagePercentage(int progress)
-    {
-        if(!minecraft.running)
-        {
-            if(!canStop)
-            {
+    public void progressStagePercentage(int progress) {
+        if (!this.minecraft.running) {
+            if (!this.canStop) {
                 throw new MinecraftError();
             }
         }
         long time = System.currentTimeMillis();
-        if(time - startTime < 20L)
-        {
+        if (time - this.startTime < 20L) {
             return;
         }
-        startTime = time;
+        this.startTime = time;
 
-        minecraft.renderer.beginRenderGame(1.0f);
-    	glEnable(GL_ALPHA_TEST);
+        this.minecraft.renderer.beginRenderGame(1.0f);
+//    	glEnable(GL_ALPHA_TEST);
 
         // Set up background
-        int width = minecraft.resolution.getScaledWidthScreenCoords();
-        int height = minecraft.resolution.getScaledHeightScreenCoords();
-        GL11.glDisable(GL11.GL_DEPTH_TEST);
-        GL11.glMatrixMode(GL_PROJECTION);
-        GL11.glLoadIdentity();
-        GL11.glOrtho(0.0D, minecraft.resolution.getExactScaledWidthScreenCoords(), minecraft.resolution.getExactScaledHeightScreenCoords(), 0.0D, 100D, 300D);
-        GL11.glMatrixMode(GL_MODELVIEW);
-        GL11.glLoadIdentity();
-        GL11.glTranslatef(0.0F, 0.0F, -200F);
-        Tessellator t = Tessellator.instance;
-        minecraft.textureManager.loadTexture(backgroundPath).bind();
+        int width = this.minecraft.resolution.getScaledWidthScreenCoords();
+        int height = this.minecraft.resolution.getScaledHeightScreenCoords();
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.projectionM4f().identity().ortho(0.0f, (float) this.minecraft.resolution.getExactScaledWidthScreenCoords(), (float) this.minecraft.resolution.getExactScaledHeightScreenCoords(), 0.0f, 100f, 300f);
+        GLRenderer.viewM4f().identity().translate(0.0F, 0.0F, -200F);
+        GLRenderer.modelM4f().identity();
+
+        TessellatorGeneral t = GLRenderer.getTessellator();
+        this.minecraft.textureManager.loadTexture(this.backgroundPath).bind();
         float f = 32F;
 
         // Draw background
         t.startDrawingQuads();
-        t.setColorOpaque_I(0x404040);
-        t.addVertexWithUV(0.0D, height, 0.0D, 0.0D, (float)height / f);
-        t.addVertexWithUV(width, height, 0.0D, (float)width / f, (float)height / f);
-        t.addVertexWithUV(width, 0.0D, 0.0D, (float)width / f, 0.0D);
+        t.setColorOpaque1i(0x404040);
+        t.addVertexWithUV(0.0D, height, 0.0D, 0.0D, (float) height / f);
+        t.addVertexWithUV(width, height, 0.0D, (float) width / f, (float) height / f);
+        t.addVertexWithUV(width, 0.0D, 0.0D, (float) width / f, 0.0D);
         t.addVertexWithUV(0.0D, 0.0D, 0.0D, 0.0D, 0.0D);
         t.draw();
 
         // Draw progress bar
-        if(progress >= 0)
-        {
+        if (progress >= 0) {
             byte barWidth = 100;
             byte barHeight = 2;
             int x = width / 2 - barWidth / 2;
             int y = height / 2 + 16;
-            GL11.glDisable(GL_TEXTURE_2D);
+            GLRenderer.pushFrame();
+            GLRenderer.setShader(Shaders.COLOR);
             t.startDrawingQuads();
-            t.setColorOpaque_I(0x808080);
+            t.setColorOpaque1i(0x808080);
             t.addVertex(x, y, 0.0D);
             t.addVertex(x, y + barHeight, 0.0D);
             t.addVertex(x + barWidth, y + barHeight, 0.0D);
             t.addVertex(x + barWidth, y, 0.0D);
-            t.setColorOpaque_I(0x80FF80);
+            t.setColorOpaque1i(0x80FF80);
             t.addVertex(x, y, 0.0D);
             t.addVertex(x, y + barHeight, 0.0D);
             t.addVertex(x + progress, y + barHeight, 0.0D);
             t.addVertex(x + progress, y, 0.0D);
             t.draw();
-            GL11.glEnable(GL_TEXTURE_2D);
+            GLRenderer.popFrame();
         }
 
         // Draw title and stage
-        this.minecraft.font.renderCentered(t, this.title, width / 2, height / 2 - 4 - 16).setShadow().call();
-        this.minecraft.font.renderCentered(t, this.stage, width / 2, (height / 2 - 4) + 8).setShadow().call();
+        this.minecraft.font.renderCentered(this.title, width / 2, height / 2 - 4 - 16).setShadow().call();
+        this.minecraft.font.renderCentered(this.stage, width / 2, (height / 2 - 4) + 8).setShadow().call();
 
         // Draw tip
-        this.minecraft.font.renderCentered(t, this.tip, width / 2, (height / 2 - 4) + 32).setShadow().call();
+        this.minecraft.font.renderCentered(this.tip, width / 2, (height / 2 - 4) + 32).setShadow().call();
 
         this.minecraft.renderer.endRenderGame(1.0f);
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/MapItemRenderer.java b/game/client/src/main/java/net/minecraft/client/render/MapItemRenderer.java
index 13a77552e..5fe1a6c41 100644
--- a/game/client/src/main/java/net/minecraft/client/render/MapItemRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/MapItemRenderer.java
@@ -4,18 +4,20 @@ import java.awt.image.BufferedImage;
 import java.util.Iterator;
 
 import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.TextureBuffered;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.material.MaterialColor;
 import net.minecraft.core.util.helper.Color;
 import net.minecraft.client.util.helper.Colors;
 import net.minecraft.core.world.saveddata.maps.ItemMapSavedData;
 import net.minecraft.core.world.saveddata.maps.MapWaypoint;
+import org.joml.Math;
 import org.lwjgl.opengl.GL11;
 
-public class MapItemRenderer
-{
+public class MapItemRenderer {
     public static final int IMAGE_WIDTH = 128;
     public static final int IMAGE_HEIGHT = 128;
     public static final int IMAGE_AREA = 128 * 128;
@@ -23,33 +25,28 @@ public class MapItemRenderer
     private final int[] mapImageData;
     private TextureBuffered mapTexture;
 
-    public MapItemRenderer()
-    {
-        mapImageData = new int[IMAGE_AREA];
+    public MapItemRenderer() {
+        this.mapImageData = new int[IMAGE_AREA];
     }
 
     public void preRender() {
-        if (mapTexture == null) {
-            mapTexture = Minecraft.getMinecraft().textureManager.loadBufferedTexture(new BufferedImage(128, 128, 2));
-            for(int i = 0; i < IMAGE_AREA; i++)
-            {
-                mapImageData[i] = 0;
+        if (this.mapTexture == null) {
+            this.mapTexture = Minecraft.getMinecraft().textureManager.loadBufferedTexture(new BufferedImage(128, 128, 2));
+            for (int i = 0; i < IMAGE_AREA; i++) {
+                this.mapImageData[i] = 0;
             }
         }
     }
 
-    public void renderMap(Tessellator tessellator, ItemMapSavedData data, float brightness)
-    {
+    public void renderMap(TessellatorGeneral tessellator, ItemMapSavedData data) {
         preRender();
         TextureManager textureManager = Minecraft.getMinecraft().textureManager;
-        for(int i = 0; i < IMAGE_AREA; i++)
-        {
+        for (int i = 0; i < IMAGE_AREA; i++) {
             int colorIndex = data.colors[i];
             //value is divided by 4 to get the map colour id
-            if(colorIndex >> 2 == 0)
-            {
+            if (colorIndex >> 2 == 0) {
                 //if blank, render checkerboard texture
-                mapImageData[i] = (i + i / 128 & 1) * 8 + 16 << 24;
+                this.mapImageData[i] = (i + i / 128 & 1) * 8 + 16 << 24;
                 continue;
             }
             int col = MaterialColor.getColorFromIndex(colorIndex >> 2);
@@ -58,55 +55,52 @@ public class MapItemRenderer
 
             int shade = 220;
             // if higher shade
-            if(i1 == 2)
-            {
+            if (i1 == 2) {
                 shade = 255;
             }
             // if lower shade
-            if(i1 == 0)
-            {
+            if (i1 == 0) {
                 shade = 180;
             }
 
 
-            int red =   (Color.redFromInt(col)   * shade) / 255;
+            int red = (Color.redFromInt(col) * shade) / 255;
             int green = (Color.greenFromInt(col) * shade) / 255;
-            int blue =  (Color.blueFromInt(col)  * shade) / 255;
-            mapImageData[i] = Color.intToIntARGB(255, red, green, blue);
+            int blue = (Color.blueFromInt(col) * shade) / 255;
+            this.mapImageData[i] = Color.intToIntARGB(255, red, green, blue);
         }
 
 
-        textureManager.updateTextureData(mapImageData, 128, 128, mapTexture.id());
+        textureManager.updateTextureData(this.mapImageData, 128, 128, this.mapTexture.id());
         int j = 0;
         int k = 0;
         float f = 0.0F;
         //renders the map
-        mapTexture.bind();
-        GL11.glEnable(GL11.GL_BLEND);
+        this.mapTexture.bind();
+        GLRenderer.enableState(State.BLEND);
         GL11.glDisable(GL11.GL_ALPHA_TEST);
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV((float)(j) + f, (float)(k + 128) - f, -0.01D, 0.0D, 1.0D);
-        tessellator.addVertexWithUV((float)(j + 128) - f, (float)(k + 128) - f, -0.01D, 1.0D, 1.0D);
-        tessellator.addVertexWithUV((float)(j + 128) - f, (float)(k) + f, -0.01D, 1.0D, 0.0D);
-        tessellator.addVertexWithUV((float)(j) + f, (float)(k) + f, -0.01D, 0.0D, 0.0D);
+        tessellator.addVertexWithUV((float) (j) + f, (float) (k + 128) - f, -0.01D, 0.0D, 1.0D);
+        tessellator.addVertexWithUV((float) (j + 128) - f, (float) (k + 128) - f, -0.01D, 1.0D, 1.0D);
+        tessellator.addVertexWithUV((float) (j + 128) - f, (float) (k) + f, -0.01D, 1.0D, 0.0D);
+        tessellator.addVertexWithUV((float) (j) + f, (float) (k) + f, -0.01D, 0.0D, 0.0D);
         tessellator.draw();
         GL11.glEnable(GL11.GL_ALPHA_TEST);
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.disableState(State.BLEND);
         textureManager.bindTexture(textureManager.loadTexture("/assets/minecraft/textures/misc/mapicons.png"));
 
-        for(Iterator<MapWaypoint> iterator = data.mapWaypoints.iterator(); iterator.hasNext(); GL11.glPopMatrix())
-        {
+        for (Iterator<MapWaypoint> iterator = data.mapWaypoints.iterator(); iterator.hasNext(); GL11.glPopMatrix()) {
             MapWaypoint mapWaypoint = iterator.next();
-            GL11.glPushMatrix();
-            GL11.glTranslatef((float)j + (float)mapWaypoint.mapCoordX / 2.0F + 64, (float)k + (float)mapWaypoint.mapCoordZ / 2.0F + 64, -0.02F);
-            GL11.glRotatef((float)(8 * 360) / 16F , 0.0F, 0.0F, 1.0F);
-            GL11.glScalef(4F, 4F, 3F);
-            GL11.glTranslatef(-0.125F, 0.125F, 0.0F);
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().translate((float) j + (float) mapWaypoint.mapCoordX / 2.0F + 64, (float) k + (float) mapWaypoint.mapCoordZ / 2.0F + 64, -0.02F);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians((8 * 360) / 16F));
+            GLRenderer.modelM4f().scale(4F, 4F, 3F);
+            GLRenderer.modelM4f().translate(-0.125F, 0.125F, 0.0F);
             double zIndex = 0.0d;
-            float f1 = (float)(5 % 4) / 4F;
-            float f2 = (float)(5 / 4) / 4F;
-            float f3 = (float)(5 % 4 + 1) / 4F;
-            float f4 = (float)(5 / 4 + 1) / 4F;
+            float f1 = (float) (5 % 4) / 4F;
+            float f2 = (float) (5 / 4) / 4F;
+            float f3 = (float) (5 % 4 + 1) / 4F;
+            float f4 = (float) (5 / 4 + 1) / 4F;
             tessellator.startDrawingQuads();
             tessellator.addVertexWithUV(-1D, 1.0D, zIndex, f1, f2);
             tessellator.addVertexWithUV(1.0D, 1.0D, zIndex, f3, f2);
@@ -116,19 +110,18 @@ public class MapItemRenderer
         }
         //renders map icons
         textureManager.bindTexture(textureManager.loadTexture("/assets/minecraft/textures/misc/mapicons.png"));
-        for(Iterator<ItemMapSavedData.MapDecoration> iterator = data.decorations.iterator(); iterator.hasNext(); GL11.glPopMatrix())
-        {
+        for (Iterator<ItemMapSavedData.MapDecoration> iterator = data.decorations.iterator(); iterator.hasNext(); GLRenderer.popFrame()) {
             ItemMapSavedData.MapDecoration decoration = iterator.next();
-            GL11.glPushMatrix();
-            GL11.glTranslatef((float)j + (float)decoration.x / 2.0F + 64, (float)k + (float)decoration.y / 2.0F + 64, -0.02F);
-            GL11.glRotatef((decoration.rot * 360F) / ItemMapSavedData.MapDecoration.ROTATION_STEPS, 0.0F, 0.0F, 1.0F);
-            GL11.glScalef(4F, 4F, 3F);
-            GL11.glTranslatef(-0.125F, 0.125F, 0.0F);
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().translate((float) j + (float) decoration.x / 2.0F + 64, (float) k + (float) decoration.y / 2.0F + 64, -0.02F);
+            GLRenderer.modelM4f().rotateZ((decoration.rot * Math.PI_TIMES_2_f) / ItemMapSavedData.MapDecoration.ROTATION_STEPS);
+            GLRenderer.modelM4f().scale(4F, 4F, 3F);
+            GLRenderer.modelM4f().translate(-0.125F, 0.125F, 0.0F);
             double zIndex = -1.0d;
-            float f1 = (float)(decoration.type % 4) / 4F;
-            float f2 = (float)(decoration.type / 4) / 4F;
-            float f3 = (float)(decoration.type % 4 + 1) / 4F;
-            float f4 = (float)(decoration.type / 4 + 1) / 4F;
+            float f1 = (float) (decoration.type % 4) / 4F;
+            float f2 = (float) (decoration.type / 4) / 4F;
+            float f3 = (float) (decoration.type % 4 + 1) / 4F;
+            float f4 = (float) (decoration.type / 4 + 1) / 4F;
 
             tessellator.startDrawingQuads();
             tessellator.addVertexWithUV(-1D, 1.0D, zIndex, f1, f2);
@@ -138,47 +131,47 @@ public class MapItemRenderer
             tessellator.draw();
 
 
-            GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
+            GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f);
         }
-        GL11.glPushMatrix();
+        GLRenderer.pushFrame();
 
         textureManager.bindTexture(textureManager.loadTexture("/assets/minecraft/textures/misc/flagicon.png"));
         // begin drawing flag colors
-        for(Iterator<MapWaypoint> iterator = data.mapWaypoints.iterator(); iterator.hasNext(); GL11.glPopMatrix()) {
+        for (Iterator<MapWaypoint> iterator = data.mapWaypoints.iterator(); iterator.hasNext(); GL11.glPopMatrix()) {
             MapWaypoint mapWaypoint = iterator.next();
-            GL11.glPushMatrix();
+            GLRenderer.pushFrame();
             for (int y = 0; y < 3; y++) {
                 for (int x = 0; x < 3; x++) {
-					Color color = Colors.allFlagColors[15 - mapWaypoint.colors[x * 3 + y]];
-                	float red = color.getRed() / 255.0f;
-                	float green = color.getGreen() / 255.0f;
-                	float blue = color.getBlue() / 255.0f;
-                	GL11.glColor4f(red * brightness, green * brightness, blue * brightness, 1.0f);
-                    GL11.glPushMatrix();
-                    GL11.glTranslatef((float) (j + x % 3) + (float) (mapWaypoint.mapCoordX) / 2.0F + 64F, (float) (k + y % 3) + (float) (mapWaypoint.mapCoordZ) / 2.0F + 64F, -0.0F);
-                    GL11.glRotatef((float) (8 * 360) / 16F, 0.0F, 0.0F, 1.0F);
-                    GL11.glScalef(0.5F, 0.5F, 0.5F);
-                    GL11.glTranslatef(0.0F, 4F, 0.0F);
+                    Color color = Colors.allFlagColors[15 - mapWaypoint.colors[x * 3 + y]];
+                    float red = color.getRed() / 255.0f;
+                    float green = color.getGreen() / 255.0f;
+                    float blue = color.getBlue() / 255.0f;
+                    GLRenderer.setColor4f(red, green, blue, 1.0f);
+                    GLRenderer.pushFrame();
+                    GLRenderer.modelM4f().translate((float) (j + x % 3) + (float) (mapWaypoint.mapCoordX) / 2.0F + 64F, (float) (k + y % 3) + (float) (mapWaypoint.mapCoordZ) / 2.0F + 64F, -0.0F);
+                    GLRenderer.modelM4f().rotateZ(Math.toRadians((8 * 360) / 16F));
+                    GLRenderer.modelM4f().scale(0.5F, 0.5F, 0.5F);
+                    GLRenderer.modelM4f().translate(0.0F, 4F, 0.0F);
                     double zIndex = -0.1d;
-                    float flagXMin = (float) ((x+y) % 4) / 4F;
-                    float flagYMin = (float) ((x+y) / 4) / 4F;
-                    float flagXMax = (float) ((x+y) % 4 + 1) / 4F;
-                    float flagYMax = (float) ((x+y) / 4 + 1) / 4F;
+                    float flagXMin = (float) ((x + y) % 4) / 4F;
+                    float flagYMin = (float) ((x + y) / 4) / 4F;
+                    float flagXMax = (float) ((x + y) % 4 + 1) / 4F;
+                    float flagYMax = (float) ((x + y) / 4 + 1) / 4F;
                     tessellator.startDrawingQuads();
                     tessellator.addVertexWithUV(-1D, 1.0D, zIndex, flagXMin, flagYMin);
                     tessellator.addVertexWithUV(1.0D, 1.0D, zIndex, flagXMax, flagYMin);
                     tessellator.addVertexWithUV(1.0D, -1D, zIndex, flagXMax, flagYMax);
                     tessellator.addVertexWithUV(-1D, -1D, zIndex, flagXMin, flagYMax);
                     tessellator.draw();
-                    GL11.glPopMatrix();
+                    GLRenderer.popFrame();
                 }
             }
         }
 
-        GL11.glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
-        GL11.glTranslatef(0.0F, 0.0F, -0.04F);
-        GL11.glScalef(1.0F, 1.0F, 1.0F);
+        GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f);
+        GLRenderer.modelM4f().translate(0.0F, 0.0F, -0.04F);
+        GLRenderer.modelM4f().scale(1.0F, 1.0F, 1.0F);
         //field_28160_d.drawString("X: " + (int)entityplayer.posX + " Z: " + (int)entityplayer.posZ, j, k, 0xff000000);
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/OpenGLHelper.java b/game/client/src/main/java/net/minecraft/client/render/OpenGLHelper.java
index 5f44c9b2f..fedbe58df 100644
--- a/game/client/src/main/java/net/minecraft/client/render/OpenGLHelper.java
+++ b/game/client/src/main/java/net/minecraft/client/render/OpenGLHelper.java
@@ -1,100 +1,82 @@
 package net.minecraft.client.render;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.util.HashSet;
 import java.util.Set;
 
 import com.mojang.logging.LogUtils;
 import net.minecraft.core.Global;
+import net.minecraft.core.enums.EnumOS;
+import org.jetbrains.annotations.NotNull;
 import org.lwjgl.opengl.ARBFramebufferObject;
 import org.lwjgl.opengl.ContextCapabilities;
+import org.lwjgl.opengl.GL41;
+import org.lwjgl.opengl.GLCapabilities;
 import org.lwjgl.opengl.GLContext;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.shader.Shaders;
 import org.slf4j.Logger;
 
 public class OpenGLHelper {
-	private static final Logger LOGGER = LogUtils.getLogger();
-	private static final Set<String> errors = new HashSet<>();
-	
-	public static boolean enableOcclusionCheck = false;
-	public static boolean enableSphericalFog = false;
-	public static boolean gl20 = false;
-	public static boolean gl31 = false;
-	public static boolean gl32 = false;
-	public static boolean gl43 = false;
+    private static final Logger LOGGER = LogUtils.getLogger();
+    private static final Set<String> errors = new HashSet<>();
+
+    public static int[] versionPairs = new int[] {4, 6, 4, 3, 4, 1};
 
-    public static void testCapabilities(Minecraft minecraft) {
-		LOGGER.info("");
-		LOGGER.info("=== GPU VENDOR INFO ===");
-        LOGGER.info(glGetString(GL_VERSION));
-        LOGGER.info(glGetString(GL_VENDOR));
-        LOGGER.info(glGetString(GL_RENDERER));
+    public static boolean gl46 = false;
+    public static boolean gl43 = false;
 
-		LOGGER.info("");
+    public static void testCapabilities(@NotNull GLCapabilities capabilities) {
+        LOGGER.info("");
+        LOGGER.info("=== GPU VENDOR INFO ===");
+        LOGGER.info("OpenGL {}.{}", GL41.glGetInteger(GL41.GL_MAJOR_VERSION), GL41.glGetInteger(GL41.GL_MINOR_VERSION));
+        LOGGER.info(GL41.glGetString(GL41.GL_VERSION));
+        LOGGER.info(GL41.glGetString(GL41.GL_VENDOR));
+        LOGGER.info(GL41.glGetString(GL41.GL_RENDERER));
+
+        LOGGER.info("");
 
-        ContextCapabilities capabilities = GLContext.getCapabilities();
         LOGGER.info("GL_ARB_framebuffer_object: {}", capabilities.GL_ARB_framebuffer_object);
         LOGGER.info("GL_ARB_occlusion_query: {}", capabilities.GL_ARB_occlusion_query);
         LOGGER.info("GL_NV_fog_distance: {}", capabilities.GL_NV_fog_distance);
-        
-        enableOcclusionCheck = capabilities.GL_ARB_occlusion_query;
-        enableSphericalFog = capabilities.GL_NV_fog_distance;
-        gl20 = capabilities.OpenGL20;
-        gl31 = capabilities.OpenGL31;
-        gl32 = capabilities.OpenGL32;
-		gl43 = capabilities.OpenGL43;
 
-		LOGGER.info("");
-        
-		if(minecraft.gameSettings.disableShaders.value) {
-			Shaders.enableShaders = false;
-			LOGGER.warn("Shaders disabled in options file!");
-			return;
-		}
-		
-		Shaders.enableShaders = capabilities.GL_ARB_framebuffer_object && capabilities.OpenGL20;
+        gl43 = capabilities.OpenGL43;;
+        gl46 = capabilities.OpenGL46;
 
-        LOGGER.info("Shaders enabled: {}", Shaders.enableShaders);
-		LOGGER.info("");
+        if (!capabilities.OpenGL41) {
+            if (Minecraft.getOs() == EnumOS.macos) {
+                LOGGER.warn("BTA Requires OpenGL4.1 but only {} was found! If you're on MacOS this is probably just Apple misreporting the GLVersion number and not actually due to a lack of support.", GL41.glGetString(GL41.GL_VERSION));
+            } else {
+                LOGGER.error("BTA Requires OpenGL4.1 but only {} was found!", GL41.glGetString(GL41.GL_VERSION));
+            }
+        }
     }
-	
-	public static void checkError(String info) {
-		int errorCode = glGetError();
-		
-		if(errorCode != GL_NO_ERROR) {
-			if(Global.BUILD_CHANNEL.isUnstableBuild()) {
-				String error = errorCode + " (" + getErrorDescription(errorCode) + "): " + info;
-				throw new RuntimeException("OpenGL Error " + error);
-			}
-			
-			if(!errors.contains(info)) {
-				errors.add(info);
-				String error = errorCode + " (" + getErrorDescription(errorCode) + "): " + info;
-	            LOGGER.error("########## GL ERROR ##########");
+
+    public static void checkError(String info) {
+        int errorCode = GL41.glGetError();
+
+        if (errorCode != GL41.GL_NO_ERROR) {
+            if (Global.BUILD_CHANNEL.isUnstableBuild()) {
+                String error = errorCode + " (" + getErrorDescription(errorCode) + "): " + info;
+                throw new RuntimeException("OpenGL Error " + error);
+            }
+
+            if (!errors.contains(info)) {
+                errors.add(info);
+                String error = errorCode + " (" + getErrorDescription(errorCode) + "): " + info;
+                LOGGER.error("########## GL ERROR ##########");
                 LOGGER.error("OpenGL Error {}", error);
-			}
-		}
-	}
-	
-	public static String getErrorDescription(int error) {
-		if(error == GL_INVALID_ENUM) return "Invalid Enum";
-		if(error == GL_INVALID_VALUE) return "Invalid Value";
-		if(error == GL_INVALID_OPERATION) return "Invalid Operation";
-		if(error == ARBFramebufferObject.GL_INVALID_FRAMEBUFFER_OPERATION) return "Invalid Framebuffer Operation";
-		if(error == GL_OUT_OF_MEMORY) return "Out of Memory";
-		if(error == GL_STACK_UNDERFLOW) return "Stack Underflow";
-		if(error == GL_STACK_OVERFLOW) return "Stack Overflow";
-		return "Unknown Error";
-	}
+            }
+        }
+    }
 
-	public static void glColor1i(int argb) {
-		float a = (float)(argb >> 24 & 0xff) / 255F;
-		float r = (float)(argb >> 16 & 0xff) / 255F;
-		float g = (float)(argb >> 8 & 0xff) / 255F;
-		float b = (float)(argb & 0xff) / 255F;
-		glColor4f(r, g, b, a);
-	}
+    public static String getErrorDescription(int error) {
+        if (error == GL41.GL_INVALID_ENUM) return "Invalid Enum";
+        if (error == GL41.GL_INVALID_VALUE) return "Invalid Value";
+        if (error == GL41.GL_INVALID_OPERATION) return "Invalid Operation";
+        if (error == ARBFramebufferObject.GL_INVALID_FRAMEBUFFER_OPERATION) return "Invalid Framebuffer Operation";
+        if (error == GL41.GL_OUT_OF_MEMORY) return "Out of Memory";
+        if (error == GL41.GL_STACK_UNDERFLOW) return "Stack Underflow";
+        if (error == GL41.GL_STACK_OVERFLOW) return "Stack Overflow";
+        return "Unknown Error";
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/ParticleEngine.java b/game/client/src/main/java/net/minecraft/client/render/ParticleEngine.java
index 3ef5d30fc..0254e9be9 100644
--- a/game/client/src/main/java/net/minecraft/client/render/ParticleEngine.java
+++ b/game/client/src/main/java/net/minecraft/client/render/ParticleEngine.java
@@ -6,9 +6,15 @@ import it.unimi.dsi.fastutil.objects.ObjectArrayList;
 import net.minecraft.client.render.camera.ICamera;
 import net.minecraft.client.render.particle.ParticleBlockBreaking;
 import net.minecraft.client.render.particle.Particle;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.CompareFunc;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
+import net.minecraft.client.render.tessellator.TessellatorParticleShader;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.World;
 import net.minecraft.core.block.Block;
@@ -16,18 +22,16 @@ import net.minecraft.core.block.Blocks;
 import net.minecraft.core.world.pos.TilePos;
 import org.jetbrains.annotations.NotNull;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 /**
  * Handles rendering and ticking of client-side particles.
  */
 public final class ParticleEngine {
-    public static final int PARTICLE_TEXTURE = 0;
-    public static final int TERRAIN_TEXTURE = 1;
-    public static final int ITEM_TEXTURE = 2;
-    public static final int ENTITY_PARTICLE_TEXTURE = 3;
-    public static final int TEXTURE_COUNT = 4;
+    public static final int WORLD_TEXTURE = 0;
+    public static final int ENTITY_PARTICLE_TEXTURE = 1;
+    public static final int TEXTURE_COUNT = 2;
 
+    private final @NotNull TessellatorParticleShader shaderParticleTessellator = new TessellatorParticleShader(4000 * 40);
     private World world;
     private final List<Particle>[] particles;
     private final Random rand;
@@ -54,6 +58,7 @@ public final class ParticleEngine {
             this.particles[t].remove(0);
         }
         this.particles[t].add(p);
+        p.init();
     }
 
     /**
@@ -77,23 +82,25 @@ public final class ParticleEngine {
      * @param camera      The camera relative to whose perspective the particles should be drawn.
      * @param partialTick The time since the last tick.
      */
-    public void renderParticles(@NotNull ParticleTessellator tessellator, @NotNull ICamera camera, float partialTick) {
+    public void renderParticles(@NotNull ICamera camera, float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.PARTICLE);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.setDepthFunc(CompareFunc.LESS);
+
+        TessellatorParticle tessellator = this.shaderParticleTessellator;
         tessellator.setupParticleValues(camera, partialTick);
         double xOff = camera.getX(partialTick);
         double yOff = camera.getY(partialTick);
         double zOff = camera.getZ(partialTick);
 
-        for (int tt = 0; tt < 3; tt++) {
+        for (int tt = 0; tt <= WORLD_TEXTURE; tt++) {
             if (this.particles[tt].isEmpty()) {
                 continue;
             }
-            int texture = switch (tt) {
-                case PARTICLE_TEXTURE -> TextureRegistry.particleAtlas.id();
-                case TERRAIN_TEXTURE -> TextureRegistry.blockAtlas.id();
-                case ITEM_TEXTURE -> TextureRegistry.itemAtlas.id();
-                default -> 0;
-            };
-            GL11.glBindTexture(GL11.GL_TEXTURE_2D, texture);
+            TextureRegistry.worldAtlas.bind();
             tessellator.setTranslation(-xOff, -yOff, -zOff);
             tessellator.startDrawingParticles();
             for (int i = 0; i < this.particles[tt].size(); i++) {
@@ -103,6 +110,7 @@ public final class ParticleEngine {
             tessellator.drawParticles();
         }
         tessellator.setTranslation(0, 0, 0);
+        GLRenderer.popFrame();
     }
 
     /**
@@ -121,7 +129,7 @@ public final class ParticleEngine {
         double xOff = camera.getX(partialTick);
         double yOff = camera.getY(partialTick);
         double zOff = camera.getZ(partialTick);
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         for (int i = 0; i < this.particles[tt].size(); i++) {
             Particle p = this.particles[tt].get(i);
             p.renderLit(tessellator, partialTick, xOff, yOff, zOff);
@@ -206,6 +214,6 @@ public final class ParticleEngine {
     }
 
     public int countParticles() {
-        return this.particles[PARTICLE_TEXTURE].size() + this.particles[TERRAIN_TEXTURE].size() + this.particles[ITEM_TEXTURE].size() + this.particles[ENTITY_PARTICLE_TEXTURE].size();
+        return this.particles[WORLD_TEXTURE].size() + this.particles[ENTITY_PARTICLE_TEXTURE].size();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/RenderGlobal.java b/game/client/src/main/java/net/minecraft/client/render/RenderGlobal.java
index 6706e3f2a..8b159ac28 100644
--- a/game/client/src/main/java/net/minecraft/client/render/RenderGlobal.java
+++ b/game/client/src/main/java/net/minecraft/client/render/RenderGlobal.java
@@ -1,7 +1,6 @@
 package net.minecraft.client.render;
 
 import it.unimi.dsi.fastutil.objects.ObjectArrayList;
-import net.minecraft.client.GLAllocation;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.particle.Particle;
 import net.minecraft.client.render.particle.ParticleDispatcher;
@@ -14,10 +13,18 @@ import net.minecraft.client.render.camera.EntityCamera;
 import net.minecraft.client.render.camera.ICamera;
 import net.minecraft.client.render.colorizer.Colorizers;
 import net.minecraft.client.render.culling.CameraFrustum;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.CompareFunc;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.terrain.ChunkRenderer;
+import net.minecraft.client.render.tessellator.RenderBuffer;
+import net.minecraft.client.render.tessellator.TessellatorShader;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.worldtype.WorldTypeFX;
 import net.minecraft.client.render.worldtype.WorldTypeFXDispatcher;
 import net.minecraft.client.world.WorldClient;
@@ -53,18 +60,14 @@ import org.joml.Vector3dc;
 import org.joml.Vector3fc;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.ARBOcclusionQuery;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL15;
+import org.lwjgl.opengl.GL41;
 
-import java.nio.IntBuffer;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
 import java.util.Random;
 
 import static java.awt.Color.HSBtoRGB;
-import static org.lwjgl.opengl.GL11.*;
 
 public class RenderGlobal
     implements LevelListener {
@@ -79,21 +82,16 @@ public class RenderGlobal
     public static final int RENDER_CHUNK_SIZE = 16;
     public static final int MAX_VISIBLE_REBUILDS_PER_FRAME = 6;
     public static final int MAX_INVISIBLE_REBUILDS_PER_FRAME = 1;
-    public static final int RENDER_LIST_BASE_WIDTH = 48;
 
     public List<TileEntity> renderableTileEntities = new ObjectArrayList<>();
     private WorldClient world;
     private final TextureManager textureManager;
     private final List<@NotNull ChunkRenderer> dirtyChunks = new ObjectArrayList<>();
-    private ChunkRenderer[] sortedChunkRenderers;
     private ChunkRenderer[] chunkRenderers;
     private int xChunks;
     private int yChunks;
     private int zChunks;
-    private int chunkLists;
     private final Minecraft mc;
-    private IntBuffer occlusionCheckIds;
-    private boolean occlusionCheck = false;
     private float lastCloudOffsetX = 0;
     private float lastCloudOffsetZ = 0;
     private float cloudOffsetX = 0;
@@ -101,8 +99,8 @@ public class RenderGlobal
     private float cloudVelocityX;
     private float cloudVelocityZ;
     private int ticks;
-    private final int starList;
-    private final int skyList;
+    private @NotNull RenderBuffer starBuffer;
+    private final @NotNull RenderBuffer skyBuffer;
     private int xMinChunk;
     private int yMinChunk;
     private int zMinChunk;
@@ -114,17 +112,12 @@ public class RenderGlobal
     private int totalEntities;
     private int renderedEntities;
     private int culledEntities;
-    IntBuffer resultBuffer = GLAllocation.createDirectIntBuffer(64);
     private int totalChunks;
     private int offscreenChunks;
     private int occludedChunks;
     private int renderedChunks;
     private int emptyChunks;
     private int chunkFixOffs;
-    private final List<ChunkRenderer> renderChunks = new ObjectArrayList<>();
-    private final DisplayList[] renderLists = {
-        new DisplayList(), new DisplayList(), new DisplayList(), new DisplayList()
-    };
     double xOld = -9999D;
     double yOld = -9999D;
     double zOld = -9999D;
@@ -139,53 +132,37 @@ public class RenderGlobal
     public RenderGlobal(Minecraft mc, TextureManager textureManager) {
         this.mc = mc;
         this.textureManager = textureManager;
-        this.chunkLists = GLAllocation.generateDisplayLists(RENDER_LIST_BASE_WIDTH * RENDER_LIST_BASE_WIDTH * RENDER_LIST_BASE_WIDTH * MAX_VISIBLE_REBUILDS_PER_FRAME);
-        this.occlusionCheck = OpenGLHelper.enableOcclusionCheck;
-        if (this.occlusionCheck) {
-            this.resultBuffer.clear();
-            this.occlusionCheckIds = GLAllocation.createDirectIntBuffer(RENDER_LIST_BASE_WIDTH * RENDER_LIST_BASE_WIDTH * RENDER_LIST_BASE_WIDTH);
-            this.occlusionCheckIds.clear();
-            this.occlusionCheckIds.position(0);
-            this.occlusionCheckIds.limit(RENDER_LIST_BASE_WIDTH * RENDER_LIST_BASE_WIDTH * RENDER_LIST_BASE_WIDTH);
-            ARBOcclusionQuery.glGenQueriesARB(this.occlusionCheckIds);
-        }
 
-        // Set up call list for stars
-        this.starList = GLAllocation.generateDisplayLists(3);
-        updateStars();
 
-        // Set up call list for sky
-        Tessellator t = Tessellator.instance;
-        this.skyList = this.starList + 1;
-        GL11.glNewList(this.skyList, GL11.GL_COMPILE);
+        // Set up buffer for stars
+        this.starBuffer = renderStars();
+
+        // Set up buffer for sky
+        TessellatorGeneral t = GLRenderer.getTessellator();
         int s = 64;
         int d = 256 / s + 2;
         float yy = 16F;
+        t.startDrawingQuads();
         for (int xx = -s * d; xx <= s * d; xx += s) {
             for (int zz = -s * d; zz <= s * d; zz += s) {
-                t.startDrawingQuads();
                 t.addVertex(xx, yy, zz);
                 t.addVertex(xx + s, yy, zz);
                 t.addVertex(xx + s, yy, zz + s);
                 t.addVertex(xx, yy, zz + s);
-                t.draw();
             }
         }
-        GL11.glEndList();
+        this.skyBuffer = t.record(GL41.glGenVertexArrays(), GL41.glGenBuffers());
     }
 
     public void updateStars() {
-        GL11.glPushMatrix();
-        GL11.glNewList(this.starList, GL11.GL_COMPILE);
-        renderStars();
-        GL11.glEndList();
-        GL11.glPopMatrix();
+        this.starBuffer.delete();
+        this.starBuffer = renderStars();
     }
 
-    private void renderStars() {
+    private @NotNull RenderBuffer renderStars() {
         Random random = new Random(10842L);
         Random colorRandom = new Random(10842L); // Created a second random so the new color don't change the positions of the stars
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         for (int i = 0; i < 1500; i++) {
             double d = random.nextFloat() * 2.0F - 1.0F;
@@ -230,7 +207,7 @@ public class RenderGlobal
 
         }
 
-        tessellator.draw();
+        return tessellator.record(GL41.glGenVertexArrays(), GL41.glGenBuffers());
     }
 
     public void setWorld(final WorldClient world) {
@@ -252,11 +229,6 @@ public class RenderGlobal
     public void allChanged() {
         ScreenOptions.queueReload = false;
         updateStars();
-        // Delete all display lists - this is a (hopefully temporary) workaround to AMD's OpenGL driver leaking memory
-        // See https://community.amd.com/t5/opengl-vulkan/high-vram-consumption-in-minecraft/m-p/607299
-        deleteChunkLists();
-        this.chunkLists = GLAllocation.generateDisplayLists(RENDER_LIST_BASE_WIDTH * RENDER_LIST_BASE_WIDTH * RENDER_LIST_BASE_WIDTH * MAX_VISIBLE_REBUILDS_PER_FRAME);
-
         BlockModelLeaves.setGraphicsLevel(this.mc.gameSettings.fancyGraphics.value == 1);
         this.renderDistance = this.mc.gameSettings.renderDistance.value;
         if (this.world == null) return;
@@ -269,12 +241,15 @@ public class RenderGlobal
         }
         int dist = this.renderDistance * 16 * 2;
 
+        this.xOld = this.mc.activeCamera.getX();
+        this.yOld = this.mc.activeCamera.getY();
+        this.zOld = this.mc.activeCamera.getZ();
+
         this.xChunks = dist / RENDER_CHUNK_SIZE + 1;
         this.yChunks = this.world.getHeightBlocks() / RENDER_CHUNK_SIZE;
         this.zChunks = dist / RENDER_CHUNK_SIZE + 1;
 
         this.chunkRenderers = new ChunkRenderer[this.xChunks * this.yChunks * this.zChunks];
-        this.sortedChunkRenderers = new ChunkRenderer[this.xChunks * this.yChunks * this.zChunks];
 
         int id = 0;
         int count = 0;
@@ -297,16 +272,10 @@ public class RenderGlobal
             for (int y = 0; y < this.yChunks; y++) {
                 for (int z = 0; z < this.zChunks; z++) {
                     int index = (z * this.yChunks + y) * this.xChunks + x;
-                    this.chunkRenderers[index] = this.mc.terrainRenderer.createChunkRenderer(this.world, this.renderableTileEntities, x * RENDER_CHUNK_SIZE, y * RENDER_CHUNK_SIZE, z * RENDER_CHUNK_SIZE, RENDER_CHUNK_SIZE, this.chunkLists + id);
-                    if (this.occlusionCheck) {
-                        this.chunkRenderers[index].occlusionId = this.occlusionCheckIds.get(count);
-                    }
-                    this.chunkRenderers[index].occlusionQuerying = false;
-                    this.chunkRenderers[index].occlusionVisible = true;
+                    this.chunkRenderers[index] = this.mc.terrainRenderer.createChunkRenderer(this.world, this.renderableTileEntities, x * RENDER_CHUNK_SIZE, y * RENDER_CHUNK_SIZE, z * RENDER_CHUNK_SIZE, RENDER_CHUNK_SIZE);
                     this.chunkRenderers[index].visible = true;
                     this.chunkRenderers[index].id = count++;
                     this.chunkRenderers[index].setDirty();
-                    this.sortedChunkRenderers[index] = this.chunkRenderers[index];
                     this.dirtyChunks.add(this.chunkRenderers[index]);
                     id += ChunkRenderer.MAX_RENDER_PASSES + 1;
                 }
@@ -315,12 +284,11 @@ public class RenderGlobal
 
         }
 
-        if (this.world != null) {
-            if (this.mc.activeCamera != null) {
-                resortChunks(MathHelper.floor(this.mc.activeCamera.getX()), MathHelper.floor(this.mc.activeCamera.getY()), MathHelper.floor(this.mc.activeCamera.getZ()));
-                Arrays.sort(this.sortedChunkRenderers, new CameraSorter(this.mc.activeCamera));
-            }
-        }
+        resortChunks(
+            MathHelper.floor(this.mc.activeCamera.getX()),
+            MathHelper.floor(this.mc.activeCamera.getY()),
+            MathHelper.floor(this.mc.activeCamera.getZ())
+        );
 
         this.noEntityRenderFrames = 2;
     }
@@ -365,13 +333,13 @@ public class RenderGlobal
         double auroraBrightnessDelta = totalDelta / 100;
         this.auroraBrightness += auroraBrightnessDelta * partialTick;
 
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glDepthFunc(GL11.GL_ALWAYS);
-        GL11.glDisable(GL11.GL_FOG);
-        GL11.glDisable(GL11.GL_ALPHA_TEST);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.setDepthFunc(CompareFunc.ALWAYS);
+//        GL11.glDisable(GL11.GL_FOG);
+//        GL11.glDisable(GL11.GL_ALPHA_TEST);
 
         final double scale = 1f;
         double auroraY = (this.world.getWorldType().getMinY() + this.world.getWorldType().getYRange() + 64f) * 2f;
@@ -387,7 +355,8 @@ public class RenderGlobal
         double radius = 512;
         long worldTime = this.world.getWorldTime();
 
-        Tessellator.instance.startDrawingQuads();
+        TessellatorGeneral t = GLRenderer.getTessellator();
+        t.startDrawingQuads();
         for (double x = -radius; x < radius; x += 16) {
             for (double z = -radius; z < radius; z += 16) {
                 double posX = cameraX + x;
@@ -404,34 +373,32 @@ public class RenderGlobal
                     for (int j = 0; j < 2; j++) {
                         double xOff = i * 8;
                         double zOff = j * 8;
-                        renderAuroraBeam(
+                        renderAuroraBeam(t,
                             (x + xOff) * scale,
                             (auroraY * scale - cameraY * scale) + aurora.getAuroraHeightOffset((posX + xOff), (posZ + zOff), time),
-                            (z + zOff) * scale,
-                            rotationX, rotationZ,
+                            (z + zOff) * scale, rotationX,
+                            rotationZ,
                             aurora.getAuroraRedOffset((posX + xOff), (posZ + zOff), time),
                             aurora.getAuroraGreenOffset((posX + xOff), (posZ + zOff), time),
-                            aurora.getAuroraBlueOffset((posX + xOff), (posZ + zOff), time),
-                            scale, (float) (sample * 0.3f * distanceSqPercentage)
-                        );
+                            aurora.getAuroraBlueOffset((posX + xOff), (posZ + zOff), time), scale,
+                            (float) (sample * 0.3f * distanceSqPercentage));
                     }
                 }
             }
         }
-        Tessellator.instance.draw();
-
-        GL11.glEnable(GL11.GL_FOG);
-        GL11.glEnable(GL11.GL_ALPHA_TEST);
-        GL11.glDepthFunc(GL11.GL_LEQUAL);
-        GL11.glColor4f(1f, 1f, 1f, 1f);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glDisable(GL11.GL_LIGHTING);
+        t.draw();
+
+//        GL11.glEnable(GL11.GL_FOG);
+//        GL11.glEnable(GL11.GL_ALPHA_TEST);
+        GLRenderer.setDepthFunc(CompareFunc.LESS_EQUAL);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.globalSetLightEnabled(false);
     }
 
-    private void renderAuroraBeam(double x, double y, double z, double xOffset, double zOffset, float redOffset, float greenOffset, float blueOffset, double scale, float transparency) {
+    private void renderAuroraBeam(@NotNull TessellatorGeneral tessellator, double x, double y, double z, double xOffset, double zOffset, float redOffset, float greenOffset, float blueOffset, double scale, float transparency) {
         float width = 16f;
-        Tessellator tessellator = Tessellator.instance;
-        tessellator.setColorRGBA_F(0 / 255f + redOffset, 255 / 255f + greenOffset, 127 / 255f + blueOffset, transparency);
+        tessellator.setColor4f(0 / 255f + redOffset, 255 / 255f + greenOffset, 127 / 255f + blueOffset, transparency);
         tessellator.addVertexWithUV(x - xOffset * scale * width, y - scale * 256, z - zOffset * scale * width, 1.0, 1.0);
         tessellator.addVertexWithUV(x - xOffset * scale * width, y + scale, z - zOffset * scale * width, 1.0, 0.0);
         tessellator.addVertexWithUV(x + xOffset * scale * width, y + scale, z + zOffset * scale * width, 0.0, 0.0);
@@ -444,39 +411,41 @@ public class RenderGlobal
             return;
         }
         TileEntityRenderDispatcher.instance.cacheActiveRenderInfo(this.world, camera, partialTick);
-        EntityRenderDispatcher.instance.cacheActiveRenderInfo(this.world, camera, partialTick);
+        EntityRendererDispatcher.instance.cacheActiveRenderInfo(this.world, camera, partialTick);
         this.totalEntities = 0;
         this.renderedEntities = 0;
         this.culledEntities = 0;
-        EntityRenderDispatcher.renderPosX = camera.getX(partialTick);
-        EntityRenderDispatcher.renderPosY = camera.getY(partialTick);
-        EntityRenderDispatcher.renderPosZ = camera.getZ(partialTick);
+        EntityRendererDispatcher.renderPosX = camera.getX(partialTick);
+        EntityRendererDispatcher.renderPosY = camera.getY(partialTick);
+        EntityRendererDispatcher.renderPosZ = camera.getZ(partialTick);
         TileEntityRenderDispatcher.renderPosX = camera.getX(partialTick);
         TileEntityRenderDispatcher.renderPosY = camera.getY(partialTick);
         TileEntityRenderDispatcher.renderPosZ = camera.getZ(partialTick);
         List<Entity> loadedEntities = this.world.getLoadedEntityList();
         this.totalEntities = loadedEntities.size();
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         Vector3dc cameraPos = camera.getPosition(partialTick);
         // Render weather effects
         for (int i = 0; i < this.world.weatherEffects.size(); i++) {
             Entity entity = this.world.weatherEffects.get(i);
             this.renderedEntities++;
-            if (entity.shouldRender(cameraPos, 1) || this.mc.thePlayer.vehicle == entity) {
-                EntityRenderDispatcher.instance.renderEntity(tessellator, entity, partialTick);
+            if ((entity.shouldRender(cameraPos, 1) && camera.getFrustum().isVisible(entity.bb, partialTick)) || this.mc.thePlayer.vehicle == entity) {
+                EntityRendererDispatcher.instance.renderEntity(tessellator, entity, partialTick);
             }
         }
 
         // DO NOT TURN THIS INTO A FOREACH
         for (int i = 0; i < loadedEntities.size(); i++) {
             Entity entity = loadedEntities.get(i);
-            if (this.mc.activeCamera != null && this.mc.activeCamera instanceof EntityCamera && ((EntityCamera) this.mc.activeCamera).mob == entity) {
+            if (this.mc.activeCamera != null && this.mc.activeCamera instanceof EntityCamera entityCamera && entityCamera.mob == entity) {
                 if (!this.mc.activeCamera.showPlayer()) {
                     continue;
                 }
             }
-            if (this.mc.thePlayer.vehicle != entity && (!entity.shouldRender(cameraPos, this.mc.gameSettings.entityRenderDistance.value) || !entity.ignoreFrustumCheck && !camera.getFrustum().isVisible(EntityRenderDispatcher.instance.getRenderer(entity).entityViewBox(entity), partialTick))) {
-                continue;
+            if (this.mc.thePlayer.vehicle != entity) {
+                if (!entity.shouldRender(cameraPos, this.mc.gameSettings.entityRenderDistance.value)) continue;
+                if (!entity.ignoreFrustumCheck && !camera.getFrustum().isVisible(EntityRendererDispatcher.instance.getRenderer(entity).entityViewBox(entity), partialTick))
+                    continue; // TODO OPENGL fix this broken check, nearly always returns false now
             }
             int floorY = MathHelper.floor(entity.y);
             if (floorY < 0) {
@@ -488,7 +457,7 @@ public class RenderGlobal
             }
             if (this.world.isBlockLoaded(MathHelper.floor(entity.x), floorY, MathHelper.floor(entity.z)) || this.mc.thePlayer.vehicle == entity) {
                 this.renderedEntities++;
-                EntityRenderDispatcher.instance.renderEntity(tessellator, entity, partialTick);
+                EntityRendererDispatcher.instance.renderEntity(tessellator, entity, partialTick);
             }
         }
 
@@ -601,9 +570,6 @@ public class RenderGlobal
             this.emptyChunks = 0;
         }
 
-        double xOff = camera.getX((float) partialTick);
-        double yOff = camera.getY((float) partialTick);
-        double zOff = camera.getZ((float) partialTick);
         double xd = camera.getX() - this.xOld;
         double yd = camera.getY() - this.yOld;
         double zd = camera.getZ() - this.zOld;
@@ -612,169 +578,10 @@ public class RenderGlobal
             this.yOld = camera.getY();
             this.zOld = camera.getZ();
             resortChunks(MathHelper.floor(camera.getX()), MathHelper.floor(camera.getY()), MathHelper.floor(camera.getZ()));
-            Arrays.sort(this.sortedChunkRenderers, new CameraSorter(camera));
         }
 
         Lighting.disable();
-        int count = 0;
-        if (this.occlusionCheck && this.mc.gameSettings.advancedOpenGL.value && renderPass == 0) {
-            int from = 0;
-            int to = RENDER_CHUNK_SIZE;
-            checkQueryResults(from, to);
-            for (int i = from; i < to; i++) {
-                this.sortedChunkRenderers[i].occlusionVisible = true;
-            }
-
-            count += renderChunks(from, to, renderPass, partialTick);
-            do {
-                from = to;
-                to *= 2;
-                if (to > this.sortedChunkRenderers.length) {
-                    to = this.sortedChunkRenderers.length;
-                }
-                GL11.glDisable(GL11.GL_TEXTURE_2D);
-                GL11.glDisable(GL11.GL_LIGHTING);
-                GL11.glDisable(GL11.GL_ALPHA_TEST);
-                GL11.glDisable(GL11.GL_FOG);
-                GL11.glColorMask(false, false, false, false);
-                GL11.glDepthMask(false);
-                checkQueryResults(from, to);
-                GL11.glPushMatrix();
-                float xo = 0.0F;
-                float yo = 0.0F;
-                float zo = 0.0F;
-                for (int ix = from; ix < to; ix++) {
-                    if (this.sortedChunkRenderers[ix].isEmpty()) {
-                        this.sortedChunkRenderers[ix].visible = false;
-                        continue;
-                    }
-                    if (!this.sortedChunkRenderers[ix].visible) {
-                        this.sortedChunkRenderers[ix].occlusionVisible = true;
-                    }
-                    if (!this.sortedChunkRenderers[ix].visible || this.sortedChunkRenderers[ix].occlusionQuerying) {
-                        continue;
-                    }
-                    float dist = MathHelper.sqrt_float(this.sortedChunkRenderers[ix].distanceToCameraSquared(camera));
-                    int frequency = (int) (1.0F + dist / 128F);
-                    if (this.ticks % frequency != ix % frequency) {
-                        continue;
-                    }
-                    ChunkRenderer chunkRenderer = this.sortedChunkRenderers[ix];
-                    float xt = (float) ((double) chunkRenderer.xRender - xOff);
-                    float yt = (float) ((double) chunkRenderer.yRender - yOff);
-                    float zt = (float) ((double) chunkRenderer.zRender - zOff);
-                    float xdd = xt - xo;
-                    float ydd = yt - yo;
-                    float zdd = zt - zo;
-                    if (xdd != 0.0F || ydd != 0.0F || zdd != 0.0F) {
-                        GL11.glTranslatef(xdd, ydd, zdd);
-                        xo += xdd;
-                        yo += ydd;
-                        zo += zdd;
-                    }
-                    ARBOcclusionQuery.glBeginQueryARB(GL15.GL_SAMPLES_PASSED, this.sortedChunkRenderers[ix].occlusionId);
-                    this.sortedChunkRenderers[ix].renderBB();
-                    ARBOcclusionQuery.glEndQueryARB(GL15.GL_SAMPLES_PASSED);
-                    this.sortedChunkRenderers[ix].occlusionQuerying = true;
-                }
-
-                GL11.glPopMatrix();
-                GL11.glColorMask(true, true, true, true);
-                GL11.glDepthMask(true);
-                GL11.glEnable(GL11.GL_TEXTURE_2D);
-                GL11.glEnable(GL11.GL_ALPHA_TEST);
-                GL11.glEnable(GL11.GL_FOG);
-                count += renderChunks(from, to, renderPass, partialTick);
-            } while (to < this.sortedChunkRenderers.length);
-        } else {
-            count += renderChunks(0, this.sortedChunkRenderers.length, renderPass, partialTick);
-        }
-        return count;
-    }
-
-    private void checkQueryResults(int from, int to) {
-        for (int i = from; i < to; i++) {
-            if (!this.sortedChunkRenderers[i].occlusionQuerying) {
-                continue;
-            }
-            this.resultBuffer.clear();
-            ARBOcclusionQuery.glGetQueryObjectuivARB(this.sortedChunkRenderers[i].occlusionId, GL15.GL_QUERY_RESULT_AVAILABLE, this.resultBuffer);
-            if (this.resultBuffer.get(0) != 0) {
-                this.sortedChunkRenderers[i].occlusionQuerying = false;
-                this.resultBuffer.clear();
-                ARBOcclusionQuery.glGetQueryObjectuivARB(this.sortedChunkRenderers[i].occlusionId, GL15.GL_QUERY_RESULT, this.resultBuffer);
-                this.sortedChunkRenderers[i].occlusionVisible = this.resultBuffer.get(0) != 0;
-            }
-        }
-
-    }
-
-    private int renderChunks(int from, int to, int renderPass, double partialTick) {
-        this.renderChunks.clear();
-        int count = 0;
-
-        for (int i = from; i < to; i++) {
-            if (renderPass == 0) {
-                this.totalChunks++;
-                if (this.sortedChunkRenderers[i].empty[renderPass]) {
-                    this.emptyChunks++;
-                } else if (!this.sortedChunkRenderers[i].visible) {
-                    this.offscreenChunks++;
-                } else if (this.occlusionCheck && !this.sortedChunkRenderers[i].occlusionVisible) {
-                    this.occludedChunks++;
-                } else {
-                    this.renderedChunks++;
-                }
-            }
-
-            if (this.sortedChunkRenderers[i].empty[renderPass] || !this.sortedChunkRenderers[i].visible || this.occlusionCheck && !this.sortedChunkRenderers[i].occlusionVisible) {
-                continue;
-            }
-            int list = this.sortedChunkRenderers[i].getList(renderPass);
-            if (list >= 0) {
-                this.renderChunks.add(this.sortedChunkRenderers[i]);
-                count++;
-            }
-        }
-
-        double xOff = this.mc.activeCamera.getX((float) partialTick);
-        double yOff = this.mc.activeCamera.getY((float) partialTick);
-        double zOff = this.mc.activeCamera.getZ((float) partialTick);
-        int lists = 0;
-        for (DisplayList displayList : this.renderLists) {
-            displayList.clear();
-        }
-
-        for (ChunkRenderer renderer : this.renderChunks) {
-            int list = -1;
-            for (int i = 0; i < lists; i++) {
-                if (this.renderLists[i].isSetToPos(renderer.xRender, renderer.yRender, renderer.zRender)) {
-                    list = i;
-                }
-            }
-
-            if (list < 0) {
-                list = lists++;
-                this.renderLists[list].setToPos(renderer.xRender, renderer.yRender, renderer.zRender, xOff, yOff, zOff);
-            }
-            this.renderLists[list].addCallToList(renderer.getList(renderPass));
-        }
-
-        if (!this.mc.gameSettings.fog.value) {
-            GL11.glDisable(GL11.GL_FOG);
-        }
-        renderSameAsLast(renderPass, partialTick);
-        if (!this.mc.gameSettings.fog.value) {
-            GL11.glEnable(GL11.GL_FOG);
-        }
-        return count;
-    }
-
-    public void renderSameAsLast(int renderPass, double partialTick) {
-        for (DisplayList displayList : this.renderLists) {
-            displayList.call();
-        }
-
+        return 0;
     }
 
     public void tick() {
@@ -807,38 +614,43 @@ public class RenderGlobal
             return;
         }
         float celestialAngle = this.world.getCelestialAngle(partialTick);
-        GL11.glDisable(GL_TEXTURE_2D);
+
+
+        GLRenderer.pushFrame();
+        this.mc.worldRenderer.fogManager.setupFog(FogManager.FOG_MODE_SKY, this.mc.worldRenderer.farPlaneDistance, partialTick, GLRenderer.getFogState());
+        GLRenderer.setShader(Shaders.COLOR_WORLD);
         Vector3fc skyColor = this.world.getSkyColor(this.mc.activeCamera, partialTick);
         float r = skyColor.x();
         float g = skyColor.y();
         float b = skyColor.z();
-        GL11.glColor3f(r, g, b);
-        Tessellator t = Tessellator.instance;
-        GL11.glDepthMask(false);
-        GL11.glEnable(GL_FOG);
-        GL11.glColor3f(r, g, b);
-        GL11.glCallList(this.skyList);
-        GL11.glDisable(GL_FOG);
-        GL11.glDisable(GL_ALPHA_TEST);
-        GL11.glEnable(GL_BLEND);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setDepthMask(false);
+        GLRenderer.setColor3f(r, g, b);
+        GLRenderer.render(this.skyBuffer);
+        GLRenderer.popFrame();
+
+
+        GLRenderer.pushFrame();
+        GLRenderer.getFogState().disable();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         Lighting.disable();
+        TessellatorGeneral t = GLRenderer.getTessellator();
         float[] sunriseColor = worldTypeFX.getSunriseColor(celestialAngle, partialTick);
         if (sunriseColor != null) {
-            GL11.glDisable(GL_TEXTURE_2D);
-            GL11.glShadeModel(GL_SMOOTH);
-            GL11.glPushMatrix();
-            GL11.glRotatef(-90F, 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(90F, 1.0F, 0.0F, 0.0F);
-            GL11.glRotatef(celestialAngle <= 0.5F ? 0.0F : 180F, 0.0F, 0.0F, 1.0F);
+            GLRenderer.pushFrame();
+            GLRenderer.setDepthMask(false);
+            GLRenderer.setShader(Shaders.COLOR);
+            GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(-90F));
+            GLRenderer.modelM4f().rotateX(org.joml.Math.toRadians(90F));
+            GLRenderer.modelM4f().rotateZ(org.joml.Math.toRadians(celestialAngle <= 0.5F ? 0.0F : 180F));
             float sr = sunriseColor[0];
             float sg = sunriseColor[1];
             float sb = sunriseColor[2];
-            t.startDrawing(GL_TRIANGLE_FAN);
-            t.setColorRGBA_F(sr, sg, sb, sunriseColor[3]);
+            t.startDrawing(DrawMode.TRIANGLE_FAN);
+            t.setColor4f(sr, sg, sb, sunriseColor[3]);
             t.addVertex(0.0D, 100D, 0.0D);
             int numVertices = 16;
-            t.setColorRGBA_F(sunriseColor[0], sunriseColor[1], sunriseColor[2], 0.0F);
+            t.setColor4f(sunriseColor[0], sunriseColor[1], sunriseColor[2], 0.0F);
             for (int i = 0; i <= numVertices; i++) {
                 float theta = ((float) i * MathHelper.PI * 2.0F) / (float) numVertices;
                 float sunriseX = MathHelper.sin(theta);
@@ -847,26 +659,27 @@ public class RenderGlobal
             }
 
             t.draw();
-            GL11.glPopMatrix();
-            GL11.glShadeModel(GL_FLAT);
+            GLRenderer.popFrame();
         }
-        GL11.glEnable(GL_TEXTURE_2D);
-        GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE);
-        GL11.glPushMatrix();
+        GLRenderer.popFrame();
+
+        GLRenderer.pushFrame();
+        GLRenderer.setDepthMask(false);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE);
         float sunAlpha = 1.0F - (this.world.getCurrentWeather() != null && this.world.getCurrentWeather() != Weathers.OVERWORLD_CLEAR ? (this.world.weatherManager.getWeatherIntensity() * this.world.weatherManager.getWeatherPower()) * 1.5f : 0.0f);
 
         float x = 0.0F;
         float y = 0.0F;
         float z = 0.0F;
 
-        GL11.glTranslatef(x, y, z);
-        GL11.glRotatef(0, 0.0F, 0.0F, 1.0F);
-        GL11.glRotatef(celestialAngle * 360F, 0.0F, 0.0F, 1.0F);
+        GLRenderer.modelM4f().translate(x, y, z);
+        GLRenderer.modelM4f().rotateZ(org.joml.Math.toRadians(celestialAngle * 360F));
 
         // Render sun
         float size = 30F;
         this.textureManager.loadTexture("/assets/minecraft/textures/terrain/sun.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, sunAlpha);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, sunAlpha);
         t.startDrawingQuads();
         t.addVertexWithUV(-size, 100D, -size, 0.0D, 0.0D);
         t.addVertexWithUV(size, 100D, -size, 1.0D, 0.0D);
@@ -930,7 +743,7 @@ public class RenderGlobal
                 size = 200F - i * 4;
                 int color = HSBtoRGB(i / (float) iterations, 1, (float) (0.3f * this.rainbowBrightness));
                 float rainbowAlpha = (float) ((0.35f - (0.15f * Math.abs(i - iterations / 2) / (iterations / 2f))) * this.rainbowBrightness);
-                t.setColorRGBA_F(Color.redFromInt(color) / 255f, Color.greenFromInt(color) / 255f, Color.blueFromInt(color) / 255f, rainbowAlpha);
+                t.setColor4f(Color.redFromInt(color) / 255f, Color.greenFromInt(color) / 255f, Color.blueFromInt(color) / 255f, rainbowAlpha);
                 t.addVertexWithUV(-size, -100D, size, 1.0D, 1.0D);
                 t.addVertexWithUV(size, -100D, size, 0.0D, 1.0D);
                 t.addVertexWithUV(size, -100D, -size, 0.0D, 0.0D);
@@ -944,7 +757,7 @@ public class RenderGlobal
         // Render moon
         size = 20F;
         this.textureManager.loadTexture("/assets/minecraft/textures/terrain/moon.png").bind();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, sunAlpha);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, sunAlpha);
         t.startDrawingQuads();
         t.addVertexWithUV(-size, -100D, size, 1.0D, 1.0D);
         t.addVertexWithUV(size, -100D, size, 0.0D, 1.0D);
@@ -952,25 +765,14 @@ public class RenderGlobal
         t.addVertexWithUV(-size, -100D, -size, 1.0D, 0.0D);
         t.draw();
 
-        float f17 = this.world.getStarBrightness(partialTick) * sunAlpha;
-        if (f17 > 0.0F) {
+        float starVis = this.world.getStarBrightness(partialTick) * sunAlpha * sunAlpha * sunAlpha;
+        if (starVis > 0.0F) {
             this.textureManager.loadTexture("/assets/minecraft/textures/colormap/stars/default.png").bind();
-            GL11.glColor4f(f17, f17, f17, f17);
-            GL11.glCallList(this.starList);
-        }
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glDisable(GL11.GL_TEXTURE_2D);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glEnable(GL11.GL_ALPHA_TEST);
-        GL11.glEnable(GL11.GL_FOG);
-        GL11.glPopMatrix();
-        if (worldTypeFX.hasGround()) {
-            GL11.glColor3f(r * 0.2F + 0.04F, g * 0.2F + 0.04F, b * 0.6F + 0.1F);
-        } else {
-            GL11.glColor3f(r, g, b);
+            GLRenderer.setColor4f(starVis, starVis, starVis, starVis);
+            GLRenderer.render(this.starBuffer);
         }
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
-        GL11.glDepthMask(true);
+        GLRenderer.popFrame();
+
     }
 
     private float getCloudHeightModifier() {
@@ -989,21 +791,24 @@ public class RenderGlobal
             renderCloudsFancy(partialTick);
             return;
         }
-        GL11.glDisable(GL11.GL_CULL_FACE);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.CLOUDS);
+        GLRenderer.setLightmapCoord2i(15, 15);
+        GLRenderer.disableState(State.CULL_FACE);
         float cameraY = (float) this.mc.activeCamera.getY(partialTick);
         byte cloudRadius = 32;
         int i = 256 / cloudRadius;
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         this.textureManager.loadTexture("/assets/minecraft/textures/environment/clouds.png").bind();
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         Vector3fc dimensionColor = this.world.getDimensionColor(this.mc.activeCamera, partialTick);
         float r = dimensionColor.x();
         float g = dimensionColor.y();
         float b = dimensionColor.z();
         float f6 = 1f / 2048f;
-        double posX = this.mc.activeCamera.getX(partialTick) + (double) ((this.lastCloudOffsetX + (this.cloudOffsetX - this.lastCloudOffsetX) * partialTick) * 0.03F);
-        double posZ = this.mc.activeCamera.getZ(partialTick) + (double) ((this.lastCloudOffsetZ + (this.cloudOffsetZ - this.lastCloudOffsetZ) * partialTick) * 0.03F);
+        double posX = this.mc.activeCamera.getX(partialTick) + (double) (org.joml.Math.lerp(this.lastCloudOffsetX, this.cloudOffsetX, partialTick) * 0.03F);
+        double posZ = this.mc.activeCamera.getZ(partialTick) + (double) (org.joml.Math.lerp(this.lastCloudOffsetZ, this.cloudOffsetZ, partialTick) * 0.03F);
         int j = MathHelper.floor(posX / 2048D);
         int k = MathHelper.floor(posZ / 2048D);
         posX -= j * 2048;
@@ -1012,24 +817,31 @@ public class RenderGlobal
         float f10 = (float) (posX * (double) f6);
         float f11 = (float) (posZ * (double) f6);
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_F(r, g, b, 0.8F);
-        for (int cloudX = -cloudRadius * i; cloudX < cloudRadius * i; cloudX += cloudRadius) {
-            for (int cloudZ = -cloudRadius * i; cloudZ < cloudRadius * i; cloudZ += cloudRadius) {
-                tessellator.addVertexWithUV(cloudX, cloudHeight, cloudZ + cloudRadius, (float) (cloudX) * f6 + f10, (float) (cloudZ + cloudRadius) * f6 + f11);
-                tessellator.addVertexWithUV(cloudX + cloudRadius, cloudHeight, cloudZ + cloudRadius, (float) (cloudX + cloudRadius) * f6 + f10, (float) (cloudZ + cloudRadius) * f6 + f11);
-                tessellator.addVertexWithUV(cloudX + cloudRadius, cloudHeight, cloudZ, (float) (cloudX + cloudRadius) * f6 + f10, (float) (cloudZ) * f6 + f11);
-                tessellator.addVertexWithUV(cloudX, cloudHeight, cloudZ, (float) (cloudX) * f6 + f10, (float) (cloudZ) * f6 + f11);
-            }
-
-        }
-
+        tessellator.setColor4f(r, g, b, 0.8F);
+        int dist = (cloudRadius * i * 2);
+        int cloudZ = -cloudRadius * i;
+        int cloudX = -cloudRadius * i;
+        tessellator.addVertexWithUV(
+            cloudX, cloudHeight, cloudZ + cloudRadius * dist,
+            cloudX * f6 + f10, (cloudZ + cloudRadius * dist) * f6 + f11);
+        tessellator.addVertexWithUV(
+            cloudX + cloudRadius * dist, cloudHeight, cloudZ + cloudRadius * dist,
+            (cloudX + cloudRadius * dist) * f6 + f10, (cloudZ + cloudRadius * dist) * f6 + f11);
+        tessellator.addVertexWithUV(
+            cloudX + cloudRadius * dist, cloudHeight, cloudZ,
+            (cloudX + cloudRadius * dist) * f6 + f10, cloudZ * f6 + f11);
+        tessellator.addVertexWithUV(
+            cloudX, cloudHeight, cloudZ,
+            (cloudX) * f6 + f10, cloudZ * f6 + f11);
         tessellator.draw();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glEnable(GL11.GL_CULL_FACE);
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.popFrame();
     }
 
     public void renderCloudsFancy(float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.setLightmapCoord2i(15, 15);
         WorldTypeFX worldTypeFX = WorldTypeFXDispatcher.getInstance().getDispatch(this.mc.currentWorld.getWorldType());
         this.mc.renderer.beginRenderClouds(partialTick);
 
@@ -1048,9 +860,9 @@ public class RenderGlobal
         final float gDim = dimensionColor.y();
         final float bDim = dimensionColor.z();
 
-        GL11.glDisable(GL11.GL_CULL_FACE);
+        GLRenderer.disableState(State.CULL_FACE);
         float cameraY = (float) this.mc.activeCamera.getY(partialTick);
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorShader tessellator = GLRenderer.getTessellator();
         float cloudWidth = 12F;
         float cloudThickness = 4F;
         double dx = (this.mc.activeCamera.getX(partialTick) + (double) ((this.lastCloudOffsetX + (this.cloudOffsetX - this.lastCloudOffsetX) * partialTick) * 0.03F)) / (double) cloudWidth;
@@ -1061,8 +873,8 @@ public class RenderGlobal
         dx -= i * 2048;
         dz -= j * 2048;
         this.textureManager.loadTexture("/assets/minecraft/textures/environment/clouds.png").bind();
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         float f13 = 1F / 256F;
         float f9 = (float) MathHelper.floor(dx) * f13;
         float f11 = (float) MathHelper.floor(dz) * f13;
@@ -1071,95 +883,100 @@ public class RenderGlobal
         int cloudWidthScale = 8;
         byte radius = 3;
         float f16 = 1F / 1024F;
-        GL11.glScalef(cloudWidth, 1.0F, cloudWidth);
+        GLRenderer.modelM4f().scale(cloudWidth, 1.0F, cloudWidth);
 
         float red = rDim + (rSun - rDim) * aSun;
         float green = gDim + (gSun - gDim) * aSun;
         float blue = bDim + (bSun - bDim) * aSun;
 
-        for (int l = 0; l < 2; l++) {
-            if (l == 0) {
-                GL11.glColorMask(false, false, false, true);
-            } else {
-                GL11.glColorMask(true, true, true, true);
+        tessellator.startDrawingQuads();
+        {
+            float width = (radius * 2 + 2) * cloudWidthScale;
+            float minX = (-radius - 1) * cloudWidthScale;
+            float minZ = (-radius - 1) * cloudWidthScale;
+            float cloudX = minX - f14;
+            float cloudZ = minZ - f15;
+            if (dy > -cloudThickness - 1.0F) {
+                tessellator.setColor4f(red * 0.7F, green * 0.7F, blue * 0.7F, 0.8F);
+                tessellator.setNormal(0.0F, -1F, 0.0F);
+                tessellator.addVertexWithUV(cloudX + 0.0F, dy + 0.0F, cloudZ + width, (minX + 0.0F) * f13 + f9, (minZ + width) * f13 + f11);
+                tessellator.addVertexWithUV(cloudX + width, dy + 0.0F, cloudZ + width, (minX + width) * f13 + f9, (minZ + width) * f13 + f11);
+                tessellator.addVertexWithUV(cloudX + width, dy + 0.0F, cloudZ + 0.0F, (minX + width) * f13 + f9, (minZ + 0.0F) * f13 + f11);
+                tessellator.addVertexWithUV(cloudX + 0.0F, dy + 0.0F, cloudZ + 0.0F, (minX + 0.0F) * f13 + f9, (minZ + 0.0F) * f13 + f11);
             }
-            tessellator.startDrawingQuads();
-            for (int ix = -radius - 1; ix <= radius; ix++) {
-                for (int iz = -radius - 1; iz <= radius; iz++) {
-
-                    float f17 = ix * cloudWidthScale;
-                    float f18 = iz * cloudWidthScale;
-                    float cloudX = f17 - f14;
-                    float cloudZ = f18 - f15;
-                    if (dy > -cloudThickness - 1.0F) {
-                        tessellator.setColorRGBA_F(red * 0.7F, green * 0.7F, blue * 0.7F, 0.8F);
-                        tessellator.setNormal(0.0F, -1F, 0.0F);
-                        tessellator.addVertexWithUV(cloudX + 0.0F, dy + 0.0F, cloudZ + (float) cloudWidthScale, (f17 + 0.0F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
-                        tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + 0.0F, cloudZ + (float) cloudWidthScale, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
-                        tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + 0.0F, cloudZ + 0.0F, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + 0.0F) * f13 + f11);
-                        tessellator.addVertexWithUV(cloudX + 0.0F, dy + 0.0F, cloudZ + 0.0F, (f17 + 0.0F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
-                    }
-                    if (dy <= cloudThickness + 1.0F) {
-                        tessellator.setColorRGBA_F(red, green, blue, 0.8F);
-                        tessellator.setNormal(0.0F, 1.0F, 0.0F);
-                        tessellator.addVertexWithUV(cloudX + 0.0F, (dy + cloudThickness) - f16, cloudZ + (float) cloudWidthScale, (f17 + 0.0F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
-                        tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, (dy + cloudThickness) - f16, cloudZ + (float) cloudWidthScale, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
-                        tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, (dy + cloudThickness) - f16, cloudZ + 0.0F, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + 0.0F) * f13 + f11);
-                        tessellator.addVertexWithUV(cloudX + 0.0F, (dy + cloudThickness) - f16, cloudZ + 0.0F, (f17 + 0.0F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
+            if (dy <= cloudThickness + 1.0F) {
+                tessellator.setColor4f(red, green, blue, 0.8F);
+                tessellator.setNormal(0.0F, 1.0F, 0.0F);
+                tessellator.addVertexWithUV(cloudX + 0.0F, (dy + cloudThickness) - f16, cloudZ + width, (minX + 0.0F) * f13 + f9, (minZ + width) * f13 + f11);
+                tessellator.addVertexWithUV(cloudX + width, (dy + cloudThickness) - f16, cloudZ + width, (minX + width) * f13 + f9, (minZ + width) * f13 + f11);
+                tessellator.addVertexWithUV(cloudX + width, (dy + cloudThickness) - f16, cloudZ + 0.0F, (minX + width) * f13 + f9, (minZ + 0.0F) * f13 + f11);
+                tessellator.addVertexWithUV(cloudX + 0.0F, (dy + cloudThickness) - f16, cloudZ + 0.0F, (minX + 0.0F) * f13 + f9, (minZ + 0.0F) * f13 + f11);
+            }
+        }
+        for (int ix = -radius - 1; ix <= radius + 1; ix++) {
+            for (int iz = -radius - 1; iz <= radius + 1; iz++) {
+
+                float f17 = ix * cloudWidthScale;
+                float f18 = iz * cloudWidthScale;
+                float cloudX = f17 - f14;
+                float cloudZ = f18 - f15;
+                tessellator.setColor4f(red * 0.9F, green * 0.9F, blue * 0.9F, 0.8F);
+                if (ix > -1) {
+                    tessellator.setNormal(-1F, 0.0F, 0.0F);
+                    for (int k1 = 0; k1 < cloudWidthScale; k1++) {
+                        tessellator.addVertexWithUV(cloudX + (float) k1 + 0.0F, dy + 0.0F, cloudZ + (float) cloudWidthScale, (f17 + (float) k1 + 0.5F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + (float) k1 + 0.0F, dy + cloudThickness, cloudZ + (float) cloudWidthScale, (f17 + (float) k1 + 0.5F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + (float) k1 + 0.0F, dy + cloudThickness, cloudZ + 0.0F, (f17 + (float) k1 + 0.5F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + (float) k1 + 0.0F, dy + 0.0F, cloudZ + 0.0F, (f17 + (float) k1 + 0.5F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
                     }
-                    tessellator.setColorRGBA_F(red * 0.9F, green * 0.9F, blue * 0.9F, 0.8F);
-                    if (ix > -1) {
-                        tessellator.setNormal(-1F, 0.0F, 0.0F);
-                        for (int k1 = 0; k1 < cloudWidthScale; k1++) {
-                            tessellator.addVertexWithUV(cloudX + (float) k1 + 0.0F, dy + 0.0F, cloudZ + (float) cloudWidthScale, (f17 + (float) k1 + 0.5F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + (float) k1 + 0.0F, dy + cloudThickness, cloudZ + (float) cloudWidthScale, (f17 + (float) k1 + 0.5F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + (float) k1 + 0.0F, dy + cloudThickness, cloudZ + 0.0F, (f17 + (float) k1 + 0.5F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + (float) k1 + 0.0F, dy + 0.0F, cloudZ + 0.0F, (f17 + (float) k1 + 0.5F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
-                        }
 
+                } else {
+                    tessellator.setNormal(1.0F, 0.0F, 0.0F);
+                    for (int l1 = 0; l1 < cloudWidthScale; l1++) {
+                        tessellator.addVertexWithUV((cloudX + (float) l1 + 1.0F) - f16, dy + 0.0F, cloudZ + (float) cloudWidthScale, (f17 + (float) l1 + 0.5F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
+                        tessellator.addVertexWithUV((cloudX + (float) l1 + 1.0F) - f16, dy + cloudThickness, cloudZ + (float) cloudWidthScale, (f17 + (float) l1 + 0.5F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
+                        tessellator.addVertexWithUV((cloudX + (float) l1 + 1.0F) - f16, dy + cloudThickness, cloudZ + 0.0F, (f17 + (float) l1 + 0.5F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
+                        tessellator.addVertexWithUV((cloudX + (float) l1 + 1.0F) - f16, dy + 0.0F, cloudZ + 0.0F, (f17 + (float) l1 + 0.5F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
                     }
-                    if (ix <= 1) {
-                        tessellator.setNormal(1.0F, 0.0F, 0.0F);
-                        for (int l1 = 0; l1 < cloudWidthScale; l1++) {
-                            tessellator.addVertexWithUV((cloudX + (float) l1 + 1.0F) - f16, dy + 0.0F, cloudZ + (float) cloudWidthScale, (f17 + (float) l1 + 0.5F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
-                            tessellator.addVertexWithUV((cloudX + (float) l1 + 1.0F) - f16, dy + cloudThickness, cloudZ + (float) cloudWidthScale, (f17 + (float) l1 + 0.5F) * f13 + f9, (f18 + (float) cloudWidthScale) * f13 + f11);
-                            tessellator.addVertexWithUV((cloudX + (float) l1 + 1.0F) - f16, dy + cloudThickness, cloudZ + 0.0F, (f17 + (float) l1 + 0.5F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
-                            tessellator.addVertexWithUV((cloudX + (float) l1 + 1.0F) - f16, dy + 0.0F, cloudZ + 0.0F, (f17 + (float) l1 + 0.5F) * f13 + f9, (f18 + 0.0F) * f13 + f11);
-                        }
 
+                }
+                tessellator.setColor4f(red * 0.8F, green * 0.8F, blue * 0.8F, 0.8F);
+                if (iz > -1) {
+                    tessellator.setNormal(0.0F, 0.0F, -1F);
+                    for (int i2 = 0; i2 < cloudWidthScale; i2++) {
+                        tessellator.addVertexWithUV(cloudX + 0.0F, dy + cloudThickness, cloudZ + (float) i2 + 0.0F, (f17 + 0.0F) * f13 + f9, (f18 + (float) i2 + 0.5F) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + cloudThickness, cloudZ + (float) i2 + 0.0F, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) i2 + 0.5F) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + 0.0F, cloudZ + (float) i2 + 0.0F, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) i2 + 0.5F) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + 0.0F, dy + 0.0F, cloudZ + (float) i2 + 0.0F, (f17 + 0.0F) * f13 + f9, (f18 + (float) i2 + 0.5F) * f13 + f11);
                     }
-                    tessellator.setColorRGBA_F(red * 0.8F, green * 0.8F, blue * 0.8F, 0.8F);
-                    if (iz > -1) {
-                        tessellator.setNormal(0.0F, 0.0F, -1F);
-                        for (int i2 = 0; i2 < cloudWidthScale; i2++) {
-                            tessellator.addVertexWithUV(cloudX + 0.0F, dy + cloudThickness, cloudZ + (float) i2 + 0.0F, (f17 + 0.0F) * f13 + f9, (f18 + (float) i2 + 0.5F) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + cloudThickness, cloudZ + (float) i2 + 0.0F, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) i2 + 0.5F) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + 0.0F, cloudZ + (float) i2 + 0.0F, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) i2 + 0.5F) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + 0.0F, dy + 0.0F, cloudZ + (float) i2 + 0.0F, (f17 + 0.0F) * f13 + f9, (f18 + (float) i2 + 0.5F) * f13 + f11);
-                        }
 
+                } else {
+                    tessellator.setNormal(0.0F, 0.0F, 1.0F);
+                    for (int j2 = 0; j2 < cloudWidthScale; j2++) {
+                        tessellator.addVertexWithUV(cloudX + 0.0F, dy + cloudThickness, (cloudZ + (float) j2 + 1.0F) - f16, (f17 + 0.0F) * f13 + f9, (f18 + (float) j2 + 0.5F) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + cloudThickness, (cloudZ + (float) j2 + 1.0F) - f16, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) j2 + 0.5F) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + 0.0F, (cloudZ + (float) j2 + 1.0F) - f16, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) j2 + 0.5F) * f13 + f11);
+                        tessellator.addVertexWithUV(cloudX + 0.0F, dy + 0.0F, (cloudZ + (float) j2 + 1.0F) - f16, (f17 + 0.0F) * f13 + f9, (f18 + (float) j2 + 0.5F) * f13 + f11);
                     }
-                    if (iz <= 1) {
-                        tessellator.setNormal(0.0F, 0.0F, 1.0F);
-                        for (int j2 = 0; j2 < cloudWidthScale; j2++) {
-                            tessellator.addVertexWithUV(cloudX + 0.0F, dy + cloudThickness, (cloudZ + (float) j2 + 1.0F) - f16, (f17 + 0.0F) * f13 + f9, (f18 + (float) j2 + 0.5F) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + cloudThickness, (cloudZ + (float) j2 + 1.0F) - f16, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) j2 + 0.5F) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + (float) cloudWidthScale, dy + 0.0F, (cloudZ + (float) j2 + 1.0F) - f16, (f17 + (float) cloudWidthScale) * f13 + f9, (f18 + (float) j2 + 0.5F) * f13 + f11);
-                            tessellator.addVertexWithUV(cloudX + 0.0F, dy + 0.0F, (cloudZ + (float) j2 + 1.0F) - f16, (f17 + 0.0F) * f13 + f9, (f18 + (float) j2 + 0.5F) * f13 + f11);
-                        }
 
-                    }
                 }
-
             }
-            tessellator.draw();
 
         }
+        GLRenderer.setShader(Shaders.CLOUDS);
+        GLRenderer.setColorMask(false, false, false, true);
+        tessellator.draw();
+
+        // Hack for not needing to record the cloud buffer twice
+        GLRenderer.setColorMask(true, true, true, true);
+        GLRenderer.getShader().bind();
+        GL41.glBindVertexArray(tessellator.vao);
+        GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, tessellator.vbo);
+        GL41.glDrawArrays(tessellator.drawMode.cap, 0, tessellator.vertexCount);
+        GL41.glBindVertexArray(0);
 
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glEnable(GL11.GL_CULL_FACE);
 
+        GLRenderer.popFrame();
         this.mc.renderer.endRenderClouds(partialTick);
     }
 
@@ -1254,35 +1071,34 @@ public class RenderGlobal
     }
 
     public void drawBlockBreaking(@NotNull ICamera camera, @NotNull HitResult.Tile tileHit, float partialTick) {
-        Tessellator tessellator = Tessellator.instance;
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glEnable(GL11.GL_ALPHA_TEST);
-        GL11.glBlendFunc(770, 1);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, (MathHelper.sin((float) System.currentTimeMillis() / 100F) * 0.2F + 0.4F) * 0.5F);
+        GLRenderer.pushFrame();
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        GLRenderer.enableState(State.BLEND);
+//        GL11.glEnable(GL11.GL_ALPHA_TEST);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, (MathHelper.sin((float) System.currentTimeMillis() / 100F) * 0.2F + 0.4F) * 0.5F);
         if (this.destroyProgress > 0.0F) {
-            GL11.glBlendFunc(774, 768);
-            TextureRegistry.blockAtlas.bind();
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 0.5F);
-            GL11.glPushMatrix();
+            GLRenderer.setBlendFunc(BlendFactor.DST_COLOR, BlendFactor.SRC1_COLOR);
+            TextureRegistry.worldAtlas.bind();
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 0.5F);
+            GLRenderer.pushFrame();
             int k = this.world.getBlockId(tileHit.tilePos);
             Block<?> block = k <= 0 ? null : Blocks.blocksList[k];
-            GL11.glDisable(GL11.GL_ALPHA_TEST);
-            GL11.glPolygonOffset(-3F, -3F);
-            GL11.glEnable(GL_POLYGON_OFFSET_FILL);
+//            GL11.glDisable(GL11.GL_ALPHA_TEST);
+            GLRenderer.setPolygonOffset(-3F, -3F);
+            GLRenderer.enableState(State.POLYGON_OFFSET_FILL);
             double x = camera.getX(partialTick);
             double y = camera.getY(partialTick);
             double z = camera.getZ(partialTick);
             if (block == null) {
                 block = Blocks.STONE;
             }
-            GL11.glEnable(GL11.GL_ALPHA_TEST);
+//            GL11.glEnable(GL11.GL_ALPHA_TEST);
             tessellator.startDrawingQuads();
             tessellator.setTranslation(-x, -y, -z);
             tessellator.lockColor();
-            if (LightmapHelper.isLightmapEnabled()) {
-                // Make sure it's active to prevent crash if a model doesnt enable it
-                tessellator.setLightmapCoord(LightmapHelper.getLightmapCoord(15, 0));
-            }
+            // Make sure it's active to prevent crash if a model doesnt enable it
+            tessellator.setLightmapCoord1i(LightmapHelper.getLightmapCoord(15, 0));
             BlockModelDispatcher.getInstance()
                 .getDispatch(block)
                 .renderWithOverrideTexture(
@@ -1292,26 +1108,22 @@ public class RenderGlobal
                     breakingAnimation[MathHelper.clamp((int) (this.destroyProgress * 10F), 0, breakingAnimation.length - 1)]);
             tessellator.draw();
             tessellator.setTranslation(0.0D, 0.0D, 0.0D);
-            GL11.glDisable(GL11.GL_ALPHA_TEST);
-            GL11.glPolygonOffset(0.0F, 0.0F);
-            GL11.glDisable(GL_POLYGON_OFFSET_FILL);
-            GL11.glEnable(GL11.GL_ALPHA_TEST);
-            GL11.glDepthMask(true);
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         }
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glDisable(GL11.GL_ALPHA_TEST);
+//        GL11.glDisable(GL11.GL_ALPHA_TEST);
+        GLRenderer.popFrame();
     }
 
     public void drawSelectionBox(ICamera camera, HitResult hitResult, float partialTick) {
         if (this.mc.gameSettings.immersiveMode.drawOutline() && this.mc.gameSettings.blockOutlineWidth.value > 0.01f && !(this.mc.currentScreen instanceof ScreenModelViewer)) {
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+            GLRenderer.pushFrame();
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
             float w = this.mc.getOutlineWidth();
-            GL11.glColor4f(0.0F, 0.0F, 0.0F, 0.35f + w * 0.3f);
-            GL11.glLineWidth(java.lang.Math.max(4.0f * w * 2.0f, 1.0f));
-            GL11.glDisable(GL11.GL_TEXTURE_2D);
-            GL11.glDepthMask(false);
+            GLRenderer.setColor4f(0.0F, 0.0F, 0.0F, 0.35f + w * 0.3f);
+            GLRenderer.setLineWidth(org.joml.Math.max(4.0f * w * 2.0f, 1.0f));
+            GLRenderer.setShader(Shaders.LINES);
+            GLRenderer.setDepthMask(false);
             double offsetX = camera.getX(partialTick);
             double offsetY = camera.getY(partialTick);
             double offsetZ = camera.getZ(partialTick);
@@ -1329,7 +1141,7 @@ public class RenderGlobal
                         drawOutlinedBoundingBox(selectionBB);
                     }
                     if (this.mc.gameSettings.viewSupportMode.value) {
-                        Tessellator t = Tessellator.instance;
+                        TessellatorGeneral t = GLRenderer.getTessellator();
 
                         double x = hitTile.tilePos.x() - offsetX;
                         double y = hitTile.tilePos.y() - offsetY;
@@ -1349,9 +1161,9 @@ public class RenderGlobal
 
                         {// Top
                             if (sTop.canSupport(PartialSupport.INSTANCE.center(), Side.BOTTOM)) {
-                                t.setColorRGBA_F(0f, 1f, 0f, 0.25f);
+                                t.setColor4f(0f, 1f, 0f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0f, 0.25f);
+                                t.setColor4f(1f, 0f, 0f, 0.25f);
                             }
                             t.addVertex(x + oMin + 0.25, y + oMax, z + oMin + 0.25);
                             t.addVertex(x + oMin + 0.25, y + oMax, z + oMax - 0.25);
@@ -1359,9 +1171,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax - 0.25, y + oMax, z + oMin + 0.25);
 
                             if (sTop.canSupport(PartialSupport.INSTANCE.up(), Side.BOTTOM)) {
-                                t.setColorRGBA_F(0.5f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0.5f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMin);
                             t.addVertex(x + oMin + 0.25, y + oMax, z + oMin + 0.25);
@@ -1369,9 +1181,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax, y + oMax, z + oMin);
 
                             if (sTop.canSupport(PartialSupport.INSTANCE.down(), Side.BOTTOM)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMax);
                             t.addVertex(x + oMax, y + oMax, z + oMax);
@@ -1379,9 +1191,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin + 0.25, y + oMax, z + oMax - 0.25);
 
                             if (sTop.canSupport(PartialSupport.INSTANCE.left(), Side.BOTTOM)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMin);
                             t.addVertex(x + oMin, y + oMax, z + oMax);
@@ -1389,9 +1201,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin + 0.25, y + oMax, z + oMin + 0.25);
 
                             if (sTop.canSupport(PartialSupport.INSTANCE.right(), Side.BOTTOM)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMax, z + oMin);
                             t.addVertex(x + oMax - 0.25, y + oMax, z + oMin + 0.25);
@@ -1401,9 +1213,9 @@ public class RenderGlobal
 
                         {// Bottom
                             if (sBottom.canSupport(PartialSupport.INSTANCE.center(), Side.TOP)) {
-                                t.setColorRGBA_F(0f, 1f, 0f, 0.25f);
+                                t.setColor4f(0f, 1f, 0f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0f, 0.25f);
+                                t.setColor4f(1f, 0f, 0f, 0.25f);
                             }
                             t.addVertex(x + oMin + 0.25, y + oMin, z + oMin + 0.25);
                             t.addVertex(x + oMax - 0.25, y + oMin, z + oMin + 0.25);
@@ -1411,9 +1223,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin + 0.25, y + oMin, z + oMax - 0.25);
 
                             if (sBottom.canSupport(PartialSupport.INSTANCE.up(), Side.TOP)) {
-                                t.setColorRGBA_F(0.5f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0.5f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin + 0.25, y + oMin, z + oMax - 0.25);
                             t.addVertex(x + oMax - 0.25, y + oMin, z + oMax - 0.25);
@@ -1421,9 +1233,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin, y + oMin, z + oMax);
 
                             if (sBottom.canSupport(PartialSupport.INSTANCE.down(), Side.TOP)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin + 0.25, y + oMin, z + oMin + 0.25);
                             t.addVertex(x + oMin, y + oMin, z + oMin);
@@ -1431,9 +1243,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax - 0.25, y + oMin, z + oMin + 0.25);
 
                             if (sBottom.canSupport(PartialSupport.INSTANCE.left(), Side.TOP)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMin, z + oMin);
                             t.addVertex(x + oMax, y + oMin, z + oMax);
@@ -1441,9 +1253,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax - 0.25, y + oMin, z + oMin + 0.25);
 
                             if (sBottom.canSupport(PartialSupport.INSTANCE.right(), Side.TOP)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMin, z + oMin);
                             t.addVertex(x + oMin + 0.25, y + oMin, z + oMin + 0.25);
@@ -1453,9 +1265,9 @@ public class RenderGlobal
 
                         {// North
                             if (sNorth.canSupport(PartialSupport.INSTANCE.center(), Side.SOUTH)) {
-                                t.setColorRGBA_F(0f, 1f, 0f, 0.25f);
+                                t.setColor4f(0f, 1f, 0f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0f, 0.25f);
+                                t.setColor4f(1f, 0f, 0f, 0.25f);
                             }
                             t.addVertex(x + oMin + 0.25, y + oMax - 0.25, z + oMin);
                             t.addVertex(x + oMax - 0.25, y + oMax - 0.25, z + oMin);
@@ -1463,9 +1275,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin + 0.25, y + oMin + 0.25, z + oMin);
 
                             if (sNorth.canSupport(PartialSupport.INSTANCE.up(), Side.SOUTH)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMin);
                             t.addVertex(x + oMax, y + oMax, z + oMin);
@@ -1473,9 +1285,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin + 0.25, y + oMax - 0.25, z + oMin);
 
                             if (sNorth.canSupport(PartialSupport.INSTANCE.down(), Side.SOUTH)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin + 0.25, y + oMin + 0.25, z + oMin);
                             t.addVertex(x + oMax - 0.25, y + oMin + 0.25, z + oMin);
@@ -1483,9 +1295,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin, y + oMin, z + oMin);
 
                             if (sNorth.canSupport(PartialSupport.INSTANCE.right(), Side.SOUTH)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMin);
                             t.addVertex(x + oMin + 0.25, y + oMax - 0.25, z + oMin);
@@ -1493,9 +1305,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin, y + oMin, z + oMin);
 
                             if (sNorth.canSupport(PartialSupport.INSTANCE.left(), Side.SOUTH)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMax, z + oMin);
                             t.addVertex(x + oMax, y + oMin, z + oMin);
@@ -1505,9 +1317,9 @@ public class RenderGlobal
 
                         {// South
                             if (sSouth.canSupport(PartialSupport.INSTANCE.center(), Side.NORTH)) {
-                                t.setColorRGBA_F(0f, 1f, 0f, 0.25f);
+                                t.setColor4f(0f, 1f, 0f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0f, 0.25f);
+                                t.setColor4f(1f, 0f, 0f, 0.25f);
                             }
                             t.addVertex(x + oMin + 0.25, y + oMax - 0.25, z + oMax);
                             t.addVertex(x + oMin + 0.25, y + oMin + 0.25, z + oMax);
@@ -1515,9 +1327,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax - 0.25, y + oMax - 0.25, z + oMax);
 
                             if (sSouth.canSupport(PartialSupport.INSTANCE.up(), Side.NORTH)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMax);
                             t.addVertex(x + oMin + 0.25, y + oMax - 0.25, z + oMax);
@@ -1525,9 +1337,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax, y + oMax, z + oMax);
 
                             if (sSouth.canSupport(PartialSupport.INSTANCE.down(), Side.NORTH)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin + 0.25, y + oMin + 0.25, z + oMax);
                             t.addVertex(x + oMin, y + oMin, z + oMax);
@@ -1535,9 +1347,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax - 0.25, y + oMin + 0.25, z + oMax);
 
                             if (sSouth.canSupport(PartialSupport.INSTANCE.right(), Side.NORTH)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMax, z + oMax);
                             t.addVertex(x + oMax - 0.25, y + oMax - 0.25, z + oMax);
@@ -1545,9 +1357,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax, y + oMin, z + oMax);
 
                             if (sSouth.canSupport(PartialSupport.INSTANCE.left(), Side.NORTH)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMax);
                             t.addVertex(x + oMin, y + oMin, z + oMax);
@@ -1557,9 +1369,9 @@ public class RenderGlobal
 
                         {// West
                             if (sWest.canSupport(PartialSupport.INSTANCE.center(), Side.EAST)) {
-                                t.setColorRGBA_F(0f, 1f, 0f, 0.25f);
+                                t.setColor4f(0f, 1f, 0f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0f, 0.25f);
+                                t.setColor4f(1f, 0f, 0f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax - 0.25, z + oMin + 0.25);
                             t.addVertex(x + oMin, y + oMin + 0.25, z + oMin + 0.25);
@@ -1567,9 +1379,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin, y + oMax - 0.25, z + oMax - 0.25);
 
                             if (sWest.canSupport(PartialSupport.INSTANCE.up(), Side.EAST)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMin);
                             t.addVertex(x + oMin, y + oMax - 0.25, z + oMin + 0.25);
@@ -1577,9 +1389,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin, y + oMax, z + oMax);
 
                             if (sWest.canSupport(PartialSupport.INSTANCE.down(), Side.EAST)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMin, z + oMin);
                             t.addVertex(x + oMin, y + oMin, z + oMax);
@@ -1587,9 +1399,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin, y + oMin + 0.25, z + oMin + 0.25);
 
                             if (sWest.canSupport(PartialSupport.INSTANCE.left(), Side.EAST)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax, z + oMin);
                             t.addVertex(x + oMin, y + oMin, z + oMin);
@@ -1597,9 +1409,9 @@ public class RenderGlobal
                             t.addVertex(x + oMin, y + oMax - 0.25, z + oMin + 0.25);
 
                             if (sWest.canSupport(PartialSupport.INSTANCE.right(), Side.EAST)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMin, y + oMax - 0.25, z + oMax - 0.25);
                             t.addVertex(x + oMin, y + oMin + 0.25, z + oMax - 0.25);
@@ -1609,9 +1421,9 @@ public class RenderGlobal
 
                         {// East
                             if (sEast.canSupport(PartialSupport.INSTANCE.center(), Side.WEST)) {
-                                t.setColorRGBA_F(0f, 1f, 0f, 0.25f);
+                                t.setColor4f(0f, 1f, 0f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0f, 0.25f);
+                                t.setColor4f(1f, 0f, 0f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMax - 0.25, z + oMin + 0.25);
                             t.addVertex(x + oMax, y + oMax - 0.25, z + oMax - 0.25);
@@ -1619,9 +1431,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax, y + oMin + 0.25, z + oMin + 0.25);
 
                             if (sEast.canSupport(PartialSupport.INSTANCE.up(), Side.WEST)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMax, z + oMin);
                             t.addVertex(x + oMax, y + oMax, z + oMax);
@@ -1629,9 +1441,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax, y + oMax - 0.25, z + oMin + 0.25);
 
                             if (sEast.canSupport(PartialSupport.INSTANCE.down(), Side.WEST)) {
-                                t.setColorRGBA_F(0f, 1f, 0.5f, 0.25f);
+                                t.setColor4f(0f, 1f, 0.5f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 0.5f, 0.25f);
+                                t.setColor4f(1f, 0f, 0.5f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMin, z + oMin);
                             t.addVertex(x + oMax, y + oMin + 0.25, z + oMin + 0.25);
@@ -1639,9 +1451,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax, y + oMin, z + oMax);
 
                             if (sEast.canSupport(PartialSupport.INSTANCE.left(), Side.WEST)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMax - 0.25, z + oMax - 0.25);
                             t.addVertex(x + oMax, y + oMax, z + oMax);
@@ -1649,9 +1461,9 @@ public class RenderGlobal
                             t.addVertex(x + oMax, y + oMin + 0.25, z + oMax - 0.25);
 
                             if (sEast.canSupport(PartialSupport.INSTANCE.right(), Side.WEST)) {
-                                t.setColorRGBA_F(0f, 1f, 1f, 0.25f);
+                                t.setColor4f(0f, 1f, 1f, 0.25f);
                             } else {
-                                t.setColorRGBA_F(1f, 0f, 1f, 0.25f);
+                                t.setColor4f(1f, 0f, 1f, 0.25f);
                             }
                             t.addVertex(x + oMax, y + oMax, z + oMin);
                             t.addVertex(x + oMax, y + oMax - 0.25, z + oMin + 0.25);
@@ -1665,23 +1477,21 @@ public class RenderGlobal
             } else if (hitResult instanceof HitResult.Entity hitEntity && hitEntity.entity.showBoundingBoxOnHover() && !this.mc.gameSettings.showCollisionBoxes.value) {
                 drawInterpolatedEntityBoundingBox(hitEntity.entity, hitEntity.entity.bb, camera, partialTick);
             }
-
-            GL11.glDepthMask(true);
-            GL11.glEnable(GL11.GL_TEXTURE_2D);
-            GL11.glDisable(GL11.GL_BLEND);
+            GLRenderer.popFrame();
         }
     }
 
     public void drawDebugEntityOutlines(ICamera camera, float partialTicks) {
-        glDisable(GL_TEXTURE_2D);
-        glLineWidth(2.0f);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.LINES);
+        GLRenderer.setLineWidth(2f);
 
         double offsetX = camera.getX(partialTicks);
         double offsetY = camera.getY(partialTicks);
         double offsetZ = camera.getZ(partialTicks);
         float expand = 0.002F;
         List<AABBdc> collidingBoundingBoxes = this.world.getCubes(this.mc.thePlayer, MathHelper.aabbGrow(this.mc.thePlayer.bb, expand, expand, expand, new AABBd()));
-        glColor4f(0.0f, 0.0f, 1.0f, 1.0f);
+        GLRenderer.setColor4f(0.0f, 0.0f, 1.0f, 1.0f);
         for (AABBdc aabb : collidingBoundingBoxes) {
             AABBd bb = aabb.translate(-offsetX, -offsetY, -offsetZ, new AABBd());
             MathHelper.aabbGrow(bb, expand, expand, expand, bb);
@@ -1694,45 +1504,43 @@ public class RenderGlobal
         }
         List<Entity> entitiesNearby = this.world.getEntitiesWithinAABBExcludingEntity(null, MathHelper.aabbGrow(this.mc.thePlayer.bb, entityRadius, entityRadius, entityRadius, new AABBd()));
         for (Entity e : entitiesNearby) {
-            glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
+            GLRenderer.setColor4f(1.0f, 1.0f, 1.0f, 1.0f);
             drawInterpolatedEntityBoundingBox(e, e.bb, camera, partialTicks); // Bounds
 
-            glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
+            GLRenderer.setColor4f(1.0f, 0.0f, 0.0f, 1.0f);
             final AABBd head = new AABBd(e.bb);
             head.setMin(head.minX, e.y + e.getHeadHeight() - 0.005, head.minZ).setMax(head.maxX, e.y + e.getHeadHeight() + 0.005, head.maxZ);
             drawInterpolatedEntityBoundingBox(e, head, camera, partialTicks); // Head
 
-            glColor4f(1.0f, 0.0f, 1.0f, 1.0f);
+            GLRenderer.setColor4f(1.0f, 0.0f, 1.0f, 1.0f);
             final AABBd feet = new AABBd(e.bb.minX, e.y - 0.005, e.bb.minZ, e.bb.maxX, e.y + 0.005, e.bb.maxZ);
             drawInterpolatedEntityBoundingBox(e, feet, camera, partialTicks); // Feet
 
-            glColor4f(0.75f, 0.75f, 1.0f, 1.0f);
-            drawInterpolatedEntityBoundingBox(e, EntityRenderDispatcher.instance.getRenderer(e).entityViewBox(e), camera, partialTicks); // Model vis bounds
+            GLRenderer.setColor4f(0.75f, 0.75f, 1.0f, 1.0f);
+            drawInterpolatedEntityBoundingBox(e, EntityRendererDispatcher.instance.getRenderer(e).entityViewBox(e), camera, partialTicks); // Model vis bounds
 
             double lerpOffsetX = MathHelper.lerp(e.xo, e.x, partialTicks) - camera.getX(partialTicks);
             double lerpOffsetY = MathHelper.lerp(e.yo, e.y, partialTicks) - camera.getY(partialTicks);
             double lerpOffsetZ = MathHelper.lerp(e.zo, e.z, partialTicks) - camera.getZ(partialTicks);
-            drawDebugVec(Tessellator.instance, new Vector3d(lerpOffsetX, lerpOffsetY + e.getHeadHeight(), lerpOffsetZ), e.getViewVector(partialTicks), 1, 0, 1, 0, 1);
-            glDisable(GL_TEXTURE_2D);
-            GL11.glLineWidth(2);
+            drawDebugVec(GLRenderer.getTessellator(), new Vector3d(lerpOffsetX, lerpOffsetY + e.getHeadHeight(), lerpOffsetZ), e.getViewVector(partialTicks), 1, 0, 1, 0, 1);
         }
-
-        glEnable(GL_TEXTURE_2D);
+        GLRenderer.popFrame();
     }
 
-    public static void drawDebugVec(final @NotNull Tessellator tessellator, final @NotNull Vector3dc pos, final @Nullable Vector3dc vec, final double scale, final float r, final float g, final float b, final float a) {
+    public static void drawDebugVec(final @NotNull TessellatorGeneral tessellator, final @NotNull Vector3dc pos, final @Nullable Vector3dc vec, final double scale, final float r, final float g, final float b, final float a) {
         if (vec == null) return;
-        GL11.glLineWidth(10);
-        GL11.glDisable(GL11.GL_TEXTURE_2D);
-        tessellator.startDrawing(GL11.GL_LINES);
-        tessellator.setColorRGBA_F(r, g, b, a);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.LINES);
+        GLRenderer.setLineWidth(10f);
+        tessellator.startDrawing(DrawMode.LINES);
+        tessellator.setColor4f(r, g, b, a);
         tessellator.addVertex(pos.x(), pos.y(), pos.z());
         tessellator.addVertex(
             pos.x() + vec.x() * scale,
             pos.y() + vec.y() * scale,
             pos.z() + vec.z() * scale);
         tessellator.draw();
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
+        GLRenderer.popFrame();
     }
 
     public void drawInterpolatedEntityBoundingBox(@NotNull Entity entity, @NotNull AABBdc boundingBox, @NotNull ICamera camera, float partialTicks) {
@@ -1751,14 +1559,15 @@ public class RenderGlobal
     }
 
     public void drawDebugChunkBorders(@NotNull ICamera camera, float partialTicks) {
-        glDisable(GL_TEXTURE_2D);
-        glDisable(GL_FOG);
+//        glDisable(GL_FOG);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.LINES);
 
         double offsetX = camera.getX(partialTicks);
         double offsetY = camera.getY(partialTicks);
         double offsetZ = camera.getZ(partialTicks);
 
-        Tessellator tessellator = Tessellator.instance;
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.setTranslation(-offsetX, -offsetY, -offsetZ);
 
         int blockX = MathHelper.floor(this.mc.thePlayer.x);
@@ -1775,9 +1584,9 @@ public class RenderGlobal
 
         int worldHeight = this.mc.currentWorld.getHeightBlocks();
 
-        glLineWidth(2.0f);
-        glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
-        tessellator.startDrawing(GL_LINES);
+        GLRenderer.setLineWidth(2.0f);
+        GLRenderer.setColor4f(1.0f, 0.0f, 0.0f, 1.0f);
+        tessellator.startDrawing(DrawMode.LINES);
 
         // Draw vertical red lines
         for (int i = -1; i <= 2; i++) {
@@ -1792,9 +1601,9 @@ public class RenderGlobal
 
         tessellator.draw();
 
-        glLineWidth(1.0f);
-        glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
-        tessellator.startDrawing(GL_LINES);
+        GLRenderer.setLineWidth(1.0f);
+        GLRenderer.setColor4f(0.0f, 1.0f, 0.0f, 1.0f);
+        tessellator.startDrawing(DrawMode.LINES);
 
         // Draw horizontal green lines
         for (int y = 0; y <= worldHeight; y++) {
@@ -1834,27 +1643,27 @@ public class RenderGlobal
         tessellator.draw();
 
         tessellator.setTranslation(0.0, 0.0, 0.0);
-        glEnable(GL_TEXTURE_2D);
-        glEnable(GL_FOG);
+        GLRenderer.popFrame();
+//        glEnable(GL_FOG);
     }
 
     public void drawOutlinedBoundingBox(@NotNull AABBdc aabb) {
-        Tessellator tessellator = Tessellator.instance;
-        tessellator.startDrawing(GL11.GL_LINE_STRIP);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        tessellator.startDrawing(DrawMode.LINE_STRIP);
         tessellator.addVertex(aabb.minX(), aabb.minY(), aabb.minZ());
         tessellator.addVertex(aabb.maxX(), aabb.minY(), aabb.minZ());
         tessellator.addVertex(aabb.maxX(), aabb.minY(), aabb.maxZ());
         tessellator.addVertex(aabb.minX(), aabb.minY(), aabb.maxZ());
         tessellator.addVertex(aabb.minX(), aabb.minY(), aabb.minZ());
         tessellator.draw();
-        tessellator.startDrawing(GL11.GL_LINE_STRIP);
+        tessellator.startDrawing(DrawMode.LINE_STRIP);
         tessellator.addVertex(aabb.minX(), aabb.maxY(), aabb.minZ());
         tessellator.addVertex(aabb.maxX(), aabb.maxY(), aabb.minZ());
         tessellator.addVertex(aabb.maxX(), aabb.maxY(), aabb.maxZ());
         tessellator.addVertex(aabb.minX(), aabb.maxY(), aabb.maxZ());
         tessellator.addVertex(aabb.minX(), aabb.maxY(), aabb.minZ());
         tessellator.draw();
-        tessellator.startDrawing(GL11.GL_LINES);
+        tessellator.startDrawing(DrawMode.LINES);
         tessellator.addVertex(aabb.minX(), aabb.minY(), aabb.minZ());
         tessellator.addVertex(aabb.minX(), aabb.maxY(), aabb.minZ());
         tessellator.addVertex(aabb.maxX(), aabb.minY(), aabb.minZ());
@@ -1867,8 +1676,8 @@ public class RenderGlobal
     }
 
     public void drawOutlinedVolume(BoundingVolume volume, double xOffset, double yOffset, double zOffset, float expand) {
-        Tessellator t = Tessellator.instance;
-        t.startDrawing(GL11.GL_LINES);
+        TessellatorGeneral t = GLRenderer.getTessellator();
+        t.startDrawing(DrawMode.LINES);
         Float[] points = volume.getBakedLineCoords();
         for (int i = 0; i < points.length; i += 3) {
             float expand0 = ((points[i] - 0.5f) * 2) * expand;
@@ -1979,7 +1788,7 @@ public class RenderGlobal
         if (seasonChanged) {
             Colorizers.update(false);
         }
-        if (seasonChanged || lightChanged && !LightmapHelper.isLightmapEnabled()) {
+        if (seasonChanged) {
             for (ChunkRenderer chunkRenderer : this.chunkRenderers) {
                 if (chunkRenderer.skyLit && !chunkRenderer.dirty) {
                     this.dirtyChunks.add(chunkRenderer);
@@ -1993,12 +1802,6 @@ public class RenderGlobal
     public void tileEntityChanged(int x, int y, int z, TileEntity tileEntity) {
     }
 
-    public void deleteChunkLists() {
-        if (this.chunkLists >= 0) {
-            GLAllocation.deleteDisplayList(this.chunkLists);
-        }
-    }
-
     @Override
     public void levelEvent(@Nullable Player player, int id, int x, int y, int z, int data) {
         Random random = this.world.rand;
diff --git a/game/client/src/main/java/net/minecraft/client/render/Renderer.java b/game/client/src/main/java/net/minecraft/client/render/Renderer.java
index f53280117..9c6f20d14 100644
--- a/game/client/src/main/java/net/minecraft/client/render/Renderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/Renderer.java
@@ -1,8 +1,5 @@
 package net.minecraft.client.render;
 
-import net.minecraft.client.render.tessellator.ParticleTessellator;
-import org.jetbrains.annotations.NotNull;
-
 public interface Renderer {
 	
 	public void beginRenderGame(float partialTicks);
@@ -13,8 +10,6 @@ public interface Renderer {
 
 	public void beginRenderParticles(float partialTicks);
 
-	public @NotNull ParticleTessellator getParticleTessellator();
-
 	public void endRenderGame(float partialTicks);
 
 	public void endRenderWorld(float partialTicks);
diff --git a/game/client/src/main/java/net/minecraft/client/render/TextureManager.java b/game/client/src/main/java/net/minecraft/client/render/TextureManager.java
index 6a202bb0b..0bb6b5568 100644
--- a/game/client/src/main/java/net/minecraft/client/render/TextureManager.java
+++ b/game/client/src/main/java/net/minecraft/client/render/TextureManager.java
@@ -8,7 +8,6 @@ import java.awt.image.BufferedImage;
 import java.nio.ByteBuffer;
 import java.util.ArrayList;
 import java.util.Collection;
-import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
 import java.util.Objects;
@@ -16,6 +15,8 @@ import java.util.Objects;
 import com.mojang.logging.LogUtils;
 import it.unimi.dsi.fastutil.ints.Int2ObjectArrayMap;
 import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
+import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
+import it.unimi.dsi.fastutil.objects.ObjectArrayList;
 import net.minecraft.client.GLAllocation;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.popup.PopupScreen;
@@ -67,16 +68,16 @@ public class TextureManager {
 	public final Minecraft mc;
 
 	public final Int2ObjectMap<Texture> idToTextureMap = new Int2ObjectArrayMap<>();
-	public final Map<String, Texture> textureMap = new HashMap<>();
-	public final List<TextureBuffered> bufferedTextures = new ArrayList<>();
-	public final Map<String, TextureDownloaded> downloadedTextures = new HashMap<>();
-	public final Map<String, DynamicTexture> dynamicTextures = new HashMap<>();
+	public final Map<String, Texture> textureMap = new Object2ObjectOpenHashMap<>();
+	public final List<TextureBuffered> bufferedTextures = new ObjectArrayList<>();
+	public final Map<String, TextureDownloaded> downloadedTextures = new Object2ObjectOpenHashMap<>();
+	public final Map<NamespaceID, DynamicTexture> dynamicTextures = new Object2ObjectOpenHashMap<>();
 	
 	private final GameSettings gameSettings;
 	public TexturePackList texturePacks;
 	
-	private boolean clampTexture;
-	private boolean blurTexture;
+	private final boolean clampTexture;
+	private final boolean blurTexture;
 
 	public TextureManager(final Minecraft minecraft, final TexturePackList texturePacks, final GameSettings gameSettings) {
 		this.mc = minecraft;
@@ -102,9 +103,9 @@ public class TextureManager {
 			}
 		}
 
-        addDynamicTextureOverride(new DynamicTextureClock(mc), true);
-		addDynamicTextureOverride(new DynamicTextureCalendar(mc), true);
-		addDynamicTextureOverride(new DynamicTextureCompass(mc, TextureRegistry.getTexture("minecraft:item/tool_compass")), true);
+        addDynamicTextureOverride(new DynamicTextureClock(this.mc), true);
+		addDynamicTextureOverride(new DynamicTextureCalendar(this.mc), true);
+		addDynamicTextureOverride(new DynamicTextureCompass(this.mc, TextureRegistry.getTexture("minecraft:item/tool_compass")), true);
 	}
 
 	protected void addNativeDynamicTextures(int state) {
@@ -120,8 +121,8 @@ public class TextureManager {
 				addDynamicTexture(new DynamicTextureFireflyJar(TextureRegistry.getTexture("minecraft:block/lantern_firefly/" + color)));
 			}
 
-			addDynamicTexture(new DynamicTextureTrommel(mc, TextureRegistry.getTexture("minecraft:block/trommel/active_front"), true));
-			addDynamicTexture(new DynamicTextureTrommel(mc, TextureRegistry.getTexture("minecraft:block/trommel/active_back"), false));
+			addDynamicTexture(new DynamicTextureTrommel(this.mc, TextureRegistry.getTexture("minecraft:block/trommel/active_front"), true));
+			addDynamicTexture(new DynamicTextureTrommel(this.mc, TextureRegistry.getTexture("minecraft:block/trommel/active_back"), false));
 		}
 		if (state < ANIMATIONS_CUSTOM) {
 			for (final DyeColor c : DyeColor.values()) {
@@ -140,8 +141,8 @@ public class TextureManager {
 		addDynamicTextureOverride(texture, false);
 	}
 	protected void addDynamicTextureOverride(DynamicTexture texture, boolean override) {
-		if (!override && dynamicTextures.containsKey(texture.targetTexture.namespaceId)) return;
-		dynamicTextures.put(texture.targetTexture.namespaceId.namespace() + ":" + TextureRegistry.stitcherMapReverse.get(texture.targetTexture.parentAtlas) + "/" + texture.targetTexture.namespaceId.value(), texture);
+		if (!override && this.dynamicTextures.containsKey(texture.targetTexture.namespaceId)) return;
+        this.dynamicTextures.put(texture.targetTexture.namespaceId, texture);
 	}
 
 	private void loadCustomAnimations(final Collection<? super Throwable> errors) {
@@ -149,7 +150,7 @@ public class TextureManager {
 			return;
 		}
 
-		for (final AtlasStitcher stitcher : TextureRegistry.stitcherMap.values()){
+		for (final AtlasStitcher stitcher : TextureRegistry.atlases){
 			for (final IconCoordinate c : stitcher.textureMap.values()) {
 				try {
 					if (c.hasMeta("animation")) {
@@ -168,8 +169,8 @@ public class TextureManager {
 		
 		if (t == null) {
 			t = new TextureBuffered(missingTexture, false, false, false);
-			textureMap.put(name, t);
-			idToTextureMap.put(t.id(), t);
+            this.textureMap.put(name, t);
+            this.idToTextureMap.put(t.id(), t);
         }
         return t;
     }
@@ -177,7 +178,7 @@ public class TextureManager {
 	public @Nullable Texture loadTextureNoDefault(@NotNull final String name) {
 		Objects.requireNonNull(name);
 
-		Texture texture = textureMap.get(name);
+		Texture texture = this.textureMap.get(name);
 		if (texture != null) return texture;
 		if (!Minecraft.getMinecraft().texturePackList.anyHasFile(name)) return null;
 
@@ -187,8 +188,8 @@ public class TextureManager {
 				t.delete();
 				return null;
 			}
-			textureMap.put(name, t);
-			idToTextureMap.put(t.id(), t);
+            this.textureMap.put(name, t);
+            this.idToTextureMap.put(t.id(), t);
 			return t;
 		} catch (Exception e) {
             LOGGER.error("Failed to create texture for '{}'!", name, e);
@@ -198,7 +199,7 @@ public class TextureManager {
 
 	public TextureBuffered loadBufferedTexture(BufferedImage bufferedimage) { // TODO, this may need a way to reduce textures from the same BufferedImage, since this allocates a new texture to memory every time its called
 		TextureBuffered texture = new TextureBuffered(bufferedimage, false, false, false);
-		bufferedTextures.add(texture);
+        this.bufferedTextures.add(texture);
 		return texture;
 	}
 
@@ -228,7 +229,7 @@ public class TextureManager {
 		int y1 = icon.iconY;
 		glTexSubImage2D(GL_TEXTURE_2D, 0, x1, y1, icon.width, icon.height, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
 		
-		if(mc.gameSettings.mipmapLevels.value > 0 && anim.targetTexture.parentAtlas.hasMipmaps()) {
+		if(this.mc.gameSettings.mipmapLevels.value > 0 && anim.targetTexture.parentAtlas.hasMipmaps()) {
 			int levels = glGetTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL);
 
 			for(int level = 1; level <= levels; level++) {
@@ -240,7 +241,7 @@ public class TextureManager {
 						int i = (y * lod) * icon.width + (x * lod);
 						int j = y * (icon.width/lod) + x;
 
-						Buffer.buffer.put(j * 4 + 0, anim.imageData[i * 4 + 0]);
+						Buffer.buffer.put(j * 4, anim.imageData[i * 4]);
 						Buffer.buffer.put(j * 4 + 1, anim.imageData[i * 4 + 1]);
 						Buffer.buffer.put(j * 4 + 2, anim.imageData[i * 4 + 2]);
 						Buffer.buffer.put(j * 4 + 3, anim.imageData[i * 4 + 3]);
@@ -262,13 +263,13 @@ public class TextureManager {
 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
 		
-		if (blurTexture) {
+		if (this.blurTexture) {
 			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
 			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
 		}
-		if (clampTexture) {
-			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
+		if (this.clampTexture) {
+			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
 		} else {
 			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
 			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
@@ -291,7 +292,7 @@ public class TextureManager {
 	}
 
 	public void updateDynamicTextures(boolean isPaused) {
-        List<DynamicTexture> dynamics = new ArrayList<>(dynamicTextures.values());
+        List<DynamicTexture> dynamics = new ArrayList<>(this.dynamicTextures.values());
 		for (DynamicTexture dynamicTexture : dynamics) {
 			try {
 				if (dynamicTexture.runUpdates(isPaused)) {
@@ -299,14 +300,14 @@ public class TextureManager {
 				}
 			} catch(Exception e){
                 LOGGER.error("Exception while updating dynamic for '{}'. Removing from dynamic texture pool and skipping!", dynamicTexture.targetTexture.namespaceId, e);
-				dynamicTextures.remove(dynamicTexture.targetTexture.namespaceId); // Remove broken texture
+                this.dynamicTextures.remove(dynamicTexture.targetTexture.namespaceId); // Remove broken texture
 			}
 		}
 	}
 	
 	public BufferedImage getImage(String name) {
 		try {
-			return readImage(texturePacks.getResourceAsStream(name));
+			return readImage(this.texturePacks.getResourceAsStream(name));
 		}catch (Exception e) {
 			return Textures.missingTexture;
 		}
@@ -322,21 +323,21 @@ public class TextureManager {
         if(!errors.isEmpty()) {
         	String string = createErrorString(errors);
         	
-        	if(mc.currentScreen != null) {
-                PopupBuilder builder = new PopupBuilder(this.mc.currentScreen, mc.resolution.getScaledWidthScreenCoords() - 40);
+        	if(this.mc.currentScreen != null) {
+                PopupBuilder builder = new PopupBuilder(this.mc.currentScreen, this.mc.resolution.getScaledWidthScreenCoords() - 40);
                 builder.closeOnClickOut(0);
                 builder.closeOnEnter(0);
                 builder.closeOnEsc(0);
-                builder.withMessageBox("what", mc.resolution.getScaledHeightScreenCoords() - 120, string, Integer.MAX_VALUE);
+                builder.withMessageBox("what", this.mc.resolution.getScaledHeightScreenCoords() - 120, string, Integer.MAX_VALUE);
                 builder.withButtonGroup("ok", new String[] {"gui.options.button.done"}, new int[] {0});
             	PopupScreen popup = builder.build();
-            	
-            	mc.displayScreen(popup);
+
+                this.mc.displayScreen(popup);
         	}else {
         		String[] lines = string.split("\n");
 
                 for (String line : lines) {
-                    mc.hudIngame.addChatMessage(line);
+                    this.mc.hudIngame.addChatMessage(line);
                 }
         	}
         }
@@ -388,25 +389,25 @@ public class TextureManager {
 		// Animations may change the size of textures, so they need to be initialized before the atlas is generated
 
 		long start = System.nanoTime();
-		for (AtlasStitcher stitcher : TextureRegistry.stitcherMap.values()){
+		for (AtlasStitcher stitcher : TextureRegistry.atlases){
 			stitcher.preinit();
 		}
         LOGGER.debug("Took '{}' seconds to load atlases.", (System.nanoTime() - start) / 1_000_000_000d);
 
 		initDynamicTextures(errors);
 
-		for (AtlasStitcher stitcher : TextureRegistry.stitcherMap.values()){
+		for (AtlasStitcher stitcher : TextureRegistry.atlases){
 			stitcher.init();
 		}
 
-        for (DynamicTexture dynamicTexture : dynamicTextures.values()) {
+        for (DynamicTexture dynamicTexture : this.dynamicTextures.values()) {
             dynamicTexture.postInit();
         }
 
-		for (TextureBuffered t : bufferedTextures) {
+		for (TextureBuffered t : this.bufferedTextures) {
 			t.init();
 		}
-		for (Texture t : textureMap.values()) {
+		for (Texture t : this.textureMap.values()) {
 			t.init();
 		}
 
@@ -414,13 +415,13 @@ public class TextureManager {
 
 		Fonts.refreshFonts(this.mc.texturePackList);
 
-		mc.skinVariantList.refresh(errors);
-		mc.mainMenuBackground.refresh(errors);
+        this.mc.skinVariantList.refresh(errors);
+        this.mc.mainMenuBackground.refresh(errors);
 		
         Colorizers.reload();
         Colorizers.update(true);
-        
-        mc.worldRenderer.lightmapHelper.setup();
+
+        this.mc.worldRenderer.lightmapHelper.setup();
 	}
 
 	public void bindTexture(Texture texture) {
@@ -442,10 +443,10 @@ public class TextureManager {
 				return false;
 			}
 		}
-		TextureDownloaded texture = downloadedTextures.get(urlTexture);
+		TextureDownloaded texture = this.downloadedTextures.get(urlTexture);
 		if(texture == null) {
 			texture = new TextureDownloaded(urlTexture, imageParser);
-			downloadedTextures.put(urlTexture, texture);
+            this.downloadedTextures.put(urlTexture, texture);
 		}
 		if(!texture.isGenerated()) {
 			if(texture.image != null) {
diff --git a/game/client/src/main/java/net/minecraft/client/render/TileEntityRenderDispatcher.java b/game/client/src/main/java/net/minecraft/client/render/TileEntityRenderDispatcher.java
index d810299ae..5ad45565f 100644
--- a/game/client/src/main/java/net/minecraft/client/render/TileEntityRenderDispatcher.java
+++ b/game/client/src/main/java/net/minecraft/client/render/TileEntityRenderDispatcher.java
@@ -6,16 +6,15 @@ import net.minecraft.client.Minecraft;
 import net.minecraft.client.option.GameSettings;
 import net.minecraft.client.render.camera.ICamera;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texturepack.TexturePackList;
 import net.minecraft.client.render.tileentity.*;
-import net.minecraft.core.Global;
 import net.minecraft.core.block.entity.*;
 import net.minecraft.core.block.piston.TileEntityMovingPistonBlock;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 public final class TileEntityRenderDispatcher
 {
@@ -113,7 +112,7 @@ public final class TileEntityRenderDispatcher
         this.viewLerpPosZ = camera.getZ(partialTick);
     }
 
-    public <T extends TileEntity> void renderTileEntity(final @NotNull Tessellator tessellator, final ICamera camera, final @NotNull T tileEntity, final float partialTick)
+    public <T extends TileEntity> void renderTileEntity(final @NotNull TessellatorGeneral tessellator, final ICamera camera, final @NotNull T tileEntity, final float partialTick)
     {
         final TileEntityRenderer<T> renderer = TileEntityRenderDispatcher.instance.getRenderer(tileEntity);
 
@@ -122,16 +121,8 @@ public final class TileEntityRenderDispatcher
         if (!renderer.isVisible(tileEntity, camera, partialTick)) return;
 
         assert this.world != null;
-        final float brightness;
-        if(LightmapHelper.isLightmapEnabled()) {
-            LightmapHelper.setLightmapCoord(this.world.getLightmapCoord(tileEntity.x, tileEntity.y, tileEntity.z, 0));
-            brightness = 1.0f;
-        }else if(Global.accessor.isFullbrightEnabled()) {
-            brightness = 1.0f;
-        }else {
-            brightness = this.world.getLightBrightness(tileEntity.x, tileEntity.y, tileEntity.z);
-        }
-        GL11.glColor3f(brightness, brightness, brightness);
+        GLRenderer.setLightmapCoord1i(this.world.getLightmapCoord(tileEntity.x, tileEntity.y, tileEntity.z, 0));
+        GLRenderer.setColor3f(1f, 1f, 1f);
         renderer.doRender(tessellator,
             tileEntity,
             (double)tileEntity.x - renderPosX,
@@ -139,7 +130,7 @@ public final class TileEntityRenderDispatcher
             (double)tileEntity.z - renderPosZ, partialTick);
     }
 
-    public <T extends TileEntity> void renderTileEntity(final @NotNull Tessellator tessellator, final @NotNull T tileEntity, final double x, final double y, final double z, final float partialTick)
+    public <T extends TileEntity> void renderTileEntity(final @NotNull TessellatorGeneral tessellator, final @NotNull T tileEntity, final double x, final double y, final double z, final float partialTick)
     {
         final TileEntityRenderer<T> renderer = getRenderer(tileEntity);
         if(renderer != null)
diff --git a/game/client/src/main/java/net/minecraft/client/render/WorldRenderer.java b/game/client/src/main/java/net/minecraft/client/render/WorldRenderer.java
index 9765a92d1..7dbf69160 100644
--- a/game/client/src/main/java/net/minecraft/client/render/WorldRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/WorldRenderer.java
@@ -1,17 +1,22 @@
 package net.minecraft.client.render;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.util.List;
 import java.util.Random;
 
 import com.mojang.logging.LogUtils;
+import net.minecraft.client.render.culling.CameraFrustum;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.CompareFunc;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.window.CursorShape;
 import net.minecraft.client.render.worldtype.WorldTypeFXDispatcher;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.block.material.Materials;
 import net.minecraft.core.entity.Mob;
 import net.minecraft.core.entity.animal.MobPig;
+import net.minecraft.core.world.pos.TilePos;
 import net.minecraft.core.world.weather.IPrecipitation;
 import org.jetbrains.annotations.NotNull;
 import org.joml.Matrix4f;
@@ -20,8 +25,6 @@ import org.joml.Vector3dc;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
 import org.lwjgl.input.Mouse;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.util.glu.GLU;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.particle.ParticleWaterDrop;
@@ -40,9 +43,8 @@ import net.minecraft.client.render.camera.EntityCameraSleeping;
 import net.minecraft.client.render.camera.EntityCameraThirdPersonFront;
 import net.minecraft.client.render.camera.EntityCameraThirdPersonRear;
 import net.minecraft.client.render.colorizer.Colorizers;
-import net.minecraft.client.render.culling.Frustum;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.util.debug.Debug;
 import net.minecraft.core.util.phys.HitResult;
 import net.minecraft.core.entity.Entity;
@@ -54,6 +56,7 @@ import net.minecraft.core.world.World;
 import net.minecraft.core.world.biome.Biome;
 import net.minecraft.core.world.chunk.provider.IChunkProvider;
 import net.minecraft.core.world.weather.Weather;
+import org.lwjgl.opengl.GL41;
 import org.slf4j.Logger;
 
 public class WorldRenderer {
@@ -61,7 +64,7 @@ public class WorldRenderer {
     public static final long nsPerSecond = 1_000_000_000L;
     public final LightmapHelper lightmapHelper;
     public Minecraft mc;
-    private float farPlaneDistance;
+    public float farPlaneDistance;
     public ItemRenderer itemRenderer;
     public FogManager fogManager;
     private int rendererUpdateCount;
@@ -108,15 +111,14 @@ public class WorldRenderer {
         this.lightmapHelper.tick();
     }
 
-    private float b = 1.0f;
-    private float a = 1.0f;
-    private float currentFovModifier = 1.0f;
+    private float fovMod = 1.0f;
+    private float fovModOld = 1.0f;
 
     private void updateSpeedFov() {
         PlayerLocal player = this.mc.thePlayer;
-        this.currentFovModifier = this.mc.gameSettings.fovModification.value ? player.getFovModifier() : 1f;
-        this.a = this.b;
-        this.b += (this.currentFovModifier - this.b) * 0.5f;
+        float currentFovModifier = this.mc.gameSettings.fovModification.value ? player.getFovModifier() : 1f;
+        this.fovModOld = this.fovMod;
+        this.fovMod += (currentFovModifier - this.fovMod) * 0.5f;
     }
 
     public void getMouseOver(float partialTicks) {
@@ -204,7 +206,7 @@ public class WorldRenderer {
         float fov = 70f;
         if (isModifiedByFOV) {
             fov = (int) (this.mc.activeCamera.getFov() * 100 + 30);
-            fov *= this.a + (this.b - this.a) * partialTick;
+            fov *= org.joml.Math.lerp(this.fovModOld, this.fovMod, partialTick);
         }
         if (this.mc.gameSettings.fovModification.value && CameraUtil.isUnderLiquid(this.mc.activeCamera, this.mc.currentWorld, Materials.WATER, partialTick)) {
             fov = fov - 10;
@@ -216,66 +218,25 @@ public class WorldRenderer {
         return fov + this.fovModifierLast + (this.fovModifier - this.fovModifierLast) * partialTick;
     }
 
-    @Deprecated
-    private void hurtCameraEffect(float partialTick) {
-        if (!(this.mc.activeCamera instanceof EntityCamera entityCamera)) return;
-        Mob mob = entityCamera.mob;
-        float f1 = (float) mob.hurtTime - partialTick;
-        if (mob.getHealth() <= 0) {
-            float f2 = (float) mob.deathTime + partialTick;
-            glRotatef(40F - 8000F / (f2 + 200F), 0.0F, 0.0F, 1.0F);
-        }
-        if (f1 >= 0.0F) {
-            f1 /= mob.maxHurtTime;
-            f1 = MathHelper.sin(f1 * f1 * f1 * f1 * MathHelper.PI);
-            float f3 = mob.attackedAtYaw;
-            glRotatef(-f3, 0.0F, 1.0F, 0.0F);
-            glRotatef(-f1 * 14F, 0.0F, 0.0F, 1.0F);
-            glRotatef(f3, 0.0F, 1.0F, 0.0F);
-        }
-    }
-
     private @NotNull Matrix4f hurtCameraEffect(@NotNull Matrix4f matrix, float partialTick) {
         if (!(this.mc.activeCamera instanceof EntityCamera entityCamera)) return matrix;
         Mob mob = entityCamera.mob;
         float hurtInterp = (float) mob.hurtTime - partialTick;
         if (mob.getHealth() <= 0) {
             float f2 = (float) mob.deathTime + partialTick;
-            matrix.rotate(org.joml.Math.toRadians(40F - 8000F / (f2 + 200F)), 0.0F, 0.0F, 1.0F);
+            matrix.rotateZ(org.joml.Math.toRadians(40F - 8000F / (f2 + 200F)));
         }
         if (hurtInterp >= 0.0F) {
             hurtInterp /= mob.maxHurtTime;
             hurtInterp = MathHelper.sin(hurtInterp * hurtInterp * hurtInterp * hurtInterp * MathHelper.PI);
             float f3 = mob.attackedAtYaw;
-            matrix.rotate(org.joml.Math.toRadians(-f3), 0.0F, 1.0F, 0.0F);
-            matrix.rotate(org.joml.Math.toRadians(-hurtInterp * 14F), 0.0F, 0.0F, 1.0F);
-            matrix.rotate(org.joml.Math.toRadians(f3), 0.0F, 1.0F, 0.0F);
+            matrix.rotateY(org.joml.Math.toRadians(-f3));
+            matrix.rotateZ(org.joml.Math.toRadians(-hurtInterp * 14F));
+            matrix.rotateY(org.joml.Math.toRadians(f3));
         }
         return matrix;
     }
 
-    @Deprecated
-    private void setupViewBobbing(float partialTick, boolean isHand) {
-        if (this.mc.activeCamera instanceof EntityCamera && ((EntityCamera) this.mc.activeCamera).mob instanceof Player player) {
-            float walkDist = -MathHelper.lerp(player.walkDistO, player.walkDist, partialTick);
-            float cameraVel = MathHelper.lerp(player.cameraVelocityOld, player.cameraVelocity, partialTick);
-            float cameraPitch = MathHelper.lerp(player.prevCameraPitch, player.cameraPitch, partialTick);
-            if (isHand && player.vehicle instanceof MobPig) {
-                cameraVel /= 4;
-//                cameraPitch /= 4;
-                walkDist /= 2;
-            }
-            if (player.isSkating) {
-                walkDist *= 0.25f;
-                cameraPitch *= 0.25f;
-            }
-            GL11.glTranslatef(MathHelper.sin(walkDist * MathHelper.PI) * cameraVel * 0.5F, -Math.abs(MathHelper.cos(walkDist * MathHelper.PI) * cameraVel), 0.0F);
-            GL11.glRotatef(MathHelper.sin(walkDist * MathHelper.PI) * cameraVel * 3F, 0.0F, 0.0F, 1.0F);
-            GL11.glRotatef(java.lang.Math.abs(MathHelper.cos(walkDist * MathHelper.PI - 0.2F) * cameraVel) * 5F, 1.0F, 0.0F, 0.0F);
-            GL11.glRotatef(cameraPitch, 1.0F, 0.0F, 0.0F);
-        }
-    }
-
     private @NotNull Matrix4f setupViewBobbing(@NotNull Matrix4f matrix, float partialTick, boolean isHand) {
         if (this.mc.activeCamera instanceof EntityCamera entityCamera && entityCamera.mob instanceof Player player) {
             float walkDist = -MathHelper.lerp(player.walkDistO, player.walkDist, partialTick);
@@ -291,9 +252,9 @@ public class WorldRenderer {
                 cameraPitch *= 0.25f;
             }
             matrix.translate(MathHelper.sin(walkDist * MathHelper.PI) * cameraVel * 0.5F, -Math.abs(MathHelper.cos(walkDist * MathHelper.PI) * cameraVel), 0.0F);
-            matrix.rotate(org.joml.Math.toRadians(MathHelper.sin(walkDist * MathHelper.PI) * cameraVel * 3F), 0.0F, 0.0F, 1.0F);
-            matrix.rotate(org.joml.Math.toRadians(org.joml.Math.abs(MathHelper.cos(walkDist * MathHelper.PI - 0.2F) * cameraVel) * 5F), 1.0F, 0.0F, 0.0F);
-            matrix.rotate(org.joml.Math.toRadians(cameraPitch), 1.0F, 0.0F, 0.0F);
+            matrix.rotateZ(org.joml.Math.toRadians(MathHelper.sin(walkDist * MathHelper.PI) * cameraVel * 3F));
+            matrix.rotateX(org.joml.Math.toRadians(org.joml.Math.abs(MathHelper.cos(walkDist * MathHelper.PI - 0.2F) * cameraVel) * 5F));
+            matrix.rotateX(org.joml.Math.toRadians(cameraPitch));
         }
         return matrix;
     }
@@ -321,74 +282,23 @@ public class WorldRenderer {
 
     }
 
-    @Deprecated
-    private void orientCamera(float partialTick) {
-        setupCamera(partialTick);
-        this.mc.activeCamera.applyGlTransformations();
-
-        if (!(this.mc.currentScreen instanceof ScreenPhotoMode) && !this.mc.gameSettings.lockCamera.value) {
-            glRotatef((float) this.mc.activeCamera.getXRot(partialTick), 1.0F, 0.0F, 0.0F);
-            glRotatef((float) (this.mc.activeCamera.getYRot(partialTick) + 180F), 0.0F, 1.0F, 0.0F);
-        }
-
-        if (this.mc.currentScreen instanceof ScreenPhotoMode) {
-            glRotatef(((ScreenPhotoMode) this.mc.currentScreen).getTilt(partialTick), 1.0F, 0.0F, 0.0F);
-            glRotatef(45f + 45F * ((ScreenPhotoMode) this.mc.currentScreen).getRotation(partialTick), 0.0F, 1.0F, 0.0F);
-        }
-    }
-
     public @NotNull Matrix4f orientCamera(@NotNull Matrix4f matrix, float partialTick) {
         setupCamera(partialTick);
 
         if (!(this.mc.currentScreen instanceof ScreenPhotoMode) && !this.mc.gameSettings.lockCamera.value) {
-            matrix.rotate(org.joml.Math.toRadians((float) this.mc.activeCamera.getXRot(partialTick)), 1.0F, 0.0F, 0.0F);
-            matrix.rotate(org.joml.Math.toRadians((float) (this.mc.activeCamera.getYRot(partialTick) + 180F)), 0.0F, 1.0F, 0.0F);
+            matrix.rotateX(org.joml.Math.toRadians((float) this.mc.activeCamera.getXRot(partialTick)));
+            matrix.rotateY(org.joml.Math.toRadians((float) (this.mc.activeCamera.getYRot(partialTick) + 180F)));
         }
 
         if (this.mc.currentScreen instanceof ScreenPhotoMode screenPhotoMode) {
-            matrix.rotate(org.joml.Math.toRadians(screenPhotoMode.getTilt(partialTick)), 1.0F, 0.0F, 0.0F);
-            matrix.rotate(org.joml.Math.toRadians(45f + 45F * screenPhotoMode.getRotation(partialTick)), 0.0F, 1.0F, 0.0F);
+            matrix.rotateX(org.joml.Math.toRadians(screenPhotoMode.getTilt(partialTick)));
+            matrix.rotateY(org.joml.Math.toRadians(45f + 45F * screenPhotoMode.getRotation(partialTick)));
         }
         return matrix;
     }
 
-    @Deprecated
-    private void setupCameraTransform(final float partialTicks) {
-        this.farPlaneDistance = this.mc.gameSettings.renderDistance.value * 16;
-        glMatrixMode(GL_PROJECTION);
-        glLoadIdentity();
-        float fov = getFOVModifier(partialTicks, true);
-        if (this.zooming) {
-            fov = getZoomedFOV(fov, partialTicks);
-        } else {
-            this.zoomProgress = 0;
-        }
-        if (this.mc.currentScreen instanceof ScreenPhotoMode) {
-            final double div = java.lang.Math.pow(2, ((ScreenPhotoMode) this.mc.currentScreen).getZoom(partialTicks));
-            glTranslatef(1, 1, 0);
-            glOrtho(0, this.mc.gameWindow.getWidthPixels() / div, 0, this.mc.gameWindow.getHeightPixels() / div, this.farPlaneDistance * -2.0f, this.farPlaneDistance * 2.0f);
-            glTranslatef(((ScreenPhotoMode) this.mc.currentScreen).getPanX(partialTicks), -((ScreenPhotoMode) this.mc.currentScreen).getPanY(partialTicks), 0);
-        } else {
-            GLU.gluPerspective(fov, (float) this.mc.gameWindow.getWidthPixels() / (float) this.mc.gameWindow.getHeightPixels(), 0.05F, this.farPlaneDistance * 2.0F);
-        }
-        glMatrixMode(GL_MODELVIEW);
-        glLoadIdentity();
-        hurtCameraEffect(partialTicks);
-        if (this.mc.gameSettings.viewBobbing.value && !(this.mc.currentScreen instanceof ScreenPhotoMode)) {
-            setupViewBobbing(partialTicks, false);
-        }
-        final float portalIntensity = this.mc.gameSettings.screenMotionEffects.value ? MathHelper.lerp(this.mc.thePlayer.prevTimeInPortal, this.mc.thePlayer.timeInPortal, partialTicks) : 0f;
-        if (portalIntensity > 0.0F) {
-            float f3 = 5F / (portalIntensity * portalIntensity + 5F) - portalIntensity * 0.04F;
-            f3 *= f3;
-            glRotatef(((float) this.rendererUpdateCount + partialTicks) * 20F, 0.0F, 1.0F, 1.0F);
-            glScalef(1.0F / f3, 1.0F, 1.0F);
-            glRotatef(-((float) this.rendererUpdateCount + partialTicks) * 20F, 0.0F, 1.0F, 1.0F);
-        }
-        orientCamera(partialTicks);
-    }
-
     public @NotNull Matrix4f getProjectionMatrix(@NotNull Matrix4f matrix, float partialTick) {
+        matrix.identity();
         this.farPlaneDistance = this.mc.gameSettings.renderDistance.value * 16;
         float fov = getFOVModifier(partialTick, true);
         if (this.zooming) {
@@ -428,8 +338,9 @@ public class WorldRenderer {
     }
 
     private void renderHand(float partialTick) {
-        glMatrixMode(GL_PROJECTION);
-        glLoadIdentity();
+        Matrix4f projMat = GLRenderer.projectionM4f();
+        projMat.identity();
+        this.farPlaneDistance = this.mc.gameSettings.renderDistance.value * 16;
         float fov = getFOVModifier(partialTick, false);
         if (this.zooming) {
             fov = getZoomedFOV(fov, partialTick);
@@ -437,34 +348,37 @@ public class WorldRenderer {
             this.zoomProgress = 0;
         }
         // Fix hand being rendered inside of blocks / behind rain
-        glTranslatef(0.0f, 0.0f, -1.0f);
-        glScalef(1.0f, 1.0f, 0.1f);
+        projMat.translate(0.0f, 0.0f, -1.0f);
+        projMat.scale(1.0f, 1.0f, 0.1f);
+
+        projMat.perspective(org.joml.Math.toRadians(fov), (float) this.mc.gameWindow.getWidthPixels() / (float) this.mc.gameWindow.getHeightPixels(), 0.05F, this.farPlaneDistance * 2.0F);
+
+        Matrix4f viewMat = GLRenderer.viewM4f();
+        viewMat.identity();
 
-        GLU.gluPerspective(fov, (float) this.mc.gameWindow.getWidthPixels() / (float) this.mc.gameWindow.getHeightPixels(), 0.05F, this.farPlaneDistance * 2.0F);
-        glMatrixMode(GL_MODELVIEW);
-        glLoadIdentity();
+        GLRenderer.modelM4f().identity();
 
-        glPushMatrix();
-        hurtCameraEffect(partialTick);
+        GLRenderer.pushFrame();
+        hurtCameraEffect(viewMat, partialTick);
         if (this.mc.gameSettings.viewBobbing.value) {
-            setupViewBobbing(partialTick, true);
+            setupViewBobbing(viewMat, partialTick, true);
         }
         if (this.mc.gameSettings.thirdPersonView.value == 0 && !(this.mc.currentScreen instanceof ScreenPhotoMode) && !(!(this.mc.activeCamera instanceof EntityCamera) || ((EntityCamera) this.mc.activeCamera).mob.isPlayerSleeping()) && this.mc.gameSettings.immersiveMode.drawHand()) {
             this.lightmapHelper.enableLightmapRendering();
             if (!this.zooming) this.itemRenderer.renderItemInFirstPerson(partialTick);
             this.lightmapHelper.disableLightmapRendering();
         }
-        glPopMatrix();
+        GLRenderer.popFrame();
 
         Debug.change("post");
         this.mc.renderer.endRenderWorld(partialTick);
 
         if (this.mc.gameSettings.thirdPersonView.value == 0 && !(!(this.mc.activeCamera instanceof EntityCamera) || ((EntityCamera) this.mc.activeCamera).mob.isPlayerSleeping())) {
             this.itemRenderer.renderOverlays(partialTick);
-            hurtCameraEffect(partialTick);
+            hurtCameraEffect(viewMat, partialTick);
         }
         if (this.mc.gameSettings.viewBobbing.value) {
-            setupViewBobbing(partialTick, false);
+            setupViewBobbing(viewMat, partialTick, false);
         }
     }
 
@@ -570,7 +484,7 @@ public class WorldRenderer {
             c = this.mc.gameSettings.customFpsLimit.value;
         }
         if (c <= 0) c = 1;
-        glViewport(0, 0, this.mc.gameWindow.getWidthPixels(), this.mc.gameWindow.getHeightPixels());
+        GL41.glViewport(0, 0, this.mc.gameWindow.getWidthPixels(), this.mc.gameWindow.getHeightPixels());
         if (this.mc.currentWorld != null) {
             Debug.change("world");
             if (!this.mc.gameSettings.enableVsync.value && this.mc.gameSettings.customFpsLimit.value == 0) // Max FPS
@@ -601,10 +515,9 @@ public class WorldRenderer {
             this.mc.hudIngame.renderGameOverlay(partialTick, this.mc.currentScreen != null, mouseX, mouseY);
             Debug.change("misc");
         } else {
-            glMatrixMode(GL_PROJECTION);
-            glLoadIdentity();
-            glMatrixMode(GL_MODELVIEW);
-            glLoadIdentity();
+            GLRenderer.projectionM4f().identity();
+            GLRenderer.viewM4f().identity();
+            GLRenderer.modelM4f().identity();
             setupScaledResolution();
             if (this.mc.gameSettings.enableVsync.value || this.mc.gameSettings.customFpsLimit.value > 0) {
                 Debug.change("sleep");
@@ -628,8 +541,14 @@ public class WorldRenderer {
         this.mc.guiToasts.render(partialTick);
 
         if (this.mc.currentScreen != null) {
+            GLRenderer.pushFrame();
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.enableState(State.DEPTH_TEST);
+            GLRenderer.setDepthFunc(CompareFunc.LESS_EQUAL);
+
             Debug.change("gui");
-            glClear(256);
+            GL41.glClear(GL41.GL_DEPTH_BUFFER_BIT);
             if (this.mc.inputType == InputType.CONTROLLER) {
                 mouseX = (int) this.mc.controllerInput.cursorX;
                 mouseY = (int) this.mc.controllerInput.cursorY;
@@ -650,28 +569,27 @@ public class WorldRenderer {
                 this.mc.currentScreen.drawControllerCursor();
             }
             Debug.change("misc");
+            GLRenderer.popFrame();
         }
     }
 
     public void renderWorld(float partialTicks, long updateRenderersUntil) {
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.WORLD);
         Debug.push("misc");
         Colorizers.update(false);
 
         RenderGlobal renderGlobal = this.mc.renderGlobal;
         ParticleEngine particleEngine = this.mc.particleEngine;
 
-        glEnable(GL_CULL_FACE);
-        glEnable(GL_DEPTH_TEST);
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.enableState(State.DEPTH_TEST);
         if (this.mc.activeCamera == null) {
             this.mc.activeCamera = new EntityCameraFirstPerson(this.mc, this.mc.thePlayer);
         }
         getMouseOver(partialTicks);
-        Mob activeEntity = null;
-        if (this.mc.activeCamera instanceof EntityCamera) {
-            activeEntity = ((EntityCamera) this.mc.activeCamera).mob;
-        }
-
-        if (activeEntity != null) {
+        if (this.mc.activeCamera instanceof EntityCamera camera) {
+            Mob activeEntity = camera.mob;
             double viewEntityX = activeEntity.xo + (activeEntity.x - activeEntity.xo) * (double) partialTicks;
             double viewEntityZ = activeEntity.zo + (activeEntity.z - activeEntity.zo) * (double) partialTicks;
             IChunkProvider iChunkProvider = this.mc.currentWorld.getChunkProvider();
@@ -684,24 +602,19 @@ public class WorldRenderer {
 
         Debug.change("post");
         this.mc.renderer.beginRenderWorld(partialTicks);
-        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
-        glEnable(GL_CULL_FACE);
-        setupCameraTransform((this.mc.activeCamera instanceof EntityCamera && ((EntityCamera) this.mc.activeCamera).mob.isRemoved()) ? 1f : partialTicks);
-        Frustum.getFrustum();
+        GL41.glClear(GL41.GL_COLOR_BUFFER_BIT | GL41.GL_DEPTH_BUFFER_BIT);
+        GLRenderer.enableState(State.CULL_FACE);
+        float pt = (this.mc.activeCamera instanceof EntityCamera entityCamera && entityCamera.mob.isRemoved()) ? 1f : partialTicks;
+        getProjectionMatrix(GLRenderer.projectionM4f(), pt);
+        getViewMatrix(GLRenderer.viewM4f(), pt);
+        CameraFrustum.recalcFrustrum();
         Debug.change("sky");
-        if ((this.mc.gameSettings.renderDistance.value > 4) /* Used to use Renderdistance rendersky! */ && !(this.mc.currentScreen instanceof ScreenModelViewer)) {
-            this.fogManager.setupFog(FogManager.FOG_MODE_SKY, this.farPlaneDistance, partialTicks);
-            glDisable(GL_FOG);
-
+        if ((this.mc.gameSettings.renderDistance.value > 4) && !(this.mc.currentScreen instanceof ScreenModelViewer)) {
             renderGlobal.renderSky(partialTicks);
         }
 
         Debug.change("misc");
-        glEnable(GL_FOG);
-        this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks);
-        if (this.mc.gameSettings.ambientOcclusion.value) {
-            glShadeModel(GL11.GL_SMOOTH);
-        }
+        this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks, GLRenderer.getFogState());
 
         this.mc.renderGlobal.cull(this.mc.activeCamera.getFrustum(), partialTicks);
 
@@ -725,46 +638,42 @@ public class WorldRenderer {
             } while (timeRemaining >= 0L && timeRemaining <= nsPerSecond);
         }
 
-        this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks);
-        glEnable(GL_FOG);
-        TextureRegistry.blockAtlas.bind();
+        this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks, GLRenderer.getFogState());
+        TextureRegistry.worldAtlas.bind();
         Lighting.disable();
 
         Debug.change("terrain");
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.WORLD);
+        GLRenderer.globalSetUniforms(Shaders.WORLD);
         this.lightmapHelper.enableLightmapRendering();
         this.mc.terrainRenderer.renderSolidTerrain(partialTicks);
+        GLRenderer.popFrame();
 
         Debug.change("entities");
-        glShadeModel(GL_FLAT);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         Lighting.enableLight();
-        if (!this.mc.gameSettings.fog.value) {
-            glDisable(GL_FOG);
-        }
         renderGlobal.renderEntities(this.mc.activeCamera, partialTicks);
-        if (!this.mc.gameSettings.fog.value) {
-            glEnable(GL_FOG);
-        }
 
         Debug.change("particles");
-        glDisable(GL_BLEND);
+        GLRenderer.disableState(State.BLEND);
         particleEngine.renderLitParticles(this.mc.activeCamera, partialTicks);
         Lighting.disable();
-        this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks);
+        this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks, GLRenderer.getFogState());
         this.mc.renderer.beginRenderParticles(partialTicks);
-        particleEngine.renderParticles(this.mc.renderer.getParticleTessellator(), this.mc.activeCamera, partialTicks);
+        particleEngine.renderParticles(this.mc.activeCamera, partialTicks);
         this.mc.renderer.endRenderParticles(partialTicks);
 
         this.lightmapHelper.disableLightmapRendering();
 
         Debug.change("outline");
         if (this.mc.objectMouseOver != null) {
-            glDisable(GL_ALPHA_TEST);
+//            glDisable(GL_ALPHA_TEST);
             if (this.mc.objectMouseOver instanceof HitResult.Tile hitTile) {
                 renderGlobal.drawBlockBreaking(this.mc.activeCamera, hitTile, partialTicks);
             }
             renderGlobal.drawSelectionBox(this.mc.activeCamera, this.mc.objectMouseOver, partialTicks);
-            glEnable(GL_ALPHA_TEST);
+//            glEnable(GL_ALPHA_TEST);
         }
 
         Debug.change("debugoverlays");
@@ -774,52 +683,46 @@ public class WorldRenderer {
         if (this.mc.gameSettings.showChunkBorders.value) {
             renderGlobal.drawDebugChunkBorders(this.mc.activeCamera, partialTicks);
         }
-        glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-        this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks);
-        glEnable(GL_BLEND);
-        glDisable(GL_CULL_FACE);
-        TextureRegistry.blockAtlas.bind();
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks, GLRenderer.getFogState());
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.enableState(State.CULL_FACE);
+        TextureRegistry.worldAtlas.bind();
 
         Debug.change("water");
         this.lightmapHelper.enableLightmapRendering();
-        if (this.mc.gameSettings.ambientOcclusion.value) {
-            glShadeModel(GL_SMOOTH);
-        }
-        if (!this.mc.gameSettings.fog.value) {
-            glDisable(GL_FOG);
-        }
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.disableState(State.CULL_FACE);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setShader(Shaders.WORLD);
+        GLRenderer.globalSetUniforms(Shaders.WORLD);
         this.mc.terrainRenderer.renderTranslucentTerrain(partialTicks);
-        if (!this.mc.gameSettings.fog.value) {
-            glEnable(GL_FOG);
-        }
-        glShadeModel(GL_FLAT);
+        GLRenderer.popFrame();
         this.lightmapHelper.disableLightmapRendering();
 
         Debug.change("weather");
-        glDepthMask(true);
-        glEnable(GL_CULL_FACE);
-        glDisable(GL_BLEND);
+        GLRenderer.setDepthMask(true);
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.disableState(State.BLEND);
         renderRainSnow(partialTicks);
-        glDisable(GL_FOG);
         if (this.mc.gameSettings.clouds.value) {
             Debug.change("clouds");
-            this.fogManager.setupFog(FogManager.FOG_MODE_NORMAL, this.farPlaneDistance, partialTicks);
-            glEnable(GL_FOG);
+            this.fogManager.setupFog(FogManager.FOG_MODE_SKY, this.farPlaneDistance, partialTicks, GLRenderer.getFogState());
             renderGlobal.renderClouds(partialTicks);
-            glDisable(GL_FOG);
         }
 
         Debug.change("misc");
-        this.fogManager.setupFog(1, this.farPlaneDistance, partialTicks);
-        renderHand((this.mc.activeCamera instanceof EntityCamera && ((EntityCamera) this.mc.activeCamera).mob.isRemoved()) ? 1f : partialTicks);
+        this.fogManager.setupFog(1, this.farPlaneDistance, partialTicks, GLRenderer.getFogState());
+        renderHand((this.mc.activeCamera instanceof EntityCamera camera && camera.mob.isRemoved()) ? 1f : partialTicks);
 
-        glColorMask(true, true, true, true);
         Debug.pop();
+        GLRenderer.popFrame();
     }
 
     private void addRainParticles() {
         Weather weather = this.mc.currentWorld.getCurrentWeather();
-        if (!(weather instanceof IPrecipitation) || !((IPrecipitation) weather).spawnRainParticles()) return;
+        if (!(weather instanceof IPrecipitation precipitation) || !precipitation.spawnRainParticles()) return;
 
         float f = this.mc.currentWorld.weatherManager.getWeatherIntensity() * this.mc.currentWorld.weatherManager.getWeatherPower();
 
@@ -889,12 +792,15 @@ public class WorldRenderer {
         int posX = MathHelper.floor(this.mc.activeCamera.getX());
         int posY = MathHelper.floor(this.mc.activeCamera.getY());
         int posZ = MathHelper.floor(this.mc.activeCamera.getZ());
-        Tessellator tessellator = Tessellator.instance;
-        glDisable(GL11.GL_CULL_FACE);
-        glNormal3f(0.0F, 1.0F, 0.0F);
-        glEnable(GL11.GL_BLEND);
-        glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-        glAlphaFunc(516, 0.01F);
+        TessellatorGeneral tessellator = GLRenderer.getTessellator();
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.WORLD);
+        GLRenderer.setLightmapCoord2i(15, 15);
+        GLRenderer.disableState(State.CULL_FACE);
+//        glNormal3f(0.0F, 1.0F, 0.0F);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+//        glAlphaFunc(516, 0.01F);
 
         this.mc.textureManager.loadTexture(precipitation.getPrecipitationTexturePath(world.weatherManager.getWeatherPower(), world.weatherManager.getWeatherIntensity())).bind();
 
@@ -904,7 +810,10 @@ public class WorldRenderer {
         int floorPosY = MathHelper.floor(nextPosY);
         int radiusEffect = 10;
 
+        TilePos queryPos = new TilePos();
+
         if (precipitation.getPrecipitationType() == IPrecipitation.Type.SNOW_LIKE) {
+            tessellator.startDrawingQuads();
             for (int x = posX - radiusEffect; x <= posX + radiusEffect; x++) {
                 blockedWeather:
                 for (int z = posZ - radiusEffect; z <= posZ + radiusEffect; z++) {
@@ -940,26 +849,30 @@ public class WorldRenderer {
                         double d5 = (double) ((float) x + 0.5F) - this.mc.activeCamera.getX();
                         double d6 = (double) ((float) z + 0.5F) - this.mc.activeCamera.getZ();
                         float f11 = MathHelper.sqrt(d5 * d5 + d6 * d6) / (float) radiusEffect;
-                        tessellator.startDrawingQuads();
-                        float f12 = world.getLightBrightness(x, i3, z);
-                        if (this.mc.fullbright) f12 = 1.0f;
-                        glColor4f(f12, f12, f12, ((1.0F - f11 * f11) * 0.3F + 0.5F) * world.weatherManager.getWeatherIntensity() * world.weatherManager.getWeatherPower());
+                        float brightness;
+                        if (this.mc.fullbright) {
+                            brightness = 1.0f;
+                        } else {
+                            brightness = world.getLightBrightness(queryPos.set(x, i3, z));
+                        }
+                        tessellator.setColor4f(brightness, brightness, brightness, ((1.0F - f11 * f11) * 0.3F + 0.5F) * world.weatherManager.getWeatherIntensity() * world.weatherManager.getWeatherPower());
                         tessellator.setTranslation(-nextPosX, -nextPosY, -nextPosZ);
                         tessellator.addVertexWithUV(x, k3, (double) z + 0.5D, 0.0F * f3 + f7, ((float) k3 * f3) / 4F + f6 * f3 + f8);
                         tessellator.addVertexWithUV(x + 1, k3, (double) z + 0.5D, f3 + f7, ((float) k3 * f3) / 4F + f6 * f3 + f8);
                         tessellator.addVertexWithUV(x + 1, i4, (double) z + 0.5D, f3 + f7, ((float) i4 * f3) / 4F + f6 * f3 + f8);
                         tessellator.addVertexWithUV(x, i4, (double) z + 0.5D, 0.0F * f3 + f7, ((float) i4 * f3) / 4F + f6 * f3 + f8);
+
                         tessellator.addVertexWithUV((double) x + 0.5D, k3, z, 0.0F * f3 + f7, ((float) k3 * f3) / 4F + f6 * f3 + f8);
                         tessellator.addVertexWithUV((double) x + 0.5D, k3, z + 1, f3 + f7, ((float) k3 * f3) / 4F + f6 * f3 + f8);
                         tessellator.addVertexWithUV((double) x + 0.5D, i4, z + 1, f3 + f7, ((float) i4 * f3) / 4F + f6 * f3 + f8);
                         tessellator.addVertexWithUV((double) x + 0.5D, i4, z, 0.0F * f3 + f7, ((float) i4 * f3) / 4F + f6 * f3 + f8);
                         tessellator.setTranslation(0.0D, 0.0D, 0.0D);
-                        tessellator.draw();
                     }
                 }
-
             }
+            tessellator.draw();
         } else if (precipitation.getPrecipitationType() == IPrecipitation.Type.RAIN_LIKE) {
+            tessellator.startDrawingQuads();
             for (int x = posX - radiusEffect; x <= posX + radiusEffect; x++) {
                 blockedWeather:
                 for (int z = posZ - radiusEffect; z <= posZ + radiusEffect; z++) {
@@ -980,31 +893,36 @@ public class WorldRenderer {
                     }
                     float f2 = 1.0F;
                     if (j3 != l3) {
-                        this.random.setSeed((long) x * x * 3121 /*GL_RGBA_MODE*/ + x * 0x2b24abbL + (long) z * z * 0x66397 + z * 13761L);
-                        float f4 = (((float) (this.rendererUpdateCount + x * x * 3121 /*GL_RGBA_MODE*/ + x * 0x2b24abb + z * z * 0x66397 + z * 13761 & 0x1f) + partialTick) / 32F) * (3F + this.random.nextFloat());
+                        this.random.setSeed((long) x * x * 3121 + x * 0x2b24abbL + (long) z * z * 0x66397 + z * 13761L);
+                        float f4 = (((float) (this.rendererUpdateCount + x * x * 3121 + x * 0x2b24abb + z * z * 0x66397 + z * 13761 & 0x1f) + partialTick) / 32F) * (3F + this.random.nextFloat());
                         double d3 = (double) ((float) x + 0.5F) - this.mc.activeCamera.getX();
                         double d4 = (double) ((float) z + 0.5F) - this.mc.activeCamera.getZ();
                         float f9 = MathHelper.sqrt(d3 * d3 + d4 * d4) / (float) radiusEffect;
-                        tessellator.startDrawingQuads();
-                        float f10 = world.getLightBrightness(x, world.getHeightBlocks(), z) * 0.85F + 0.15F;
-                        if (this.mc.fullbright) f10 = 1.0f;
-                        glColor4f(f10, f10, f10, ((1.0F - f9 * f9) * 0.5F + 0.5F) * (world.weatherManager.getWeatherIntensity() - 0.1f) * world.weatherManager.getWeatherPower());
+
+                        float brightness;
+                        if (this.mc.fullbright) {
+                            brightness = 1.0f;
+                        } else {
+                            brightness = world.getLightBrightness(queryPos.set(x, world.getHeightBlocks(), z)) * 0.85F + 0.15F;
+                        }
                         tessellator.setTranslation(-nextPosX, -nextPosY, -nextPosZ);
+                        tessellator.setColor4f(brightness, brightness, brightness, ((1.0F - f9 * f9) * 0.5F + 0.5F) * (world.weatherManager.getWeatherIntensity() - 0.1f) * world.weatherManager.getWeatherPower());
                         tessellator.addVertexWithUV(x, j3, (double) z + 0.5D, 0.0F * f2, ((float) j3 * f2) / 4F + f4 * f2);
                         tessellator.addVertexWithUV(x + 1, j3, (double) z + 0.5D, f2, ((float) j3 * f2) / 4F + f4 * f2);
                         tessellator.addVertexWithUV(x + 1, l3, (double) z + 0.5D, f2, ((float) l3 * f2) / 4F + f4 * f2);
                         tessellator.addVertexWithUV(x, l3, (double) z + 0.5D, 0.0F * f2, ((float) l3 * f2) / 4F + f4 * f2);
+
                         tessellator.addVertexWithUV((double) x + 0.5D, j3, z, 0.0F * f2, ((float) j3 * f2) / 4F + f4 * f2);
                         tessellator.addVertexWithUV((double) x + 0.5D, j3, z + 1, f2, ((float) j3 * f2) / 4F + f4 * f2);
                         tessellator.addVertexWithUV((double) x + 0.5D, l3, z + 1, f2, ((float) l3 * f2) / 4F + f4 * f2);
                         tessellator.addVertexWithUV((double) x + 0.5D, l3, z, 0.0F * f2, ((float) l3 * f2) / 4F + f4 * f2);
                         tessellator.setTranslation(0.0D, 0.0D, 0.0D);
-                        tessellator.draw();
                     }
                 }
-
             }
+            tessellator.draw();
         } else if (precipitation.getPrecipitationType() == IPrecipitation.Type.INVERTED_RAIN_LIKE) {
+            tessellator.startDrawingQuads();
             for (int x = posX - radiusEffect; x <= posX + radiusEffect; x++) {
                 blockedWeather:
                 for (int z = posZ - radiusEffect; z <= posZ + radiusEffect; z++) {
@@ -1025,15 +943,18 @@ public class WorldRenderer {
                     }
                     float f2 = 1.0F;
                     if (j3 != l3) {
-                        this.random.setSeed((long) x * x * 3121 /*GL_RGBA_MODE*/ + x * 0x2b24abbL + (long) z * z * 0x66397 + z * 13761L);
+                        this.random.setSeed((long) x * x * 3121 + x * 0x2b24abbL + (long) z * z * 0x66397 + z * 13761L);
                         float vOffset = (((float) (this.rendererUpdateCount + x * x * 3121 /*GL_RGBA_MODE*/ + x * 0x2b24abb + z * z * 0x66397 + z * 13761 & 0x1f) + partialTick) / 32F) * (3F + this.random.nextFloat());
                         double d3 = (double) ((float) x + 0.5F) - this.mc.activeCamera.getX();
                         double d4 = (double) ((float) z + 0.5F) - this.mc.activeCamera.getZ();
                         float f9 = MathHelper.sqrt(d3 * d3 + d4 * d4) / (float) radiusEffect;
-                        tessellator.startDrawingQuads();
-                        float f10 = world.getLightBrightness(x, world.getHeightBlocks(), z) * 0.85F + 0.15F;
-                        if (this.mc.fullbright) f10 = 1.0f;
-                        glColor4f(f10, f10, f10, ((1.0F - f9 * f9) * 0.5F + 0.5F) * (world.weatherManager.getWeatherIntensity() - 0.1f) * world.weatherManager.getWeatherPower());
+                        float brightness;
+                        if (this.mc.fullbright) {
+                            brightness = 1.0f;
+                        } else {
+                            brightness = world.getLightBrightness(queryPos.set(x, world.getHeightBlocks(), z)) * 0.85F + 0.15F;
+                        }
+                        tessellator.setColor4f(brightness, brightness, brightness, ((1.0F - f9 * f9) * 0.5F + 0.5F) * (world.weatherManager.getWeatherIntensity() - 0.1f) * world.weatherManager.getWeatherPower());
                         tessellator.setTranslation(-nextPosX, -nextPosY, -nextPosZ);
                         tessellator.addVertexWithUV(x, j3, (double) z + 0.5D, 0.0F * f2, ((float) j3 * f2) / 4F - vOffset * f2);
                         tessellator.addVertexWithUV(x + 1, j3, (double) z + 0.5D, f2, ((float) j3 * f2) / 4F - vOffset * f2);
@@ -1044,26 +965,17 @@ public class WorldRenderer {
                         tessellator.addVertexWithUV((double) x + 0.5D, l3, z + 1, f2, ((float) l3 * f2) / 4F - vOffset * f2);
                         tessellator.addVertexWithUV((double) x + 0.5D, l3, z, 0.0F * f2, ((float) l3 * f2) / 4F - vOffset * f2);
                         tessellator.setTranslation(0.0D, 0.0D, 0.0D);
-                        tessellator.draw();
                     }
                 }
-
             }
+            tessellator.draw();
         }
-
-
-        glEnable(GL11.GL_CULL_FACE);
-        glDisable(GL11.GL_BLEND);
-        glAlphaFunc(516, 0.1F);
+        GLRenderer.popFrame();
     }
 
     public void setupScaledResolution() {
-        glClear(256);
-        glMatrixMode(GL11.GL_PROJECTION);
-        glLoadIdentity();
-        glOrtho(0.0D, this.mc.resolution.getExactScaledWidthScreenCoords(), this.mc.resolution.getExactScaledHeightScreenCoords(), 0.0D, 1000D, 3000D);
-        glMatrixMode(GL11.GL_MODELVIEW);
-        glLoadIdentity();
-        glTranslatef(0.0F, 0.0F, -2000F);
+        GL41.glClear(GL41.GL_DEPTH_BUFFER_BIT);
+        this.mc.getGuiProjectionMatrix(GLRenderer.projectionM4f());
+        this.mc.getGuiViewMatrix(GLRenderer.viewM4f());
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/color/BlockColorDefault.java b/game/client/src/main/java/net/minecraft/client/render/block/color/BlockColorDefault.java
index 8186f835c..ca0b6cead 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/color/BlockColorDefault.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/color/BlockColorDefault.java
@@ -10,12 +10,12 @@ public class BlockColorDefault
     @Override
     public int getFallbackColor(int meta, int tintIndex)
     {
-        return 0xFFFFFF;
+        return 0xFFFFFFFF;
     }
 
     @Override
     public int getWorldColor(@NotNull WorldSource source, @NotNull TilePosc tilePos, int tintIndex)
     {
-        return 0xFFFFFF;
+        return 0xFFFFFFFF;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModel.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModel.java
index b9043ea79..8118e1a60 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModel.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModel.java
@@ -1,8 +1,9 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
@@ -22,11 +23,11 @@ public abstract class BlockModel<T extends BlockLogic>
     public BlockModel(final Block<T> block){
         this.block = block;
     }
-    public abstract boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos);
-    public abstract boolean renderOverbright(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos);
-    public abstract boolean renderNoCulling(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos);
-    public abstract boolean renderWithOverrideTexture(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos, IconCoordinate textureIndex);
-    public abstract void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate);
+    public abstract boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos);
+    public abstract boolean renderOverbright(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos);
+    public abstract boolean renderNoCulling(@NotNull TessellatorGeneral tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos);
+    public abstract boolean renderWithOverrideTexture(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos, IconCoordinate textureIndex);
+    public abstract void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord);
 
     public abstract boolean shouldItemRender3d();
     public abstract @NotNull DisplayPos getItemDisplayPos(@NotNull String id);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelAlgae.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelAlgae.java
index 4ae60d49b..927065ffe 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelAlgae.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelAlgae.java
@@ -1,9 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
@@ -18,21 +17,16 @@ public class BlockModelAlgae<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         AABBdc bounds = this.block.getBoundsFromState(worldSource, tilePos);
-        float brightness = 1.0f;
-        if (!LightmapHelper.isLightmapEnabled()) {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        } else {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        }
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
 
         int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getWorldColor(worldSource, tilePos, 0);
         float red = (float) (color >> 16 & 0xff) / 255F;
         float green = (float) (color >> 8 & 0xff) / 255F;
         float blue = (float) (color & 0xff) / 255F;
 
-        tessellator.setColorOpaque_F(red * brightness, green * brightness, blue * brightness);
+        tessellator.setColorOpaque3f(red, green, blue);
         IconCoordinate tex = getBlockTextureFromSideAndMetadata(Side.TOP, worldSource.getBlockData(tilePos));
         renderBlocks.renderTopFace(tessellator, bounds, tilePos.x(), tilePos.y() - 0.1125, tilePos.z(), tex);
         renderBlocks.renderBottomFace(tessellator, bounds, tilePos.x(), tilePos.y() + 0.0125, tilePos.z(), tex);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelAxisAligned.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelAxisAligned.java
index 2efffecb6..0bd3af191 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelAxisAligned.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelAxisAligned.java
@@ -1,8 +1,8 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicAxisAligned;
@@ -20,7 +20,7 @@ public class BlockModelAxisAligned<T extends BlockLogic> extends BlockModelStand
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int meta = worldSource.getBlockData(tilePos);
         Axis axis = BlockLogicAxisAligned.metaToAxis(meta);
         switch (axis) {
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBasket.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBasket.java
index fabeaf9fa..455c2be57 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBasket.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBasket.java
@@ -1,8 +1,8 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicBasket;
 import net.minecraft.core.util.helper.Side;
@@ -19,7 +19,7 @@ public class BlockModelBasket<T extends BlockLogicBasket> extends BlockModelStan
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         AABBd bounds = new AABBd(this.block.getBounds());
         // Render basket
         final float onePix = 1.0f / 16;
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBed.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBed.java
index a3d4b4b01..2e37212dc 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBed.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBed.java
@@ -1,8 +1,8 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicBed;
@@ -29,7 +29,7 @@ public class BlockModelBed<T extends BlockLogic> extends BlockModelStandard<T> {
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         TilePos queryPos = new TilePos();
         AABBd bounds = new AABBd(this.block.getBoundsFromState(worldSource, tilePos));
         renderBlocks.enableAO = true;
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBrazier.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBrazier.java
index 5130dd287..b6a23d24e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBrazier.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelBrazier.java
@@ -1,8 +1,9 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicBrazier;
 import net.minecraft.core.block.Blocks;
@@ -11,10 +12,8 @@ import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePos;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelBrazier<T extends BlockLogicBrazier>
     extends BlockModelStandard<T> {
@@ -27,9 +26,9 @@ public class BlockModelBrazier<T extends BlockLogicBrazier>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         TilePos queryPos = new TilePos();
-        tessellator.setColorOpaque_I(0xFFFFFF);
+        tessellator.setColorOpaque1i(0xFFFFFF);
 
         renderBlocks.enableAO = true;
         renderBlocks.cache.setupCache(this.block, worldSource, tilePos);
@@ -57,63 +56,42 @@ public class BlockModelBrazier<T extends BlockLogicBrazier>
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
         AABBdc bounds = this.block.getBounds();
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
-
-        GL11.glColor4f(brightness, brightness, brightness, alpha);
 
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, -1F, 0.0F);
         renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.baseTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
         renderBlocks.renderTopFace(tessellator, bounds, 0.0D, -1.0D, 0.0D, this.baseTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, -1F);
         renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.sideTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, -1F);
         renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 1.0D, this.sideTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
         renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.sideTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
         renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, -1.0D, this.sideTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(-1F, 0.0F, 0.0F);
         renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.sideTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(-1F, 0.0F, 0.0F);
         renderBlocks.renderWestFace(tessellator, bounds, 1.0D, 0.0D, 0.0D, this.sideTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.sideTexture);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, -1.0D, 0.0D, 0.0D, this.sideTexture);
         tessellator.draw();
-
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCactus.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCactus.java
index 2bb322c01..cfeb4ec06 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCactus.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCactus.java
@@ -1,17 +1,15 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.block.color.BlockColorDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelCactus<T extends BlockLogic> extends BlockModelStandard<T> {
     public BlockModelCactus(Block<T> block) {
@@ -19,7 +17,7 @@ public class BlockModelCactus<T extends BlockLogic> extends BlockModelStandard<T
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         final float sidesOffset = 0.0625F;
 
         AABBd bounds = new AABBd(this.block.getBounds());
@@ -39,58 +37,40 @@ public class BlockModelCactus<T extends BlockLogic> extends BlockModelStandard<T
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (renderBlocks.useInventoryTint) {
-            int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            float r = (float) (color >> 16 & 0xff) / 255F;
-            float g = (float) (color >> 8 & 0xff) / 255F;
-            float b = (float) (color & 0xff) / 255F;
-            GL11.glColor4f(r * brightness, g * brightness, b * brightness, alpha);
-        }
-
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
         AABBdc bounds = getBlockBoundsForItemRender();
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
-
         final float sidesOffset = 0.0625F;
 
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
+        tessellator.setColor1i(getStandaloneTintColor(metadata));
         tessellator.setNormal(0.0F, -1F, 0.0F);
         renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.BOTTOM, metadata));
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
         renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.TOP, metadata));
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, -1F);
         tessellator.offsetTranslation(0.0F, 0.0F, sidesOffset);
         renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.NORTH, metadata));
         tessellator.offsetTranslation(0.0F, 0.0F, -sidesOffset);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
         tessellator.offsetTranslation(0.0F, 0.0F, -sidesOffset);
         renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.SOUTH, metadata));
         tessellator.offsetTranslation(0.0F, 0.0F, sidesOffset);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(-1F, 0.0F, 0.0F);
         tessellator.offsetTranslation(sidesOffset, 0.0F, 0.0F);
         renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.WEST, metadata));
         tessellator.offsetTranslation(-sidesOffset, 0.0F, 0.0F);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         tessellator.offsetTranslation(-sidesOffset, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.EAST, metadata));
         tessellator.offsetTranslation(sidesOffset, 0.0F, 0.0F);
         tessellator.draw();
 
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCandle.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCandle.java
index f390ed53b..973e02383 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCandle.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCandle.java
@@ -1,7 +1,7 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
@@ -15,7 +15,7 @@ public class BlockModelCandle<T extends BlockLogic> extends BlockModelStandard<T
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         boolean isLit = (worldSource.getBlockData(tilePos) & 0b00000001) == 0;
         float brightness = isLit ? 1.0f : renderBlocks.getBlockBrightness(worldSource, tilePos);
 
@@ -59,7 +59,7 @@ public class BlockModelCandle<T extends BlockLogic> extends BlockModelStandard<T
         double wickMaxV = texIndex.getSubIconV(onePix * 6);
 
 
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
 
         // Render sides
         tessellator.addVertexWithUV(maxX, minY, minZ, sideMinU, sideMaxV);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelChest.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelChest.java
index 0dcb496d4..d1f4a7069 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelChest.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelChest.java
@@ -1,6 +1,6 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.*;
@@ -46,7 +46,7 @@ public class BlockModelChest<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int meta = worldSource.getBlockData(tilePos);
         final Direction dir = BlockLogicChest.getDirectionFromMeta(meta);
         switch (dir) {
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCropsPumpkin.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCropsPumpkin.java
index a7889c1d1..037ddb1c4 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCropsPumpkin.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCropsPumpkin.java
@@ -1,9 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
@@ -33,14 +32,10 @@ public class BlockModelCropsPumpkin<T extends BlockLogic> extends BlockModelStan
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
 
         final int meta = worldSource.getBlockData(tilePos);
         IconCoordinate leafTexture = LEAF_TEXTURE;
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCropsWheat.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCropsWheat.java
index f55d93447..6d74c9318 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCropsWheat.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCropsWheat.java
@@ -1,9 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicCropsWheat;
@@ -32,14 +31,10 @@ public class BlockModelCropsWheat<T extends BlockLogic> extends BlockModelStanda
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
 
         IconCoordinate texture = getBlockTextureFromSideAndMetadata(Side.BOTTOM, worldSource.getBlockData(tilePos));
         if (renderBlocks.overrideBlockTexture != null) {
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCrossedSquares.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCrossedSquares.java
index 25f506ac0..7b185aa07 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCrossedSquares.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCrossedSquares.java
@@ -1,9 +1,9 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.Blocks;
@@ -11,8 +11,6 @@ import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelCrossedSquares<T extends BlockLogic> extends BlockModelStandard<T> {
     public BlockModelCrossedSquares(Block<T> block) {
@@ -20,25 +18,10 @@ public class BlockModelCrossedSquares<T extends BlockLogic> extends BlockModelSt
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (LightmapHelper.isLightmapEnabled()) {
-            brightness = 1f;
-        }
-        float r = 1f;
-        float g = 1f;
-        float b = 1f;
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
         // Used for the rendering for the block inside the jar
-        GL11.glColor4f(1f, 1f, 1f, 1f);
-        if (renderBlocks.useInventoryTint) {
-            int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            r = (float) (color >> 16 & 0xff) / 255F;
-            g = (float) (color >> 8 & 0xff) / 255F;
-            b = (float) (color & 0xff) / 255F;
-        }
         final float yOffset = 0.0F;
 
-        GL11.glTranslatef(-0.5F, -0.5f, -0.5F);
-
         IconCoordinate texIndex = getBlockTextureFromSideAndMetadata(Side.BOTTOM, metadata);
         if (renderBlocks.overrideBlockTexture != null) {
             texIndex = renderBlocks.overrideBlockTexture;
@@ -48,11 +31,10 @@ public class BlockModelCrossedSquares<T extends BlockLogic> extends BlockModelSt
         final double minV = texIndex.getIconVMin();
         final double maxV = texIndex.getIconVMax();
 
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_F(r * brightness, g * brightness, b * brightness, alpha);
-        if (LightmapHelper.isLightmapEnabled() && lightmapCoordinate != null) {
-            tessellator.setLightmapCoord(lightmapCoordinate);
-        }
+        tessellator.setColor1i(getStandaloneTintColor(metadata));
+        tessellator.setLightmapCoord1i(lightmapCoord);
 
         double xd = 0;
         double yd = 0;
@@ -82,23 +64,18 @@ public class BlockModelCrossedSquares<T extends BlockLogic> extends BlockModelSt
         tessellator.addVertexWithUV(minX, yd + 0.0D, maxZ, maxU, maxV);
         tessellator.addVertexWithUV(minX, yd + 1.0D + yOffset, maxZ, maxU, minV);
         tessellator.draw();
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
-        float brightness = 1.0f;
-        if (!LightmapHelper.isLightmapEnabled()) {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        } else {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        }
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
 
         int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getWorldColor(worldSource, tilePos, 0);
         float r = (float) (color >> 16 & 0xff) / 255F;
         float g = (float) (color >> 8 & 0xff) / 255F;
         float b = (float) (color & 0xff) / 255F;
-        tessellator.setColorOpaque_F(brightness * r, brightness * g, brightness * b);
+        tessellator.setColorOpaque3f(r, g, b);
 
         double xd = tilePos.x();
         double yd = tilePos.y();
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCrystallineNetherrack.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCrystallineNetherrack.java
index f25fd0de9..e6d315aaa 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCrystallineNetherrack.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelCrystallineNetherrack.java
@@ -1,7 +1,8 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.Block;
@@ -9,9 +10,7 @@ import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelCrystallineNetherrack<T extends BlockLogic> extends BlockModelStandard<T> {
     protected IconCoordinate overlay;
@@ -22,7 +21,7 @@ public class BlockModelCrystallineNetherrack<T extends BlockLogic> extends Block
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         AABBdc bounds = this.block.getBoundsFromState(worldSource, tilePos);
         renderBlocks.renderStandardBlock(tessellator, worldSource, this, bounds, tilePos, 1.0f, 1.0f, 1.0f);
         renderBlocks.overrideBlockTexture = this.overlay;
@@ -32,45 +31,35 @@ public class BlockModelCrystallineNetherrack<T extends BlockLogic> extends Block
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
         renderBlocks.useInventoryTint = false;
-        super.renderStandalone(tessellator, metadata, brightness, alpha, lightmapCoordinate);
+        super.renderStandalone(tessellator, metadata, lightmapCoord);
         renderBlocks.useInventoryTint = true;
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
-
-        int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-        float r = (float) (color >> 16 & 0xff) / 255F;
-        float g = (float) (color >> 8 & 0xff) / 255F;
-        float b = (float) (color & 0xff) / 255F;
-        GL11.glColor4f(r * brightness, g * brightness, b * brightness, alpha);
 
         AABBdc bounds = this.block.getBounds();
-        IconCoordinate coord = this.overlay;
+        IconCoordinate tex = this.overlay;
 
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
+        tessellator.setColor1i(BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0));
         tessellator.setNormal(0.0F, -1F, 0.0F);
-        renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, coord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+        renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, tex);
+
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
-        renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, coord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+        renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, tex);
+
         tessellator.setNormal(0.0F, 0.0F, -1F);
-        renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, coord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+        renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, tex);
+
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
-        renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, coord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+        renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, tex);
+
         tessellator.setNormal(-1F, 0.0F, 0.0F);
-        renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, coord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+        renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, tex);
+
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
-        renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, coord);
+        renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, tex);
         tessellator.draw();
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 }
\ No newline at end of file
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelDoor.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelDoor.java
index dade5a67e..0405aa8ff 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelDoor.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelDoor.java
@@ -1,8 +1,8 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicDoor;
 import net.minecraft.core.util.helper.Side;
@@ -17,22 +17,15 @@ public class BlockModelDoor<T extends BlockLogicDoor> extends BlockModelStandard
         super(block);
     }
 
-    public void setBrightness(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos, float sideBrightness) {
-        float brightness = sideBrightness;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness *= renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+    public void setBrightness(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos, float sideBrightness) {
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
+        tessellator.setColorOpaque3f(sideBrightness, sideBrightness, sideBrightness);
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(LightmapHelper.getLightmapCoord(15, 15));
-        }
-        tessellator.setColorOpaque_F(1.0f, 1.0f, 1.0f);
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+        tessellator.setLightmapCoord1i(LightmapHelper.getLightmapCoord(15, 15));
+        tessellator.setColorOpaque3f(1.0f, 1.0f, 1.0f);
 
         AABBdc bounds = this.block.getBoundsFromState(worldSource, tilePos);
         TilePos queryPos = new TilePos();
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelEmpty.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelEmpty.java
index 36d0d7d2b..a8264f99d 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelEmpty.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelEmpty.java
@@ -1,6 +1,7 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -16,12 +17,12 @@ public class BlockModelEmpty<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public boolean render(@NotNull final Tessellator tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(final @NotNull TessellatorTerrain tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
         return false;
     }
 
     @Override
-    public void renderStandalone(@NotNull final Tessellator tessellator, final int metadata, final float brightness, final float alpha, @Nullable final Integer lightmapCoordinate) {
+    public void renderStandalone(@NotNull final TessellatorGeneral tessellator, final int metadata, final int lightmapCoord) {
 
     }
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFence.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFence.java
index 8ffd6326b..27005cdf9 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFence.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFence.java
@@ -1,17 +1,15 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.block.color.BlockColorDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicFence;
 import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 
 public class BlockModelFence<T extends BlockLogicFence> extends BlockModelStandard<T> {
@@ -26,7 +24,7 @@ public class BlockModelFence<T extends BlockLogicFence> extends BlockModelStanda
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         final float f = 0.375F;
         final float f1 = 0.625F;
         AABBd bounds = new AABBd(f, 0.0F, f, f1, 1.0F, f1);
@@ -77,15 +75,10 @@ public class BlockModelFence<T extends BlockLogicFence> extends BlockModelStanda
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (renderBlocks.useInventoryTint) {
-            int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            float r = (float) (color >> 16 & 0xff) / 255F;
-            float g = (float) (color >> 8 & 0xff) / 255F;
-            float b = (float) (color & 0xff) / 255F;
-            GL11.glColor4f(r * brightness, g * brightness, b * brightness, alpha);
-        }
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
+        tessellator.startDrawingQuads();
+        tessellator.setColor1i(getStandaloneTintColor(metadata));
         for (int cube = 0; cube < 4; cube++) {
 
             AABBdc bounds;
@@ -100,36 +93,26 @@ public class BlockModelFence<T extends BlockLogicFence> extends BlockModelStanda
                 default -> new AABBd(0.5F - f5, 0.5F - f5 * 3F, -f5 * 2.0F, 0.5F + f5, 0.5F - f5, 1.0F + f5 * 2.0F);
             };
 
-            tessellator.startDrawingQuads();
+
             tessellator.setNormal(0.0F, -1F, 0.0F);
             renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.BOTTOM, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 1.0F, 0.0F);
             renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.TOP, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, -1F);
             renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.NORTH, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, 1.0F);
             renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.SOUTH, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(-1F, 0.0F, 0.0F);
             renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.WEST, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(1.0F, 0.0F, 0.0F);
             renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.EAST, metadata));
-            tessellator.draw();
         }
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.draw();
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFenceGate.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFenceGate.java
index 6d9e951f4..0db20ff71 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFenceGate.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFenceGate.java
@@ -1,16 +1,14 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.block.color.BlockColorDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicFenceGate;
 import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBd;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 
 public class BlockModelFenceGate<T extends BlockLogicFenceGate> extends BlockModelStandard<T> {
@@ -25,7 +23,7 @@ public class BlockModelFenceGate<T extends BlockLogicFenceGate> extends BlockMod
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         AABBd bounds = new AABBd(this.block.getBounds());
         boolean flag = true;
         int meta = worldSource.getBlockData(tilePos);
@@ -159,58 +157,39 @@ public class BlockModelFenceGate<T extends BlockLogicFenceGate> extends BlockMod
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (renderBlocks.useInventoryTint) {
-            int j = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            float f1 = (float) (j >> 16 & 0xff) / 255F;
-            float f3 = (float) (j >> 8 & 0xff) / 255F;
-            float f5 = (float) (j & 0xff) / 255F;
-            GL11.glColor4f(f1 * brightness, f3 * brightness, f5 * brightness, alpha);
-        }
-        for (int k1 = 0; k1 < 3; k1++) {
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
+        tessellator.startDrawingQuads();
+        tessellator.setColor1i(getStandaloneTintColor(metadata));
+        for (int bar = 0; bar < 3; bar++) {
             float f6 = 0.0625F;
             AABBd bounds = new AABBd(this.block.getBounds());
-            if (k1 == 0) {
-                bounds.setMin(0.5F - f6, 0.3F, 0.0F).setMax(0.5F + f6, 1.0F, f6 * 2.0F);
-            }
-            if (k1 == 1) {
-                bounds.setMin(0.5F - f6, 0.3F, 1.0F - f6 * 2.0F).setMax(0.5F + f6, 1.0F, 1.0F);
+            switch (bar) {
+                case 0 -> bounds.setMin(0.5F - f6, 0.3F, 0.0F).setMax(0.5F + f6, 1.0F, f6 * 2.0F);
+                case 1 -> bounds.setMin(0.5F - f6, 0.3F, 1.0F - f6 * 2.0F).setMax(0.5F + f6, 1.0F, 1.0F);
+                default -> bounds.setMin(0.5F - f6, 0.5F, 0.0F).setMax(0.5F + f6, 1.0F - f6, 1.0F);
             }
-            if (k1 == 2) {
-                bounds.setMin(0.5F - f6, 0.5F, 0.0F).setMax(0.5F + f6, 1.0F - f6, 1.0F);
-            }
-            GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
-            tessellator.startDrawingQuads();
+
             tessellator.setNormal(0.0F, -1F, 0.0F);
             renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.BOTTOM, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 1.0F, 0.0F);
             renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.TOP, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, -1F);
             renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.NORTH, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, 1.0F);
             renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.SOUTH, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(-1F, 0.0F, 0.0F);
             renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.WEST, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(1.0F, 0.0F, 0.0F);
             renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.EAST, metadata));
-            tessellator.draw();
-            GL11.glTranslatef(0.5F, 0.5F, 0.5F);
         }
+        tessellator.draw();
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFenceThin.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFenceThin.java
index d1647fb68..2f1010beb 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFenceThin.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFenceThin.java
@@ -1,9 +1,10 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.block.color.BlockColorDispatcher;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicFenceThin;
 import net.minecraft.core.util.helper.Side;
@@ -12,8 +13,8 @@ import net.minecraft.core.world.pos.TilePos;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
+import org.joml.Math;
 import org.joml.primitives.AABBd;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 
 public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockModelStandard<T> {
@@ -34,14 +35,10 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
     }
 
     @Override
-    public boolean render(@NotNull Tessellator t, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain t, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            t.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
-        t.setColorOpaque_F(brightness, brightness, brightness);
+        t.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
+        t.setColorOpaque3f(brightness, brightness, brightness);
 
         TilePos queryPos = new TilePos();
 
@@ -121,7 +118,7 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
             float maxZ = tilePos.z() + ((16 / 2f) + (2 / 2f)) / 16f;
 
             // Render sides
-            t.setColorOpaque_F(cNorthSouth * brightness, cNorthSouth * brightness, cNorthSouth * brightness);
+            t.setColorOpaque3f(cNorthSouth * brightness, cNorthSouth * brightness, cNorthSouth * brightness);
             t.addVertexWithUV(maxX, minY, minZ, sidesMinU, sidesMaxV);
             t.addVertexWithUV(minX, minY, minZ, sidesMaxU, sidesMaxV);
             t.addVertexWithUV(minX, maxY, minZ, sidesMaxU, sidesMinV);
@@ -132,7 +129,7 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
             t.addVertexWithUV(maxX, maxY, maxZ, sidesMaxU, sidesMinV);
             t.addVertexWithUV(minX, maxY, maxZ, sidesMinU, sidesMinV);
 
-            t.setColorOpaque_F(cEastWest * brightness, cEastWest * brightness, cEastWest * brightness);
+            t.setColorOpaque3f(cEastWest * brightness, cEastWest * brightness, cEastWest * brightness);
             t.addVertexWithUV(maxX, minY, maxZ, sidesMinU, sidesMaxV);
             t.addVertexWithUV(maxX, minY, minZ, sidesMaxU, sidesMaxV);
             t.addVertexWithUV(maxX, maxY, minZ, sidesMaxU, sidesMinV);
@@ -149,14 +146,14 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
             double topBottomMaxV = this.columnTexIndex.getSubIconV(onePix * 2);
 
             // Render top
-            t.setColorOpaque_F(cTop * brightness, cTop * brightness, cTop * brightness);
+            t.setColorOpaque3f(cTop * brightness, cTop * brightness, cTop * brightness);
             t.addVertexWithUV(minX, maxY, maxZ, topBottomMinU, topBottomMaxV);
             t.addVertexWithUV(maxX, maxY, maxZ, topBottomMaxU, topBottomMaxV);
             t.addVertexWithUV(maxX, maxY, minZ, topBottomMaxU, topBottomMinV);
             t.addVertexWithUV(minX, maxY, minZ, topBottomMinU, topBottomMinV);
 
             // Render bottom
-            t.setColorOpaque_F(cBottom * brightness, cBottom * brightness, cBottom * brightness);
+            t.setColorOpaque3f(cBottom * brightness, cBottom * brightness, cBottom * brightness);
             t.addVertexWithUV(minX, minY, minZ, topBottomMinU, topBottomMinV);
             t.addVertexWithUV(maxX, minY, minZ, topBottomMaxU, topBottomMinV);
             t.addVertexWithUV(maxX, minY, maxZ, topBottomMaxU, topBottomMaxV);
@@ -193,7 +190,7 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
             float maxY = tilePos.y() + 1.0f;
             float maxZ = tilePos.z() + (8f / 16f);
 
-            t.setColorOpaque_F(cEastWest * brightness, cEastWest * brightness, cEastWest * brightness);
+            t.setColorOpaque3f(cEastWest * brightness, cEastWest * brightness, cEastWest * brightness);
             t.addVertexWithUV(maxX, minY, maxZ, sidesMinU, sidesMaxV);
             t.addVertexWithUV(maxX, minY, minZ, sidesMaxU, sidesMaxV);
             t.addVertexWithUV(maxX, maxY, minZ, sidesMaxU, sidesMinV);
@@ -235,7 +232,7 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
             float maxY = tilePos.y() + 1.0f;
             float maxZ = tilePos.z() + 1.0f;
 
-            t.setColorOpaque_F(cEastWest * brightness, cEastWest * brightness, cEastWest * brightness);
+            t.setColorOpaque3f(cEastWest * brightness, cEastWest * brightness, cEastWest * brightness);
             t.addVertexWithUV(maxX, minY, maxZ, sidesMinU, sidesMaxV);
             t.addVertexWithUV(maxX, minY, minZ, sidesMaxU, sidesMaxV);
             t.addVertexWithUV(maxX, maxY, minZ, sidesMaxU, sidesMinV);
@@ -277,7 +274,7 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
             float maxY = tilePos.y() + 1.0f;
             float maxZ = tilePos.z() + (8f / 16f);
 
-            t.setColorOpaque_F(cNorthSouth * brightness, cNorthSouth * brightness, cNorthSouth * brightness);
+            t.setColorOpaque3f(cNorthSouth * brightness, cNorthSouth * brightness, cNorthSouth * brightness);
             t.addVertexWithUV(maxX, minY, minZ, sidesMinU, sidesMaxV);
             t.addVertexWithUV(minX, minY, minZ, sidesMaxU, sidesMaxV);
             t.addVertexWithUV(minX, maxY, minZ, sidesMaxU, sidesMinV);
@@ -319,7 +316,7 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
             float maxY = tilePos.y() + 1.0f;
             float maxZ = tilePos.z() + (8f / 16f);
 
-            t.setColorOpaque_F(cNorthSouth * brightness, cNorthSouth * brightness, cNorthSouth * brightness);
+            t.setColorOpaque3f(cNorthSouth * brightness, cNorthSouth * brightness, cNorthSouth * brightness);
             t.addVertexWithUV(maxX, minY, minZ, sidesMinU, sidesMaxV);
             t.addVertexWithUV(minX, minY, minZ, sidesMaxU, sidesMaxV);
             t.addVertexWithUV(minX, maxY, minZ, sidesMaxU, sidesMinV);
@@ -335,64 +332,49 @@ public class BlockModelFenceThin<T extends BlockLogicFenceThin> extends BlockMod
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (renderBlocks.useInventoryTint) {
-            int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            float r = (float) (color >> 16 & 0xff) / 255F;
-            float g = (float) (color >> 8 & 0xff) / 255F;
-            float b = (float) (color & 0xff) / 255F;
-            GL11.glColor4f(r * brightness, g * brightness, b * brightness, alpha);
-        }
-        GL11.glRotatef(90, 0, 1, 0);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        int color = getStandaloneTintColor(metadata);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(90));
         AABBd bounds = new AABBd(0, 0, 0, 1, 1, 1);
         for (int i1 = 0; i1 < 2; i1++) {
-            GL11.glPushMatrix();
+            GLRenderer.pushFrame();
             float f4 = 0.125F / 2;
             bounds.setMin(0, 0.0F, 0.0F).setMax(2 * f4, 1.0F, f4 * 2.0F);
-            GL11.glTranslatef(0.5f - f4, 0, 0);
+            GLRenderer.modelM4f().translate(0.5f - f4, 0, 0);
             if (i1 == 1) {
-                GL11.glTranslatef(0, 0, 1f - (f4 * 2));
+                GLRenderer.modelM4f().translate(0, 0, 1f - (f4 * 2));
             }
-            GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
+            GLRenderer.modelM4f().translate(-0.5F, -0.5F, -0.5F);
             tessellator.startDrawingQuads();
+            tessellator.setColor1i(color);
             tessellator.setNormal(0.0F, -1F, 0.0F);
             renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.columnTexIndex);
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 1.0F, 0.0F);
             renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.columnTexIndex);
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, -1F);
             renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.columnTexIndex);
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, 1.0F);
             renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.columnTexIndex);
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(-1F, 0.0F, 0.0F);
             renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.columnTexIndex);
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(1.0F, 0.0F, 0.0F);
             renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, this.columnTexIndex);
             tessellator.draw();
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         }
 
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
-        GL11.glDisable(GL11.GL_CULL_FACE);
+        GLRenderer.modelM4f().translate(-0.5F, -0.5F, -0.5F);
+        GLRenderer.disableState(State.CULL_FACE);
         bounds.setMin(0, 0, 0).setMax(0.5f, 1, 1);
         tessellator.startDrawingQuads();
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, 0, 0, 0, this.texIndex);
         tessellator.draw();
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        GLRenderer.modelM4f().translate(0.5F, 0.5F, 0.5F);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFire.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFire.java
index cd535bb6d..058d5f2b3 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFire.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFire.java
@@ -1,8 +1,8 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.client.world.WorldClient;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -27,18 +27,12 @@ public class BlockModelFire<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         IconCoordinate tex = getBlockTextureFromSideAndMetadata(Side.BOTTOM, worldSource.getBlockData(tilePos));
         if (renderBlocks.overrideBlockTexture != null) {
             tex = renderBlocks.overrideBlockTexture;
         }
-        float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(LightmapHelper.getOverbrightLightmapCoord(worldSource.getSavedLightValue(LightLayer.Sky, tilePos)));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(LightmapHelper.getOverbrightLightmapCoord(worldSource.getSavedLightValue(LightLayer.Sky, tilePos)));
         double uMin = tex.getIconUMin();
         double uMax = tex.getIconUMax();
         double vMin = tex.getIconVMin();
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFluid.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFluid.java
index 6c6ebda32..ecd4a7058 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFluid.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFluid.java
@@ -2,8 +2,8 @@ package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicFluid;
 import net.minecraft.core.block.material.Material;
@@ -22,7 +22,7 @@ public class BlockModelFluid<T extends BlockLogicFluid> extends BlockModelStanda
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getWorldColor(worldSource, tilePos, 0);
         float r = (float) (color >> 16 & 0xff) / 255F;
         float g = (float) (color >> 8 & 0xff) / 255F;
@@ -69,14 +69,10 @@ public class BlockModelFluid<T extends BlockLogicFluid> extends BlockModelStanda
                 rotation = 0.0F;
             }
             float blockBrightness = 1.0f;
-            if (LightmapHelper.isLightmapEnabled()) {
-                int light = this.block.getLightmapCoord(worldSource, tilePos);
-                int lightUp = this.block.getLightmapCoord(worldSource, tilePos.up(queryPos));
+            int light = this.block.getLightmapCoord(worldSource, tilePos);
+            int lightUp = this.block.getLightmapCoord(worldSource, tilePos.up(queryPos));
 
-                tessellator.setLightmapCoord(LightmapHelper.max(light, lightUp));
-            } else {
-                blockBrightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-            }
+            tessellator.setLightmapCoord1i(LightmapHelper.max(light, lightUp));
             if (texture.namespaceId.toString().contains("_flowing")) {
                 double centerU = texture.getSubIconU(0.5);
                 double centerV = texture.getSubIconV(0.5);
@@ -88,13 +84,13 @@ public class BlockModelFluid<T extends BlockLogicFluid> extends BlockModelStanda
                 double minV = texture.getIconVMin();
                 double maxV = texture.getIconVMax();
 
-                tessellator.setColorOpaque_F(sideTop * blockBrightness * r, sideTop * blockBrightness * g, sideTop * blockBrightness * b);
+                tessellator.setColorOpaque3f(sideTop * blockBrightness * r, sideTop * blockBrightness * g, sideTop * blockBrightness * b);
                 tessellator.addVertexWithUV(x, (float) y + f7, z, ((minU - centerU) * sin - (maxV - centerV) * cSin) + centerU, ((maxV - centerV) * sin + (minU - centerU) * cSin) + centerV);
                 tessellator.addVertexWithUV(x, (float) y + f8, z + 1, ((maxU - centerU) * sin - (maxV - centerV) * cSin) + centerU, ((maxV - centerV) * sin + (maxU - centerU) * cSin) + centerV);
                 tessellator.addVertexWithUV(x + 1, (float) y + f9, z + 1, ((maxU - centerU) * sin - (minV - centerV) * cSin) + centerU, ((minV - centerV) * sin + (maxU - centerU) * cSin) + centerV);
                 tessellator.addVertexWithUV(x + 1, (float) y + f10, z, ((minU - centerU) * sin - (minV - centerV) * cSin) + centerU, ((minV - centerV) * sin + (minU - centerU) * cSin) + centerV);
             } else {
-                tessellator.setColorOpaque_F(sideTop * blockBrightness * r, sideTop * blockBrightness * g, sideTop * blockBrightness * b);
+                tessellator.setColorOpaque3f(sideTop * blockBrightness * r, sideTop * blockBrightness * g, sideTop * blockBrightness * b);
                 tessellator.addVertexWithUV(x, (float) y + f7, z, texture.getIconUMin(), texture.getIconVMax());
                 tessellator.addVertexWithUV(x, (float) y + f8, z + 1, texture.getIconUMax(), texture.getIconVMax());
                 tessellator.addVertexWithUV(x + 1, (float) y + f9, z + 1, texture.getIconUMax(), texture.getIconVMin());
@@ -104,12 +100,8 @@ public class BlockModelFluid<T extends BlockLogicFluid> extends BlockModelStanda
         }
         if (renderBlocks.renderAllFaces || flag1) {
             float brightness = 1.0f;
-            if (LightmapHelper.isLightmapEnabled()) {
-                tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos.down(queryPos)));
-            } else {
-                brightness = renderBlocks.getBlockBrightness(worldSource, tilePos.down(queryPos));
-            }
-            tessellator.setColorOpaque_F(sideBottom * brightness * r, sideBottom * brightness * g, sideBottom * brightness * b);
+            tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos.down(queryPos)));
+            tessellator.setColorOpaque3f(sideBottom * brightness * r, sideBottom * brightness * g, sideBottom * brightness * b);
 
             renderBlocks.renderBottomFace(tessellator, bounds, x, y + yOff, z, getBlockTextureFromSideAndMetadata(Side.TOP, 0));
             didRender = true;
@@ -176,17 +168,13 @@ public class BlockModelFluid<T extends BlockLogicFluid> extends BlockModelStanda
             double d7 = texture.getSubIconV(0.5F - f15 / 2 + vOff);
             double d8 = texture.getSubIconV(0.5F + vOff);
             float brightness = 1.0f;
-            if (LightmapHelper.isLightmapEnabled()) {
-                tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, posB));
-            } else {
-                brightness = renderBlocks.getBlockBrightness(worldSource, posB);
-            }
+            tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, posB));
             if (side < 2) {
                 brightness *= sideNorthSouth;
             } else {
                 brightness *= sideEastWest;
             }
-            tessellator.setColorOpaque_F(sideTop * brightness * r, sideTop * brightness * g, sideTop * brightness * b);
+            tessellator.setColorOpaque3f(sideTop * brightness * r, sideTop * brightness * g, sideTop * brightness * b);
             tessellator.addVertexWithUV(f17, (float) y + f13, f19, d4, d6);
             tessellator.addVertexWithUV(f20, (float) y + f15, f21, d5, d7);
             tessellator.addVertexWithUV(f20, y, f21, d5, d8);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFullyRotatable.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFullyRotatable.java
index c7dc78262..03e3e9ba9 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFullyRotatable.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelFullyRotatable.java
@@ -1,6 +1,7 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -18,7 +19,7 @@ public class BlockModelFullyRotatable<T extends BlockLogic> extends BlockModelSt
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         final int meta = worldSource.getBlockData(tilePos);
         final Direction dir = BlockLogicFullyRotatable.metaToDirection(meta);
 
@@ -64,8 +65,8 @@ public class BlockModelFullyRotatable<T extends BlockLogic> extends BlockModelSt
 
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        super.renderStandalone(tessellator, 1, brightness, alpha, lightmapCoordinate);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        super.renderStandalone(tessellator, 1, lightmapCoord);
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelGeneric.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelGeneric.java
index 23dbdad33..ec63ebae1 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelGeneric.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelGeneric.java
@@ -1,7 +1,8 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -28,7 +29,7 @@ public class BlockModelGeneric<T extends BlockLogic> extends BlockModel<T> {
     }
 
     @Override
-    public boolean renderNoCulling(@NotNull final Tessellator tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean renderNoCulling(@NotNull final TessellatorGeneral tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
         return this.staticModel.renderAttached(this,
             tessellator,
             worldSource,
@@ -39,7 +40,7 @@ public class BlockModelGeneric<T extends BlockLogic> extends BlockModel<T> {
     }
 
     @Override
-    public boolean render(@NotNull final Tessellator tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(final @NotNull TessellatorTerrain tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
         return this.staticModel.renderAttached(this,
             tessellator,
             worldSource,
@@ -50,12 +51,12 @@ public class BlockModelGeneric<T extends BlockLogic> extends BlockModel<T> {
     }
 
     @Override
-    public boolean renderOverbright(@NotNull final Tessellator tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean renderOverbright(final @NotNull TessellatorTerrain tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
         throw new UnsupportedOperationException();
     }
 
     @Override
-    public boolean renderWithOverrideTexture(@NotNull final Tessellator tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos, final IconCoordinate textureIndex) {
+    public boolean renderWithOverrideTexture(final @NotNull TessellatorTerrain tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos, final IconCoordinate textureIndex) {
         return this.staticModel.renderAttached(this,
             tessellator,
             worldSource,
@@ -66,12 +67,11 @@ public class BlockModelGeneric<T extends BlockLogic> extends BlockModel<T> {
     }
 
     @Override
-    public void renderStandalone(@NotNull final Tessellator tessellator, final int metadata, final float brightness, final float alpha, @Nullable final Integer lightmapCoordinate) {
+    public void renderStandalone(@NotNull final TessellatorGeneral tessellator, final int metadata, final int lightmapCoord) {
         this.staticModel.renderStandalone(this,
             tessellator, 0, 0, 0,
             metadata,
-            BlockColorDispatcher.getInstance().getDispatch(this.block),
-            brightness, alpha);
+            BlockColorDispatcher.getInstance().getDispatch(this.block));
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelGrass.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelGrass.java
index 354264236..17dc9bef5 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelGrass.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelGrass.java
@@ -1,9 +1,10 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.block.color.BlockColorDispatcher;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.material.Material;
@@ -16,7 +17,6 @@ import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelGrass<T extends BlockLogic> extends BlockModelStandard<T> {
     public static boolean fancyGrass = false;
@@ -35,7 +35,7 @@ public class BlockModelGrass<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         AABBdc bounds = this.block.getBounds();
         boolean didRender = isRetro() ? renderBlocks.renderStandardBlock(tessellator, worldSource, this, bounds, tilePos, 1, 1, 1) : renderBlocks.renderStandardBlock(tessellator, worldSource, this, bounds, tilePos);
         if (fancyGrass && !(this.retroBlockTextures.hasTexture() && isRetro())) {
@@ -47,68 +47,49 @@ public class BlockModelGrass<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        GL11.glColor4f(brightness, brightness, brightness, alpha);
-        float yOffset = 0.5F;
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
 
         AABBdc bounds = getBlockBoundsForItemRender();
-        GL11.glTranslatef(-0.5F, 0.0F - yOffset, -0.5F);
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
+        tessellator.setColor1i(0xFFFFFFFF);
         tessellator.setNormal(0.0F, -1F, 0.0F);
         renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.BOTTOM, metadata));
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, -1F);
         renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.NORTH, metadata));
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
         renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.SOUTH, metadata));
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(-1F, 0.0F, 0.0F);
         renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.WEST, metadata));
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.EAST, metadata));
-        tessellator.draw();
-        if (renderBlocks.useInventoryTint && !isRetro()) {
-            int l = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            float f4 = (float) (l >> 16 & 0xff) / 255F;
-            float f8 = (float) (l >> 8 & 0xff) / 255F;
-            float f9 = (float) (l & 0xff) / 255F;
-            GL11.glColor4f(f4 * brightness, f8 * brightness, f9 * brightness, alpha);
-        }
-        tessellator.startDrawingQuads();
+        tessellator.setColor1i(getStandaloneTintColor(metadata));
+
+
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
         renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.TOP, metadata));
-        tessellator.draw();
         if (fancyGrass && !isRetro()) {
             useOverlay = true;
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, -1F);
             renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.NORTH, metadata));
-            tessellator.draw();
-            tessellator.startDrawingQuads();
+
             tessellator.setNormal(0.0F, 0.0F, 1.0F);
             renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.SOUTH, metadata));
-            tessellator.draw();
-            tessellator.startDrawingQuads();
+
             tessellator.setNormal(-1F, 0.0F, 0.0F);
             renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.WEST, metadata));
-            tessellator.draw();
-            tessellator.startDrawingQuads();
+
             tessellator.setNormal(1.0F, 0.0F, 0.0F);
             renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.EAST, metadata));
-            tessellator.draw();
             useOverlay = false;
         }
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.draw();
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelJar.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelJar.java
index 0dd084c01..f87cedec6 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelJar.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelJar.java
@@ -1,9 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
@@ -21,14 +20,10 @@ public class BlockModelJar<T extends BlockLogic> extends BlockModelStandard<T> {
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         // todo: yes, i know this is horrible.
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
         float yOffset = 0f;
         int meta = worldSource.getBlockData(tilePos);
 
@@ -71,7 +66,7 @@ public class BlockModelJar<T extends BlockLogic> extends BlockModelStandard<T> {
         double extTopMinV = texV;
         double extTopMaxV = texIndex.getSubIconV(onePix * 6);
 
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
 
         // Render sides int
         tessellator.addVertexWithUV(intMaxX, intMinY, intMaxZ, extSideMinU, extSideMaxV);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelJarButterfly.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelJarButterfly.java
index ba1badcef..ce96b1683 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelJarButterfly.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelJarButterfly.java
@@ -1,7 +1,6 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -18,18 +17,14 @@ public class BlockModelJarButterfly<T extends BlockLogic> extends BlockModelStan
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int meta = worldSource.getBlockData(tilePos);
         boolean isHanging = (meta & BlockLogicJarButterfly.MASK_HANGING) == 0;
         boolean isAngled = (meta & BlockLogicJarButterfly.MASK_ANGLED) != 0;
 
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
 
         float yOffset = isHanging ? 0f : 0.375f;
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLadder.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLadder.java
index afdd888df..92e56d6d3 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLadder.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLadder.java
@@ -1,10 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
-import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicLadder;
 import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.WorldSource;
@@ -17,19 +15,13 @@ public class BlockModelLadder<T extends BlockLogicLadder> extends BlockModelStan
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int data = worldSource.getBlockData(tilePos);
         IconCoordinate tex = getBlockTextureFromSideAndMetadata(Side.BOTTOM, data);
         if (renderBlocks.overrideBlockTexture != null) {
             tex = renderBlocks.overrideBlockTexture;
         }
-        float brightness = 1.0f;
-        if (!LightmapHelper.isLightmapEnabled()) {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        } else {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
         double uMin = tex.getIconUMin();
         double uMax = tex.getIconUMax();
         double vMin = tex.getIconVMin();
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLantern.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLantern.java
index 0c12ca9fe..1014e9247 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLantern.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLantern.java
@@ -1,8 +1,7 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicLanternFirefly;
@@ -17,18 +16,14 @@ public class BlockModelLantern<T extends BlockLogic> extends BlockModelStandard<
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int meta = worldSource.getBlockData(tilePos);
         boolean isHanging = (meta & BlockLogicLanternFirefly.MASK_HANGING) == 0;
 //        boolean isAngled = (meta & BlockLogicLanternFirefly.MASK_ANGLED) != 0;
 
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
 
         float yOffset = isHanging ? 0f : 0.375f;
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLayer.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLayer.java
index f414a1ad3..e0ba0e1f2 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLayer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLayer.java
@@ -1,15 +1,13 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePos;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelLayer<T extends BlockLogic> extends BlockModelStandard<T> {
     public BlockModelLayer(Block<T> block) {
@@ -18,9 +16,10 @@ public class BlockModelLayer<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        GL11.glTranslatef(0, 0.25f, 0);
-        super.renderStandalone(tessellator, metadata, brightness, alpha, lightmapCoordinate);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        tessellator.offsetTranslation(0, 0.25, 0);
+        super.renderStandalone(tessellator, metadata, lightmapCoord);
+        tessellator.offsetTranslation(0, -0.25, 0);
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeaves.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeaves.java
index 5c213027b..e7a332456 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeaves.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeaves.java
@@ -1,6 +1,7 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.Block;
@@ -36,15 +37,15 @@ public class BlockModelLeaves<T extends BlockLogic> extends BlockModelStandard<T
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
         boolean invTint = renderBlocks.useInventoryTint;
         renderBlocks.useInventoryTint = !this.canBeRetro || !isRetro();
-        super.renderStandalone(tessellator, metadata, brightness, alpha, lightmapCoordinate);
+        super.renderStandalone(tessellator, metadata, lightmapCoord);
         renderBlocks.useInventoryTint = invTint;
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         if (this.canBeRetro && isRetro()) {
             return renderBlocks.renderStandardBlock(tessellator, worldSource, this, this.block.getBoundsFromState(worldSource, tilePos), tilePos, 1, 1, 1);
         }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeavesCacao.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeavesCacao.java
index e2f5fd36b..1e57db3c8 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeavesCacao.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeavesCacao.java
@@ -1,18 +1,17 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicLeavesCacao;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelLeavesCacao<T extends BlockLogic> extends BlockModelLeaves<T> {
     protected IconCoordinate[] growthStages = new IconCoordinate[]{
@@ -27,34 +26,27 @@ public class BlockModelLeavesCacao<T extends BlockLogic> extends BlockModelLeave
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         super.render(tessellator, worldSource, tilePos);
 
         AABBdc bounds = this.block.getBounds();
 
         final int growthRate = BlockLogicLeavesCacao.getGrowthRate(worldSource.getBlockData(tilePos));
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            int lmc = this.block.getLightmapCoord(worldSource, tilePos);
-            if (this.block.emission > 0) {
-                lmc = LightmapHelper.setBlocklightValue(lmc, 15);
-            }
-            tessellator.setLightmapCoord(lmc);
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-            if (this.block.emission > 0) {
-                brightness = 1.0f;
-            }
+        int lmc = this.block.getLightmapCoord(worldSource, tilePos);
+        if (this.block.emission > 0) {
+            lmc = LightmapHelper.setBlocklightValue(lmc, 15);
         }
+        tessellator.setLightmapCoord1i(lmc);
 
         final float cNorthSouth = 0.8F;
         final float cEastWest = 0.6F;
         if (growthRate > 0) {
             renderBlocks.overrideBlockTexture = this.growthStages[Math.min(growthRate - 1, BlockLogicLeavesCacao.MAX_GROWTH_STATE - 1)];
-            tessellator.setColorOpaque_F(cNorthSouth * brightness, cNorthSouth * brightness, cNorthSouth * brightness);
+            tessellator.setColorOpaque3f(cNorthSouth * brightness, cNorthSouth * brightness, cNorthSouth * brightness);
             renderBlocks.renderNorthFace(tessellator, bounds, tilePos, renderBlocks.overrideBlockTexture);
             renderBlocks.renderSouthFace(tessellator, bounds, tilePos, renderBlocks.overrideBlockTexture);
-            tessellator.setColorOpaque_F(cEastWest * brightness, cEastWest * brightness, cEastWest * brightness);
+            tessellator.setColorOpaque3f(cEastWest * brightness, cEastWest * brightness, cEastWest * brightness);
             renderBlocks.renderEastFace(tessellator, bounds, tilePos, renderBlocks.overrideBlockTexture);
             renderBlocks.renderWestFace(tessellator, bounds, tilePos, renderBlocks.overrideBlockTexture);
             renderBlocks.overrideBlockTexture = null;
@@ -64,45 +56,32 @@ public class BlockModelLeavesCacao<T extends BlockLogic> extends BlockModelLeave
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        super.renderStandalone(tessellator, metadata, brightness, alpha, lightmapCoordinate);
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
-
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        super.renderStandalone(tessellator, metadata, lightmapCoord);
         AABBdc bounds = this.block.getBounds();
 
         final IconCoordinate cacaoCoord = this.growthStages[BlockLogicLeavesCacao.MAX_GROWTH_STATE - 1];
-        GL11.glColor4f(brightness, brightness, brightness, alpha);
 
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, -1F, 0.0F);
         renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cacaoCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
         renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cacaoCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, -1F);
         renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cacaoCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
         renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cacaoCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(-1F, 0.0F, 0.0F);
         renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cacaoCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cacaoCoord);
         tessellator.draw();
-
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeavesCherryFlowering.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeavesCherryFlowering.java
index 8b0bbdaa1..7b4914e2e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeavesCherryFlowering.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLeavesCherryFlowering.java
@@ -1,17 +1,16 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicLeavesCherryFlowering;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelLeavesCherryFlowering<T extends BlockLogic> extends BlockModelLeaves<T> {
     private final IconCoordinate grownCherryOverlay = TextureRegistry.getTexture("minecraft:block/leaves/cherry_overlay");
@@ -22,7 +21,7 @@ public class BlockModelLeavesCherryFlowering<T extends BlockLogic> extends Block
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         super.render(tessellator, worldSource, tilePos);
 
         int growthRate = BlockLogicLeavesCherryFlowering.getGrowthRate(worldSource.getBlockData(tilePos));
@@ -39,45 +38,32 @@ public class BlockModelLeavesCherryFlowering<T extends BlockLogic> extends Block
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        super.renderStandalone(tessellator, metadata, brightness, alpha, lightmapCoordinate);
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        super.renderStandalone(tessellator, metadata, lightmapCoord);
 
         AABBdc bounds = this.block.getBoundsRaw();
-
         IconCoordinate cherryCoord = this.grownCherryOverlay;
-        GL11.glColor4f(brightness, brightness, brightness, alpha);
 
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, -1F, 0.0F);
         renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cherryCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
         renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cherryCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, -1F);
         renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cherryCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
         renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cherryCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(-1F, 0.0F, 0.0F);
         renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cherryCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, cherryCoord);
         tessellator.draw();
-
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLever.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLever.java
index 1f38d5885..76ad9fb2b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLever.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelLever.java
@@ -1,8 +1,7 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -21,7 +20,7 @@ public class BlockModelLever<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int data = worldSource.getBlockData(tilePos);
         int rotation = data & BlockLogicLever.MASK_ROTATION;
         boolean powered = (data & BlockLogicLever.MASK_POWERED) != 0;
@@ -63,16 +62,7 @@ public class BlockModelLever<T extends BlockLogic> extends BlockModelStandard<T>
         if (!overrideTexture) {
             renderBlocks.overrideBlockTexture = null;
         }
-        float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            if (this.block.emission <= 0) {
-                brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-            }
-        }
-
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
         IconCoordinate texture = getBlockTextureFromSideAndMetadata(Side.BOTTOM, data);
         if (renderBlocks.overrideBlockTexture != null) {
             texture = renderBlocks.overrideBlockTexture;
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelOverlayLeaves.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelOverlayLeaves.java
index 476c3c5b5..22a18b83c 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelOverlayLeaves.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelOverlayLeaves.java
@@ -1,16 +1,15 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelOverlayLeaves<T extends BlockLogic> extends BlockModelLeaves<T> {
     protected final IconCoordinate overlayTexture;
@@ -21,7 +20,7 @@ public class BlockModelOverlayLeaves<T extends BlockLogic> extends BlockModelLea
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         super.render(tessellator, worldSource, tilePos);
 
         renderBlocks.overrideBlockTexture = this.overlayTexture;
@@ -32,45 +31,32 @@ public class BlockModelOverlayLeaves<T extends BlockLogic> extends BlockModelLea
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        super.renderStandalone(tessellator, metadata, brightness, alpha, lightmapCoordinate);
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        super.renderStandalone(tessellator, metadata, lightmapCoord);
 
         AABBdc bounds = this.block.getBounds();
-
         IconCoordinate overlayCoord = this.overlayTexture;
-        GL11.glColor4f(brightness, brightness, brightness, alpha);
 
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, -1F, 0.0F);
         renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, overlayCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
         renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, overlayCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, -1F);
         renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, overlayCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
         renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, overlayCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(-1F, 0.0F, 0.0F);
         renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, overlayCoord);
-        tessellator.draw();
 
-        tessellator.startDrawingQuads();
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, overlayCoord);
         tessellator.draw();
-
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPebbles.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPebbles.java
index 5b6112f5b..82ce50ce1 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPebbles.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPebbles.java
@@ -1,9 +1,9 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.MathHelper;
@@ -26,14 +26,8 @@ public class BlockModelPebbles<T extends BlockLogic> extends BlockModelStandard<
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
-        float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(LightmapHelper.max(this.block.getLightmapCoord(worldSource, tilePos), this.block.getLightmapCoord(worldSource, tilePos.down(new TilePos()))));
-        } else {
-            brightness = Math.max(renderBlocks.getBlockBrightness(worldSource, tilePos), renderBlocks.getBlockBrightness(worldSource, tilePos.down(new TilePos())));
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+        tessellator.setLightmapCoord1i(LightmapHelper.max(this.block.getLightmapCoord(worldSource, tilePos), this.block.getLightmapCoord(worldSource, tilePos.down(new TilePos()))));
         renderBlocks.renderTopFace(tessellator,
             this.block.getBoundsFromState(worldSource, tilePos),
             tilePos,
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPiePumpkin.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPiePumpkin.java
index ad075a78b..0da7f040e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPiePumpkin.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPiePumpkin.java
@@ -1,8 +1,9 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicEdible;
 import net.minecraft.core.util.helper.Side;
@@ -24,7 +25,7 @@ public class BlockModelPiePumpkin<T extends BlockLogicEdible> extends BlockModel
         withCustomItemBounds(f, 0.0F, f, 1.0F - f, f1, 1.0F - f);
     }
 
-    public void renderSliceSide(final @NotNull Tessellator tessellator, final @NotNull WorldSource worldSource, final @NotNull AABBdc bounds, @NotNull TilePosc tilePos, final @NotNull Side side, final boolean overrideTex) {
+    public void renderSliceSide(final @NotNull TessellatorTerrain tessellator, final @NotNull WorldSource worldSource, final @NotNull AABBdc bounds, @NotNull TilePosc tilePos, final @NotNull Side side, final boolean overrideTex) {
         if (overrideTex)
             renderBlocks.overrideBlockTexture = this.insideTexture;
         renderBlocks.renderSide(tessellator, worldSource, this, bounds, tilePos, 1, 1, 1, side, 0);
@@ -32,7 +33,7 @@ public class BlockModelPiePumpkin<T extends BlockLogicEdible> extends BlockModel
             renderBlocks.overrideBlockTexture = null;
     }
 
-    private void renderSlice(final @NotNull Tessellator tessellator, final @NotNull WorldSource worldSource, final @NotNull AABBdc bounds, @NotNull TilePosc tilePos, final int sliceX, final int sliceZ) {
+    private void renderSlice(final @NotNull TessellatorTerrain tessellator, final @NotNull WorldSource worldSource, final @NotNull AABBdc bounds, @NotNull TilePosc tilePos, final int sliceX, final int sliceZ) {
 
         final double onePix = 0.0625;
         final double sliceWidth = onePix * 8;
@@ -64,7 +65,7 @@ public class BlockModelPiePumpkin<T extends BlockLogicEdible> extends BlockModel
     }
 
     @Override
-    public boolean render(@NotNull final Tessellator tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(final @NotNull TessellatorTerrain tessellator, @NotNull final WorldSource worldSource, @NotNull TilePosc tilePos) {
         final AABBdc bounds = this.block.getBoundsFromState(worldSource, tilePos);
 
         final int meta = worldSource.getBlockData(tilePos);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPiston.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPiston.java
index 58838765d..a1ba8bb45 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPiston.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPiston.java
@@ -1,8 +1,9 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.piston.BlockLogicPistonBase;
 import net.minecraft.core.util.helper.Direction;
@@ -45,13 +46,13 @@ public class BlockModelPiston<T extends BlockLogicPistonBase> extends BlockModel
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         return renderPistonBase(tessellator, worldSource, tilePos, false);
     }
 
     private boolean headless = false;
 
-    public boolean renderHeadless(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePos tilePos) {
+    public boolean renderHeadless(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePos tilePos) {
         renderBlocks.renderAllFaces = true;
         this.headless = true;
         boolean result = renderPistonBase(tessellator, worldSource, tilePos, true);
@@ -60,7 +61,7 @@ public class BlockModelPiston<T extends BlockLogicPistonBase> extends BlockModel
         return result;
     }
 
-    protected boolean renderPistonBase(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos, boolean noCulling) {
+    protected boolean renderPistonBase(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos, boolean noCulling) {
         int meta = worldSource.getBlockData(tilePos);
         boolean extended = noCulling || (meta & 8) != 0;
         Direction direction = BlockLogicPistonBase.getDirection(meta);
@@ -156,8 +157,8 @@ public class BlockModelPiston<T extends BlockLogicPistonBase> extends BlockModel
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        super.renderStandalone(tessellator, 1, brightness, alpha, lightmapCoordinate);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        super.renderStandalone(tessellator, 1, lightmapCoord);
     }
 
     public @NotNull IconCoordinate getFaceTexture() {
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPistonHead.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPistonHead.java
index 29fa670d5..be358a7d8 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPistonHead.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPistonHead.java
@@ -1,9 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.block.piston.BlockLogicPistonHead;
@@ -41,11 +40,11 @@ public class BlockModelPistonHead extends BlockModelStandard<BlockLogicPistonHea
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         return renderPistonHead(tessellator, worldSource, this.block, tilePos, true);
     }
 
-    public void renderPistonHeadNoCulling(Tessellator tessellator, WorldSource worldSource, Block<BlockLogicPistonHead> block, @NotNull TilePos tilePos, boolean flag) {
+    public void renderPistonHeadNoCulling(TessellatorTerrain tessellator, WorldSource worldSource, Block<BlockLogicPistonHead> block, @NotNull TilePos tilePos, boolean flag) {
         renderBlocks.renderAllFaces = true;
         renderPistonHead(tessellator, worldSource, block, tilePos, flag);
         renderBlocks.renderAllFaces = false;
@@ -55,15 +54,11 @@ public class BlockModelPistonHead extends BlockModelStandard<BlockLogicPistonHea
         this.faceTextureOverride = faceTexture;
     }
 
-    protected boolean renderPistonHead(Tessellator tessellator, WorldSource worldSource, Block<BlockLogicPistonHead> block, @NotNull TilePosc tilePos, boolean flag) {
+    protected boolean renderPistonHead(TessellatorTerrain tessellator, WorldSource worldSource, Block<BlockLogicPistonHead> block, @NotNull TilePosc tilePos, boolean flag) {
         int metadata = worldSource.getBlockData(tilePos);
         Direction direction = BlockLogicPistonHead.getDirectionFromMeta(metadata);
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-        }
+        tessellator.setLightmapCoord1i(block.getLightmapCoord(worldSource, tilePos));
         final float f1 = flag ? 1.0F : 0.5F;
         final double width = flag ? 1 : 1 / 2d;
 
@@ -142,39 +137,39 @@ public class BlockModelPistonHead extends BlockModelStandard<BlockLogicPistonHea
         return true;
     }
 
-    private void renderHeadTopBottom(final Tessellator tessellator, final double xMin, final double xMax, final double yMin, final double yMax, final double zMin, final double zMax, final float brightness, final double width) {
+    private void renderHeadTopBottom(final TessellatorTerrain tessellator, final double xMin, final double xMax, final double yMin, final double yMax, final double zMin, final double zMax, final float brightness, final double width) {
         final IconCoordinate i = renderBlocks.overrideBlockTexture != null ? renderBlocks.overrideBlockTexture : this.pistonShaft;
         final double uMin = i.getSubIconU(0.5 - this.shaftThickness / 2);
         final double vMin = i.getIconVMin();
         final double uMax = i.getSubIconU(0.5 + this.shaftThickness / 2);
         final double vMax = i.getSubIconV(width);
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
         tessellator.addVertexWithUV(xMin, yMax, zMin, uMax, vMax);
         tessellator.addVertexWithUV(xMin, yMin, zMin, uMax, vMin);
         tessellator.addVertexWithUV(xMax, yMin, zMax, uMin, vMin);
         tessellator.addVertexWithUV(xMax, yMax, zMax, uMin, vMax);
     }
 
-    private void renderHeadNorthSouth(final Tessellator tessellator, final double xMin, final double xMax, final double yMin, final double yMax, final double zMin, final double zMax, final float brightness, final double width) {
+    private void renderHeadNorthSouth(final TessellatorTerrain tessellator, final double xMin, final double xMax, final double yMin, final double yMax, final double zMin, final double zMax, final float brightness, final double width) {
         final IconCoordinate i = renderBlocks.overrideBlockTexture != null ? renderBlocks.overrideBlockTexture : this.pistonShaft;
         final double uMin = i.getSubIconU(0.5 - this.shaftThickness / 2);
         final double vMin = i.getIconVMin();
         final double uMax = i.getSubIconU(0.5 + this.shaftThickness / 2);
         final double vMax = i.getSubIconV(width);
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
         tessellator.addVertexWithUV(xMin, yMin, zMax, uMax, vMax);
         tessellator.addVertexWithUV(xMin, yMin, zMin, uMax, vMin);
         tessellator.addVertexWithUV(xMax, yMax, zMin, uMin, vMin);
         tessellator.addVertexWithUV(xMax, yMax, zMax, uMin, vMax);
     }
 
-    private void renderHeadEastWest(final Tessellator tessellator, final double xMin, final double xMax, final double yMin, final double yMax, final double zMin, final double zMax, final float brightness, final double width) {
+    private void renderHeadEastWest(final TessellatorTerrain tessellator, final double xMin, final double xMax, final double yMin, final double yMax, final double zMin, final double zMax, final float brightness, final double width) {
         final IconCoordinate i = renderBlocks.overrideBlockTexture != null ? renderBlocks.overrideBlockTexture : this.pistonShaft;
         final double uMin = i.getSubIconU(0.5 - this.shaftThickness / 2);
         final double vMin = i.getIconVMin();
         final double uMax = i.getSubIconU(0.5 + this.shaftThickness / 2);
         final double vMax = i.getSubIconV(width);
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
         tessellator.addVertexWithUV(xMax, yMin, zMin, uMax, vMax);
         tessellator.addVertexWithUV(xMin, yMin, zMin, uMax, vMin);
         tessellator.addVertexWithUV(xMin, yMax, zMax, uMin, vMin);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPumice.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPumice.java
index 7edf9ef17..02c3dae91 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPumice.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelPumice.java
@@ -1,9 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.block.color.BlockColorDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.Block;
@@ -14,7 +13,6 @@ import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBd;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelPumice<T extends BlockLogic> extends BlockModelStandard<T> {
     private boolean lavaFlag = false;
@@ -24,7 +22,7 @@ public class BlockModelPumice<T extends BlockLogic> extends BlockModelStandard<T
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         this.lavaFlag = true;
         boolean ob = renderBlocks.overbright;
         renderBlocks.overbright = true;
@@ -39,36 +37,23 @@ public class BlockModelPumice<T extends BlockLogic> extends BlockModelStandard<T
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (renderBlocks.useInventoryTint) {
-            int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            float r = (float) (color >> 16 & 0xff) / 255F;
-            float g = (float) (color >> 8 & 0xff) / 255F;
-            float b = (float) (color & 0xff) / 255F;
-            GL11.glColor4f(r * brightness, g * brightness, b * brightness, alpha);
-        } else {
-            GL11.glColor4f(brightness, brightness, brightness, alpha);
-        }
-        float yOffset = 0.5F;
-
-        GL11.glTranslatef(-0.5F, 0.0F - yOffset, -0.5F);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
 
+        int color = getStandaloneTintColor(metadata);
         this.lavaFlag = true;
         boolean ob = renderBlocks.overbright;
         renderBlocks.overbright = true;
         final double depthFixOffset = 0.001d;
         AABBd bounds = new AABBd(depthFixOffset, depthFixOffset, depthFixOffset, 1 - depthFixOffset, 1 - depthFixOffset, 1 - depthFixOffset);
-        renderBlockWithBounds(tessellator, bounds, metadata, brightness, alpha, LightmapHelper.getLightmapCoord(15, 15));
+        renderBlockWithBounds(tessellator, bounds, metadata, LightmapHelper.getLightmapCoord(15, 15), color);
 
         renderBlocks.overbright = ob;
         this.lavaFlag = false;
-        if (LightmapHelper.isLightmapEnabled()) {
-            lightmapCoordinate = Minecraft.getMinecraft().thePlayer.getLightmap(1f);
-        }
         bounds.setMin(0, 0, 0).setMax(1, 1, 1);
-        renderBlockWithBounds(tessellator, bounds, metadata, brightness, alpha, lightmapCoordinate);
+        renderBlockWithBounds(tessellator, bounds, metadata, lightmapCoord, color);
 
-        GL11.glTranslatef(0.5F, yOffset, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRail.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRail.java
index 364a4033e..faf32094f 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRail.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRail.java
@@ -1,9 +1,9 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicRail;
 import net.minecraft.core.block.Blocks;
@@ -31,7 +31,7 @@ public class BlockModelRail<T extends BlockLogicRail> extends BlockModelStandard
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int meta = worldSource.getBlockData(tilePos);
         IconCoordinate icon = getBlockTextureFromSideAndMetadata(Side.BOTTOM, meta);
         if (renderBlocks.overrideBlockTexture != null) {
@@ -39,16 +39,10 @@ public class BlockModelRail<T extends BlockLogicRail> extends BlockModelStandard
         }
         RailDirection railDirection = this.block.getLogic().getRailDirection(worldSource, tilePos);
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            if (renderBlocks.overbright) {
-                tessellator.setLightmapCoord(LightmapHelper.getOverbrightLightmapCoord(worldSource.getSavedLightValue(LightLayer.Sky, tilePos)));
-            } else {
-                tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-            }
+        if (renderBlocks.overbright) {
+            tessellator.setLightmapCoord1i(LightmapHelper.getOverbrightLightmapCoord(worldSource.getSavedLightValue(LightLayer.Sky, tilePos)));
         } else {
-            if (!renderBlocks.overbright) {
-                brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-            }
+            tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
         }
         if (renderBlocks.overbright) {
             icon = getBlockOverbrightTexture(worldSource, tilePos, Side.BOTTOM);
@@ -57,7 +51,7 @@ public class BlockModelRail<T extends BlockLogicRail> extends BlockModelStandard
             return false;
         }
 
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
         final double minU = icon.getIconUMin();
         final double maxU = icon.getIconUMax();
         final double minV = icon.getIconVMin();
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRepeater.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRepeater.java
index db6a31ca3..8091cc88b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRepeater.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRepeater.java
@@ -1,8 +1,7 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.core.Global;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicRepeater;
 import net.minecraft.core.block.Blocks;
@@ -20,7 +19,7 @@ public class BlockModelRepeater extends BlockModelStandard<BlockLogicRepeater> {
         super(block);
     }
 
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int meta = worldSource.getBlockData(tilePos);
         int direction = meta & BlockLogicRepeater.MASK_DIRECTION;
 
@@ -46,19 +45,12 @@ public class BlockModelRepeater extends BlockModelStandard<BlockLogicRepeater> {
         renderBlocks.renderStandardBlock(tessellator, worldSource, this, this.block.getBoundsFromState(worldSource, tilePos), tilePos);
         renderBlocks.resetRenderBlocks();
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            int lmc = this.block.getLightmapCoord(worldSource, tilePos);
-            if (this.block.emission > 0) {
-                lmc = LightmapHelper.setBlocklightValue(lmc, 15);
-            }
-            tessellator.setLightmapCoord(lmc);
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-            if (this.block.emission > 0 || Global.accessor.isFullbrightEnabled()) {
-                brightness = 1.0f;
-            }
+        int lmc = this.block.getLightmapCoord(worldSource, tilePos);
+        if (this.block.emission > 0) {
+            lmc = LightmapHelper.setBlocklightValue(lmc, 15);
         }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(lmc);
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
         double d = -0.1875D;
         double d1 = 0.0D;
         double d2 = 0.0D;
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRope.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRope.java
index 4d5fea1bf..b81a888ad 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRope.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelRope.java
@@ -1,6 +1,6 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicJarButterfly;
 import net.minecraft.core.block.BlockLogicLanternFirefly;
@@ -20,7 +20,7 @@ public class BlockModelRope<T extends BlockLogicRope>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         Block<?> below = worldSource.getBlock(tilePos.down(new TilePos()));
         boolean hasFloor = below != null && below.canPlaceOnSurface();
         boolean hasBlockNegX = canConnect(worldSource, tilePos, Direction.WEST);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelSeat.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelSeat.java
index 7ecdf85a9..2b25f39d9 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelSeat.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelSeat.java
@@ -1,6 +1,6 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
@@ -15,7 +15,7 @@ public class BlockModelSeat<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         AABBd bounds = new AABBd(this.block.getBoundsFromState(worldSource, tilePos));
 
         renderBlocks.setRenderSide(Side.BOTTOM, false); // Set bottom face to not render
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelSpikes.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelSpikes.java
index 060ab63f3..d6dc143ed 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelSpikes.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelSpikes.java
@@ -1,8 +1,7 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicSpikes;
@@ -18,7 +17,7 @@ public class BlockModelSpikes<T extends BlockLogic> extends BlockModelStandard<T
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int metaData = worldSource.getBlockData(tilePos);
         IconCoordinate texture = getBlockTextureFromSideAndMetadata(Side.EAST, metaData);
         if (renderBlocks.overrideBlockTexture != null) {
@@ -28,13 +27,7 @@ public class BlockModelSpikes<T extends BlockLogic> extends BlockModelStandard<T
         renderBlocks.renderStandardBlock(tessellator, worldSource, this, new AABBd(0.0F, 0.0F, 0.0F, 1.0F, 0.1875F, 1.0F), tilePos);
 
         if (BlockLogicSpikes.isSpikesUp(metaData)) {
-            float brightness = 1.0f;
-            if (LightmapHelper.isLightmapEnabled()) {
-                tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-            } else {
-                brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-            }
-            tessellator.setColorOpaque_F(brightness, brightness, brightness);
+            tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
             double uMin = texture.getIconUMin();
             double uMax = texture.getIconUMax();
             double vMin = texture.getIconVMin();
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStairs.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStairs.java
index 4d04daa49..3716fbe19 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStairs.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStairs.java
@@ -1,8 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.block.color.BlockColorDispatcher;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicStairs;
 import net.minecraft.core.util.helper.Side;
@@ -12,7 +12,6 @@ import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 
 public class BlockModelStairs<T extends BlockLogicStairs> extends BlockModelStandard<T> {
@@ -35,7 +34,7 @@ public class BlockModelStairs<T extends BlockLogicStairs> extends BlockModelStan
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int meta = worldSource.getBlockData(tilePos);
         int hRotation = meta & 0b0011;
         int vRotation = meta & 0b1000;
@@ -69,14 +68,10 @@ public class BlockModelStairs<T extends BlockLogicStairs> extends BlockModelStan
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (renderBlocks.useInventoryTint) {
-            int j = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            float f1 = (float) (j >> 16 & 0xff) / 255F;
-            float f3 = (float) (j >> 8 & 0xff) / 255F;
-            float f5 = (float) (j & 0xff) / 255F;
-            GL11.glColor4f(f1 * brightness, f3 * brightness, f5 * brightness, alpha);
-        }
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
+        tessellator.startDrawingQuads();
+        tessellator.setColor1i(getStandaloneTintColor(metadata));
         for (int l = 0; l < 2; l++) {
             AABBdc bounds;
             if (l == 0) {
@@ -84,39 +79,27 @@ public class BlockModelStairs<T extends BlockLogicStairs> extends BlockModelStan
             } else {
                 bounds = new AABBd(0.5F, 0.5F, 0.0F, 1.0F, 1.0F, 1.0F);
             }
-            GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
-            tessellator.startDrawingQuads();
+
             tessellator.setNormal(0.0F, -1F, 0.0F);
             renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.BOTTOM, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 1.0F, 0.0F);
             renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.TOP, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, -1F);
             renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.NORTH, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(0.0F, 0.0F, 1.0F);
             renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.SOUTH, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(-1F, 0.0F, 0.0F);
             renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.WEST, metadata));
-            tessellator.draw();
 
-            tessellator.startDrawingQuads();
             tessellator.setNormal(1.0F, 0.0F, 0.0F);
             renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, getBlockTextureFromSideAndMetadata(Side.EAST, metadata));
-            tessellator.draw();
-
-            GL11.glTranslatef(0.5F, 0.5F, 0.5F);
         }
+        tessellator.draw();
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStandard.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStandard.java
index cba9efab6..c53be41f5 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStandard.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStandard.java
@@ -1,9 +1,9 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -15,7 +15,6 @@ import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 
 import java.util.Arrays;
@@ -62,7 +61,7 @@ public class BlockModelStandard<T extends BlockLogic> extends BlockModel<T> {
     }
 
     @Override
-    public boolean renderNoCulling(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean renderNoCulling(@NotNull TessellatorGeneral tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         renderBlocks.renderAllFaces = true;
         boolean result = render(tessellator, worldSource, tilePos);
         renderBlocks.renderAllFaces = false;
@@ -70,7 +69,7 @@ public class BlockModelStandard<T extends BlockLogic> extends BlockModel<T> {
     }
 
     @Override
-    public boolean renderWithOverrideTexture(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos, IconCoordinate textureIndex) {
+    public boolean renderWithOverrideTexture(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos, IconCoordinate textureIndex) {
         renderBlocks.overrideBlockTexture = textureIndex;
         boolean result = render(tessellator, worldSource, tilePos);
         renderBlocks.overrideBlockTexture = null;
@@ -78,12 +77,12 @@ public class BlockModelStandard<T extends BlockLogic> extends BlockModel<T> {
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         return renderBlocks.renderStandardBlock(tessellator, worldSource, this, this.block.getBoundsFromState(worldSource, tilePos), tilePos);
     }
 
     @Override
-    public boolean renderOverbright(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean renderOverbright(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         renderBlocks.overbright = true;
         boolean result = render(tessellator, worldSource, tilePos);
         renderBlocks.overbright = false;
@@ -91,30 +90,17 @@ public class BlockModelStandard<T extends BlockLogic> extends BlockModel<T> {
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (renderBlocks.useInventoryTint) {
-            int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-            float r = (float) (color >> 16 & 0xff) / 255F;
-            float g = (float) (color >> 8 & 0xff) / 255F;
-            float b = (float) (color & 0xff) / 255F;
-            GL11.glColor4f(r * brightness, g * brightness, b * brightness, alpha);
-        } else {
-            GL11.glColor4f(brightness, brightness, brightness, alpha);
-        }
-        float yOffset = 0.5F;
-
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
         AABBdc bounds = getBlockBoundsForItemRender();
-        GL11.glTranslatef(-0.5F, 0.0F - yOffset, -0.5F);
-        renderBlockWithBounds(tessellator, bounds, metadata, brightness, alpha, lightmapCoordinate);
-        GL11.glTranslatef(0.5F, yOffset, 0.5F);
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
+        renderBlockWithBounds(tessellator, bounds, metadata, lightmapCoord, getStandaloneTintColor(metadata));
+        tessellator.offsetTranslation(0.5F, 0.5, 0.5F);
     }
 
-    public void renderBlockWithBounds(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        if (LightmapHelper.isLightmapEnabled() && lightmapCoordinate != null) {
-            LightmapHelper.setLightmapCoord(lightmapCoordinate);
-        }
-
+    public final void renderBlockWithBounds(@NotNull TessellatorGeneral tessellator, @NotNull AABBdc bounds, int metadata, int lightmapCoord, int color) {
         tessellator.startDrawingQuads();
+        tessellator.setLightmapCoord1i(lightmapCoord);
+        tessellator.setColor1i(color);
 
         tessellator.setNormal(0.0f, -1.0f, 0.0f);
         renderBlocks.renderBottomFace(tessellator, bounds, 0.0, 0.0, 0.0, getBlockTextureFromSideAndMetadata(Side.BOTTOM, metadata));
@@ -134,31 +120,8 @@ public class BlockModelStandard<T extends BlockLogic> extends BlockModel<T> {
         tessellator.setNormal(1.0f, 0.0f, 0.0f);
         renderBlocks.renderEastFace(tessellator, bounds, 0.0, 0.0, 0.0, getBlockTextureFromSideAndMetadata(Side.EAST, metadata));
 
-        tessellator.draw();
-
-        if (LightmapHelper.isLightmapEnabled() && lightmapCoordinate != null) {
-            LightmapHelper.setLastLightmapCoord();
-        }
-
         if (hasOverbright()) {
-//			GL11.glDisable(GL11.GL_LIGHTING);
-
-            float brightnessOver = 1.0f;
-            if (renderBlocks.useInventoryTint) {
-                int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-                float r = (float) (color >> 16 & 0xff) / 255F;
-                float g = (float) (color >> 8 & 0xff) / 255F;
-                float b = (float) (color & 0xff) / 255F;
-                GL11.glColor4f(r * brightnessOver, g * brightnessOver, b * brightnessOver, alpha);
-            } else {
-                GL11.glColor4f(brightnessOver, brightnessOver, brightnessOver, alpha);
-            }
-
-            if (LightmapHelper.isLightmapEnabled()) {
-                LightmapHelper.setLightmapCoord(15, 15);
-            }
-
-            tessellator.startDrawingQuads();
+            tessellator.setLightmapCoord2i(15, 15);
 
             tessellator.setNormal(0.0f, -1.0f, 0.0f);
             renderBlocks.renderBottomFace(tessellator, bounds, 0.0, 0.0, 0.0, getBlockOverbrightTextureFromSideAndMeta(Side.BOTTOM, metadata));
@@ -178,14 +141,8 @@ public class BlockModelStandard<T extends BlockLogic> extends BlockModel<T> {
             tessellator.setNormal(1.0f, 0.0f, 0.0f);
             renderBlocks.renderEastFace(tessellator, bounds, 0.0, 0.0, 0.0, getBlockOverbrightTextureFromSideAndMeta(Side.EAST, metadata));
 
-            tessellator.draw();
-
-            if (LightmapHelper.isLightmapEnabled()) {
-                LightmapHelper.setLastLightmapCoord();
-            }
-
-//			GL11.glEnable(GL11.GL_LIGHTING);
         }
+        tessellator.draw();
     }
 
     @Override
@@ -221,6 +178,13 @@ public class BlockModelStandard<T extends BlockLogic> extends BlockModel<T> {
         return getBlockOverbrightTextureFromSideAndMeta(side, source.getBlockData(tilePos));
     }
 
+    public int getStandaloneTintColor(int metadata) {
+        if (renderBlocks.useInventoryTint) {
+            return (BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0) & 0xFFFFFF) | 0xFF000000;
+        }
+        return 0xFFFFFFFF;
+    }
+
     @Override
     public boolean hasOverbright() {
         return this.overbrightTextures.hasTexture();
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStoneMossy.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStoneMossy.java
index 176048d57..2d9079661 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStoneMossy.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelStoneMossy.java
@@ -1,17 +1,16 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
-import org.jetbrains.annotations.Nullable;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelStoneMossy<T extends BlockLogic> extends BlockModelStandard<T> {
     protected IconCoordinate mossOverlay;
@@ -22,7 +21,7 @@ public class BlockModelStoneMossy<T extends BlockLogic> extends BlockModelStanda
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         AABBdc bounds = this.block.getBoundsFromState(worldSource, tilePos);
         renderBlocks.renderStandardBlock(tessellator, worldSource, this, bounds, tilePos, 1.0f, 1.0f, 1.0f);
         renderBlocks.overrideBlockTexture = this.mossOverlay;
@@ -32,45 +31,37 @@ public class BlockModelStoneMossy<T extends BlockLogic> extends BlockModelStanda
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
         renderBlocks.useInventoryTint = false;
-        super.renderStandalone(tessellator, metadata, brightness, alpha, lightmapCoordinate);
+        super.renderStandalone(tessellator, metadata, lightmapCoord);
         renderBlocks.useInventoryTint = true;
-        GL11.glTranslatef(-0.5F, -0.5F, -0.5F);
 
         int color = BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(metadata, 0);
-        float r = (float) (color >> 16 & 0xff) / 255F;
-        float g = (float) (color >> 8 & 0xff) / 255F;
-        float b = (float) (color & 0xff) / 255F;
-        GL11.glColor4f(r * brightness, g * brightness, b * brightness, alpha);
 
         AABBdc bounds = this.block.getBounds();
         IconCoordinate mossCoord = this.mossOverlay;
 
+        tessellator.offsetTranslation(-0.5, -0.5, -0.5);
         tessellator.startDrawingQuads();
+        tessellator.setColor1i(color);
         tessellator.setNormal(0.0F, -1F, 0.0F);
         renderBlocks.renderBottomFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, mossCoord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
         renderBlocks.renderTopFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, mossCoord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+
         tessellator.setNormal(0.0F, 0.0F, -1F);
         renderBlocks.renderNorthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, mossCoord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+
         tessellator.setNormal(0.0F, 0.0F, 1.0F);
         renderBlocks.renderSouthFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, mossCoord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+
         tessellator.setNormal(-1F, 0.0F, 0.0F);
         renderBlocks.renderWestFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, mossCoord);
-        tessellator.draw();
-        tessellator.startDrawingQuads();
+
         tessellator.setNormal(1.0F, 0.0F, 0.0F);
         renderBlocks.renderEastFace(tessellator, bounds, 0.0D, 0.0D, 0.0D, mossCoord);
         tessellator.draw();
-        GL11.glTranslatef(0.5F, 0.5F, 0.5F);
+        tessellator.offsetTranslation(0.5, 0.5, 0.5);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelTorch.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelTorch.java
index 3c8aad47b..5f8ee000f 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelTorch.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelTorch.java
@@ -1,8 +1,8 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicTorch;
@@ -17,17 +17,10 @@ public class BlockModelTorch<T extends BlockLogic> extends BlockModelStandard<T>
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            tessellator.setLightmapCoord(this.block.getLightmapCoord(worldSource, tilePos));
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-            if (this.block.emission > 0) {
-                brightness = 1.0F;
-            }
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+        tessellator.setLightmapCoord1i(this.block.getLightmapCoord(worldSource, tilePos));
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
         double d = 0.4;
         double d1 = 0.5D - d;
         double d2 = 0.2;
@@ -52,7 +45,7 @@ public class BlockModelTorch<T extends BlockLogic> extends BlockModelStandard<T>
         return true;
     }
 
-    public void renderTorchAtAngle(Tessellator tessellator, double x, double y, double z, double topOffsetX, double topOffsetZ) {
+    public void renderTorchAtAngle(TessellatorTerrain tessellator, double x, double y, double z, double topOffsetX, double topOffsetZ) {
         IconCoordinate texture = getBlockTextureFromSideAndMetadata(Side.BOTTOM, 0);
         if (renderBlocks.overrideBlockTexture != null) {
             texture = renderBlocks.overrideBlockTexture;
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelTrapDoor.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelTrapDoor.java
index 66be3fbd1..04d44863e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelTrapDoor.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelTrapDoor.java
@@ -1,7 +1,8 @@
 package net.minecraft.client.render.block.model;
 
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.block.BlockLogicTrapDoor;
@@ -12,7 +13,6 @@ import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 
 public class BlockModelTrapDoor<T extends BlockLogic> extends BlockModelStandard<T> {
     public BlockModelTrapDoor(Block<T> block) {
@@ -22,7 +22,7 @@ public class BlockModelTrapDoor<T extends BlockLogic> extends BlockModelStandard
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int metadata = worldSource.getBlockData(tilePos);
         boolean isUp = BlockLogicTrapDoor.isTrapdoorOpen(metadata);
 
@@ -70,14 +70,15 @@ public class BlockModelTrapDoor<T extends BlockLogic> extends BlockModelStandard
     }
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
-        GL11.glTranslatef(0, 0.25f, 0);
-        super.renderStandalone(tessellator, metadata, brightness, alpha, lightmapCoordinate);
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
+        tessellator.offsetTranslation(0, 0.25, 0);
+        super.renderStandalone(tessellator, metadata, lightmapCoord);
+        tessellator.offsetTranslation(0, -0.25, 0);
     }
 
     @Override
     public @Nullable IconCoordinate getBlockTextureFromSideAndMetadata(@NotNull Side side, int data) {
-        int orientation = data & 3;
+        int orientation = data & 0b11;
         if (BlockLogicTrapDoor.isTrapdoorOpen(data)) {
             int index = Sides.orientationLookUpTrapdoorOpen[6 * orientation + side.getId()];
             return this.blockTextures.get(index);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelVeryRotatable.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelVeryRotatable.java
index 84eb9d1ae..f8c54a8d2 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelVeryRotatable.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelVeryRotatable.java
@@ -1,6 +1,7 @@
 package net.minecraft.client.render.block.model;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -27,7 +28,7 @@ public class BlockModelVeryRotatable<T extends BlockLogic> extends BlockModelSta
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         final int meta = worldSource.getBlockData(tilePos);
         final Direction dir = BlockLogicVeryRotatable.metaToDirection(meta);
 
@@ -48,10 +49,10 @@ public class BlockModelVeryRotatable<T extends BlockLogic> extends BlockModelSta
 
 
     @Override
-    public void renderStandalone(@NotNull Tessellator tessellator, int metadata, float brightness, float alpha, @Nullable Integer lightmapCoordinate) {
+    public void renderStandalone(@NotNull TessellatorGeneral tessellator, int metadata, int lightmapCoord) {
         renderBlocks.uvRotateTop = 1;
         renderBlocks.uvRotateBottom = 1;
-        super.renderStandalone(tessellator, 3, brightness, alpha, lightmapCoordinate);
+        super.renderStandalone(tessellator, 3, lightmapCoord);
         renderBlocks.resetRenderBlocks();
     }
 
@@ -67,42 +68,26 @@ public class BlockModelVeryRotatable<T extends BlockLogic> extends BlockModelSta
 
     public Side getRotatedSide(Side side, int data) {
         final Direction dir = BlockLogicVeryRotatable.metaToDirection(data);
-        switch (dir) { // I love brute forcing fixes so much :3
-            case SOUTH:
-                return side;
-            case EAST:
-                return side.getDirection().rotate(1).getSide();
-            case NORTH:
-                return side.getDirection().rotate(2).getSide();
-            case WEST:
-                return side.getDirection().rotate(3).getSide();
-            case UP:
-                switch (side) {
-                    case NORTH:
-                        return Side.TOP;
-                    case SOUTH:
-                        return Side.BOTTOM;
-                    case TOP:
-                        return Side.SOUTH;
-                    case BOTTOM:
-                        return Side.NORTH;
-                    default:
-                        return side;
-                }
-            case DOWN:
-                switch (side) {
-                    case NORTH:
-                        return Side.TOP;
-                    case SOUTH:
-                        return Side.BOTTOM;
-                    case TOP:
-                        return Side.NORTH;
-                    case BOTTOM:
-                        return Side.SOUTH;
-                    default:
-                        return side;
-                }
-        }
-        return Side.BOTTOM;
+        return switch (dir) { // I love brute forcing fixes so much :3
+            case SOUTH -> side;
+            case EAST -> side.getDirection().rotate(1).getSide();
+            case NORTH -> side.getDirection().rotate(2).getSide();
+            case WEST -> side.getDirection().rotate(3).getSide();
+            case UP -> switch (side) {
+                case NORTH -> Side.TOP;
+                case SOUTH -> Side.BOTTOM;
+                case TOP -> Side.SOUTH;
+                case BOTTOM -> Side.NORTH;
+                default -> side;
+            };
+            case DOWN -> switch (side) {
+                case NORTH -> Side.TOP;
+                case SOUTH -> Side.BOTTOM;
+                case TOP -> Side.NORTH;
+                case BOTTOM -> Side.SOUTH;
+                default -> side;
+            };
+            default -> Side.BOTTOM;
+        };
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelWireRedstone.java b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelWireRedstone.java
index 6ca2e9507..44168af52 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelWireRedstone.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/BlockModelWireRedstone.java
@@ -1,9 +1,9 @@
 package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.client.util.helper.Colors;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogic;
@@ -26,7 +26,7 @@ public class BlockModelWireRedstone<T extends BlockLogic> extends BlockModelStan
     }
 
     @Override
-    public boolean render(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
+    public boolean render(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull TilePosc tilePos) {
         int meta = worldSource.getBlockData(tilePos);
         IconCoordinate straight = this.wireStraight;
         IconCoordinate cross = this.wireCross;
@@ -34,21 +34,13 @@ public class BlockModelWireRedstone<T extends BlockLogic> extends BlockModelStan
             cross = renderBlocks.overrideBlockTexture;
         }
         float brightness = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-//            int lmc = block.getLightmapCoord(worldSource, tilePos);
-//            if(Blocks.lightEmission[block.id] > 0) {
-//                lmc = LightmapHelper.setBlocklightValue(lmc, 15);
-//            }
-            int lmc = LightmapHelper.getLightmapCoord(worldSource.getSavedLightValue(LightLayer.Sky, tilePos), Math.max(worldSource.getSavedLightValue(LightLayer.Block, tilePos), meta & 0xF));
-            tessellator.setLightmapCoord(lmc);
-        } else {
-            brightness = renderBlocks.getBlockBrightness(worldSource, tilePos);
-            if (this.block.emission > 0) {
-                brightness = 1.0f;
-            }
-            brightness = Math.max(brightness, (meta & 0xF) / 16f);
-        }
-        tessellator.setColorOpaque_F(brightness, brightness, brightness);
+//        int lmc = block.getLightmapCoord(worldSource, tilePos);
+//        if (Blocks.lightEmission[block.id] > 0) {
+//            lmc = LightmapHelper.setBlocklightValue(lmc, 15);
+//        }
+        int lmc = LightmapHelper.getLightmapCoord(worldSource.getSavedLightValue(LightLayer.Sky, tilePos), Math.max(worldSource.getSavedLightValue(LightLayer.Block, tilePos), meta & 0xF));
+        tessellator.setLightmapCoord1i(lmc);
+        tessellator.setColorOpaque3f(brightness, brightness, brightness);
 
         Color color = Colors.allRedstoneColors[meta & 0xF];
         float red = color.getRed() / 255.0f;
@@ -57,7 +49,7 @@ public class BlockModelWireRedstone<T extends BlockLogic> extends BlockModelStan
 
         TilePos queryPos = new TilePos();
 
-        tessellator.setColorOpaque_F(brightness * red, brightness * green, brightness * blue);
+        tessellator.setColorOpaque3f(brightness * red, brightness * green, brightness * blue);
         boolean west = BlockLogicWireRedstone.shouldConnectTo(worldSource, tilePos.west(queryPos), Side.WEST) || !worldSource.isBlockNormalCube(tilePos.west(queryPos)) && BlockLogicWireRedstone.shouldConnectToDiagonal(worldSource, tilePos.add(-1, -1, 0, queryPos), Side.NONE, Side.BOTTOM);
         boolean east = BlockLogicWireRedstone.shouldConnectTo(worldSource, tilePos.east(queryPos), Side.EAST) || !worldSource.isBlockNormalCube(tilePos.east(queryPos)) && BlockLogicWireRedstone.shouldConnectToDiagonal(worldSource, tilePos.add(1, -1, 0, queryPos), Side.NONE, Side.BOTTOM);
         boolean north = BlockLogicWireRedstone.shouldConnectTo(worldSource, tilePos.north(queryPos), Side.NORTH) || !worldSource.isBlockNormalCube(tilePos.north(queryPos)) && BlockLogicWireRedstone.shouldConnectToDiagonal(worldSource, tilePos.add(0, -1, -1, queryPos), Side.NONE, Side.BOTTOM);
diff --git a/game/client/src/main/java/net/minecraft/client/render/block/model/RenderBlocks.java b/game/client/src/main/java/net/minecraft/client/render/block/model/RenderBlocks.java
index fedbd41da..77a5162ef 100644
--- a/game/client/src/main/java/net/minecraft/client/render/block/model/RenderBlocks.java
+++ b/game/client/src/main/java/net/minecraft/client/render/block/model/RenderBlocks.java
@@ -2,6 +2,7 @@ package net.minecraft.client.render.block.model;
 
 import net.minecraft.client.render.LightingCache;
 import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.world.pos.TilePos;
 import net.minecraft.core.world.pos.TilePosc;
@@ -12,7 +13,6 @@ import org.joml.primitives.AABBdc;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.enums.LightLayer;
 import net.minecraft.core.util.helper.Side;
@@ -111,11 +111,11 @@ public final class RenderBlocks {
     }
 
     @Deprecated
-    public boolean renderStandardBlock(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, int x, int y, int z) {
+    public boolean renderStandardBlock(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, int x, int y, int z) {
         return renderStandardBlock(tessellator, worldSource, blockModel, bounds, new TilePos(x, y, z));
     }
 
-    public boolean renderStandardBlock(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, @NotNull TilePosc tilePos) {
+    public boolean renderStandardBlock(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, @NotNull TilePosc tilePos) {
         int color = BlockColorDispatcher.getInstance().getDispatch(blockModel.block).getWorldColor(worldSource, tilePos, 0);
         float r = (float) (color >> 16 & 0xff) / 255F;
         float g = (float) (color >> 8 & 0xff) / 255F;
@@ -128,11 +128,11 @@ public final class RenderBlocks {
      * Thanks! :D
      */
     @Deprecated
-    public boolean renderStandardBlock(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, int x, int y, int z, float r, float g, float b) {
+    public boolean renderStandardBlock(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, int x, int y, int z, float r, float g, float b) {
         return renderStandardBlock(tessellator, worldSource, blockModel, bounds, new TilePos(x, y, z), r, g, b);
     }
 
-    public boolean renderStandardBlock(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, float r, float g, float b) {
+    public boolean renderStandardBlock(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, float r, float g, float b) {
         this.enableAO = true;
         int meta = worldSource.getBlockData(tilePos);
         this.cache.setupCache(blockModel.block, worldSource, tilePos);
@@ -145,11 +145,11 @@ public final class RenderBlocks {
     }
 
     @Deprecated
-    public boolean renderSide(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, int x, int y, int z, float r, float g, float b, @NotNull Side side, int meta) {
+    public boolean renderSide(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, int x, int y, int z, float r, float g, float b, @NotNull Side side, int meta) {
         return renderSide(tessellator, worldSource, blockModel, bounds, new TilePos(x, y, z), r, g, b, side, meta);
     }
 
-    public boolean renderSide(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, float r, float g, float b, @NotNull Side side, int meta) {
+    public boolean renderSide(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, float r, float g, float b, @NotNull Side side, int meta) {
         boolean useColor;
         return switch (side) {
             case BOTTOM -> {
@@ -208,7 +208,7 @@ public final class RenderBlocks {
      * @author CyborgCabbage
      * Thanks! :D
      */
-    public boolean renderSide(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds,
+    public boolean renderSide(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull BlockModelStandard<?> blockModel, @NotNull AABBdc bounds,
                               @NotNull TilePosc tilePos, float r, float g, float b, @NotNull Side side, int meta,
                               int dirX, int dirY, int dirZ, float depth,
                               int topX, int topY, int topZ, float topP, float botP,
@@ -262,8 +262,22 @@ public final class RenderBlocks {
         boolean ao = this.mc.isAmbientOcclusionEnabled() && block.emission == 0;
         boolean isFullCube = depth <= FULL_CUBE_THRESHOLD;
 
-        if (LightmapHelper.isLightmapEnabled()) {
-            if (this.overbright) {
+        if (this.overbright) {
+            int dirX2 = dirX;
+            int dirY2 = dirY;
+            int dirZ2 = dirZ;
+
+            if (!isFullCube) {
+                dirX2 = 0;
+                dirY2 = 0;
+                dirZ2 = 0;
+            }
+
+            int lmc = LightmapHelper.getOverbrightLightmapCoord(worldSource.getSavedLightValue(LightLayer.Sky, dirX2, dirY2, dirZ2));
+
+            this.lightmapCoordTopLeft = this.lightmapCoordBottomLeft = this.lightmapCoordBottomRight = this.lightmapCoordTopRight = lmc;
+        } else {
+            if (ao) {
                 int dirX2 = dirX;
                 int dirY2 = dirY;
                 int dirZ2 = dirZ;
@@ -274,56 +288,40 @@ public final class RenderBlocks {
                     dirZ2 = 0;
                 }
 
-                int lmc = LightmapHelper.getOverbrightLightmapCoord(worldSource.getSavedLightValue(LightLayer.Sky, dirX2, dirY2, dirZ2));
+                boolean topT = this.cache.getOpacity(dirX2 + topX, dirY2 + topY, dirZ2 + topZ);
+                boolean botT = this.cache.getOpacity(dirX2 - topX, dirY2 - topY, dirZ2 - topZ);
+                boolean lefT = this.cache.getOpacity(dirX2 + lefX, dirY2 + lefY, dirZ2 + lefZ);
+                boolean rigT = this.cache.getOpacity(dirX2 - lefX, dirY2 - lefY, dirZ2 - lefZ);
 
-                this.lightmapCoordTopLeft = this.lightmapCoordBottomLeft = this.lightmapCoordBottomRight = this.lightmapCoordTopRight = lmc;
+                boolean topLefT = this.cache.getOpacity(dirX2 + topX + lefX, dirY2 + topY + lefY, dirZ2 + topZ + lefZ);
+                boolean topRigT = this.cache.getOpacity(dirX2 + topX - lefX, dirY2 + topY - lefY, dirZ2 + topZ - lefZ);
+                boolean botLefT = this.cache.getOpacity(dirX2 - topX + lefX, dirY2 - topY + lefY, dirZ2 - topZ + lefZ);
+                boolean botRigT = this.cache.getOpacity(dirX2 - topX - lefX, dirY2 - topY - lefY, dirZ2 - topZ - lefZ);
+
+                int lmcCen = this.cache.getLightmapCoord(dirX2, dirY2, dirZ2);
+
+                int lmcTop = topT ? lmcCen : this.cache.getLightmapCoord(dirX2 + topX, dirY2 + topY, dirZ2 + topZ);
+                int lmcBot = botT ? lmcCen : this.cache.getLightmapCoord(dirX2 - topX, dirY2 - topY, dirZ2 - topZ);
+                int lmcLef = lefT ? lmcCen : this.cache.getLightmapCoord(dirX2 + lefX, dirY2 + lefY, dirZ2 + lefZ);
+                int lmcRig = rigT ? lmcCen : this.cache.getLightmapCoord(dirX2 - lefX, dirY2 - lefY, dirZ2 - lefZ);
+
+                int lmcTopLef = topT && lefT ? lmcLef : (topLefT ? lmcCen : this.cache.getLightmapCoord(dirX2 + topX + lefX, dirY2 + topY + lefY, dirZ2 + topZ + lefZ));
+                int lmcBotLef = botT && lefT ? lmcLef : (botLefT ? lmcCen : this.cache.getLightmapCoord(dirX2 - topX + lefX, dirY2 - topY + lefY, dirZ2 - topZ + lefZ));
+                int lmcTopRig = topT && rigT ? lmcRig : (topRigT ? lmcCen : this.cache.getLightmapCoord(dirX2 + topX - lefX, dirY2 + topY - lefY, dirZ2 + topZ - lefZ));
+                int lmcBotRig = botT && rigT ? lmcRig : (botRigT ? lmcCen : this.cache.getLightmapCoord(dirX2 - topX - lefX, dirY2 - topY - lefY, dirZ2 - topZ - lefZ));
+
+                this.lightmapCoordTopLeft = LightmapHelper.avg(lmcCen, lmcLef, lmcTop, lmcTopLef);
+                this.lightmapCoordTopRight = LightmapHelper.avg(lmcCen, lmcRig, lmcTop, lmcTopRig);
+                this.lightmapCoordBottomLeft = LightmapHelper.avg(lmcCen, lmcLef, lmcBot, lmcBotLef);
+                this.lightmapCoordBottomRight = LightmapHelper.avg(lmcCen, lmcRig, lmcBot, lmcBotRig);
             } else {
-                if (ao) {
-                    int dirX2 = dirX;
-                    int dirY2 = dirY;
-                    int dirZ2 = dirZ;
-
-                    if (!isFullCube) {
-                        dirX2 = 0;
-                        dirY2 = 0;
-                        dirZ2 = 0;
-                    }
-
-                    boolean topT = this.cache.getOpacity(dirX2 + topX, dirY2 + topY, dirZ2 + topZ);
-                    boolean botT = this.cache.getOpacity(dirX2 - topX, dirY2 - topY, dirZ2 - topZ);
-                    boolean lefT = this.cache.getOpacity(dirX2 + lefX, dirY2 + lefY, dirZ2 + lefZ);
-                    boolean rigT = this.cache.getOpacity(dirX2 - lefX, dirY2 - lefY, dirZ2 - lefZ);
-
-                    boolean topLefT = this.cache.getOpacity(dirX2 + topX + lefX, dirY2 + topY + lefY, dirZ2 + topZ + lefZ);
-                    boolean topRigT = this.cache.getOpacity(dirX2 + topX - lefX, dirY2 + topY - lefY, dirZ2 + topZ - lefZ);
-                    boolean botLefT = this.cache.getOpacity(dirX2 - topX + lefX, dirY2 - topY + lefY, dirZ2 - topZ + lefZ);
-                    boolean botRigT = this.cache.getOpacity(dirX2 - topX - lefX, dirY2 - topY - lefY, dirZ2 - topZ - lefZ);
-
-                    int lmcCen = this.cache.getLightmapCoord(dirX2, dirY2, dirZ2);
-
-                    int lmcTop = topT ? lmcCen : this.cache.getLightmapCoord(dirX2 + topX, dirY2 + topY, dirZ2 + topZ);
-                    int lmcBot = botT ? lmcCen : this.cache.getLightmapCoord(dirX2 - topX, dirY2 - topY, dirZ2 - topZ);
-                    int lmcLef = lefT ? lmcCen : this.cache.getLightmapCoord(dirX2 + lefX, dirY2 + lefY, dirZ2 + lefZ);
-                    int lmcRig = rigT ? lmcCen : this.cache.getLightmapCoord(dirX2 - lefX, dirY2 - lefY, dirZ2 - lefZ);
-
-                    int lmcTopLef = topT && lefT ? lmcLef : (topLefT ? lmcCen : this.cache.getLightmapCoord(dirX2 + topX + lefX, dirY2 + topY + lefY, dirZ2 + topZ + lefZ));
-                    int lmcBotLef = botT && lefT ? lmcLef : (botLefT ? lmcCen : this.cache.getLightmapCoord(dirX2 - topX + lefX, dirY2 - topY + lefY, dirZ2 - topZ + lefZ));
-                    int lmcTopRig = topT && rigT ? lmcRig : (topRigT ? lmcCen : this.cache.getLightmapCoord(dirX2 + topX - lefX, dirY2 + topY - lefY, dirZ2 + topZ - lefZ));
-                    int lmcBotRig = botT && rigT ? lmcRig : (botRigT ? lmcCen : this.cache.getLightmapCoord(dirX2 - topX - lefX, dirY2 - topY - lefY, dirZ2 - topZ - lefZ));
-
-                    this.lightmapCoordTopLeft = LightmapHelper.avg(lmcCen, lmcLef, lmcTop, lmcTopLef);
-                    this.lightmapCoordTopRight = LightmapHelper.avg(lmcCen, lmcRig, lmcTop, lmcTopRig);
-                    this.lightmapCoordBottomLeft = LightmapHelper.avg(lmcCen, lmcLef, lmcBot, lmcBotLef);
-                    this.lightmapCoordBottomRight = LightmapHelper.avg(lmcCen, lmcRig, lmcBot, lmcBotRig);
+                int lmc;
+                if (!isFullCube) {
+                    lmc = block.getLightmapCoord(worldSource, tilePos);
                 } else {
-                    int lmc;
-                    if (!isFullCube) {
-                        lmc = block.getLightmapCoord(worldSource, tilePos);
-                    } else {
-                        lmc = block.getLightmapCoord(worldSource, tilePos.add(dirX, dirY, dirZ, new TilePos()));
-                    }
-                    this.lightmapCoordTopLeft = this.lightmapCoordBottomLeft = this.lightmapCoordBottomRight = this.lightmapCoordTopRight = lmc;
+                    lmc = block.getLightmapCoord(worldSource, tilePos.add(dirX, dirY, dirZ, new TilePos()));
                 }
+                this.lightmapCoordTopLeft = this.lightmapCoordBottomLeft = this.lightmapCoordBottomRight = this.lightmapCoordTopRight = lmc;
             }
         }
 
@@ -427,11 +425,11 @@ public final class RenderBlocks {
         this.colorBlueTopRight *= ltr;
     }
 
-    public void renderBottomFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
+    public void renderBottomFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
         renderBottomFace(tessellator, bounds, tilePos.x(), tilePos.y(), tilePos.z(), tex);
     }
 
-    public void renderBottomFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
+    public void renderBottomFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
         if (this.overrideBlockTexture != null) tex = this.overrideBlockTexture;
         if (tex == null) return;
         double d3 = tex.getSubIconU(bounds.minX());
@@ -488,17 +486,17 @@ public final class RenderBlocks {
         double d14 = z + bounds.minZ();
         double d15 = z + bounds.maxZ();
         if (this.enableAO) {
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopLeft);
-            tessellator.setColorOpaque_F(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopLeft);
+            tessellator.setColorOpaque3f(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
             tessellator.addVertexWithUV(d11, d13, d15, d8, d10);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomLeft);
-            tessellator.setColorOpaque_F(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomLeft);
+            tessellator.setColorOpaque3f(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
             tessellator.addVertexWithUV(d11, d13, d14, d3, d5);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomRight);
-            tessellator.setColorOpaque_F(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomRight);
+            tessellator.setColorOpaque3f(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
             tessellator.addVertexWithUV(d12, d13, d14, d7, d9);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopRight);
-            tessellator.setColorOpaque_F(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopRight);
+            tessellator.setColorOpaque3f(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
             tessellator.addVertexWithUV(d12, d13, d15, d4, d6);
         } else {
             tessellator.addVertexWithUV(d11, d13, d15, d8, d10);
@@ -508,11 +506,11 @@ public final class RenderBlocks {
         }
     }
 
-    public void renderTopFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
+    public void renderTopFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
         renderTopFace(tessellator, bounds, tilePos.x(), tilePos.y(), tilePos.z(), tex);
     }
 
-    public void renderTopFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
+    public void renderTopFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
         if (this.overrideBlockTexture != null) tex = this.overrideBlockTexture;
         if (tex == null) return;
         double d3 = tex.getSubIconU(bounds.minX());
@@ -569,17 +567,17 @@ public final class RenderBlocks {
         double d14 = z + bounds.minZ();
         double d15 = z + bounds.maxZ();
         if (this.enableAO) {
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopLeft);
-            tessellator.setColorOpaque_F(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopLeft);
+            tessellator.setColorOpaque3f(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
             tessellator.addVertexWithUV(d12, d13, d15, d4, d6);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomLeft);
-            tessellator.setColorOpaque_F(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomLeft);
+            tessellator.setColorOpaque3f(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
             tessellator.addVertexWithUV(d12, d13, d14, d7, d9);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomRight);
-            tessellator.setColorOpaque_F(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomRight);
+            tessellator.setColorOpaque3f(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
             tessellator.addVertexWithUV(d11, d13, d14, d3, d5);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopRight);
-            tessellator.setColorOpaque_F(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopRight);
+            tessellator.setColorOpaque3f(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
             tessellator.addVertexWithUV(d11, d13, d15, d8, d10);
         } else {
             tessellator.addVertexWithUV(d12, d13, d15, d4, d6);
@@ -589,11 +587,11 @@ public final class RenderBlocks {
         }
     }
 
-    public void renderNorthFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
+    public void renderNorthFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
         renderNorthFace(tessellator, bounds, tilePos.x(), tilePos.y(), tilePos.z(), tex);
     }
 
-    public void renderNorthFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
+    public void renderNorthFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
         if (this.overrideBlockTexture != null) tex = this.overrideBlockTexture;
         if (tex == null) return;
         double d3 = tex.getSubIconU(bounds.minX());
@@ -655,17 +653,17 @@ public final class RenderBlocks {
         double d15 = y + bounds.maxY();
         double d16 = z + bounds.minZ();
         if (this.enableAO) {
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopLeft);
-            tessellator.setColorOpaque_F(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopLeft);
+            tessellator.setColorOpaque3f(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
             tessellator.addVertexWithUV(d12, d15, d16, d8, d10);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomLeft);
-            tessellator.setColorOpaque_F(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomLeft);
+            tessellator.setColorOpaque3f(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
             tessellator.addVertexWithUV(d13, d15, d16, d3, d5);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomRight);
-            tessellator.setColorOpaque_F(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomRight);
+            tessellator.setColorOpaque3f(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
             tessellator.addVertexWithUV(d13, d14, d16, d9, d11);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopRight);
-            tessellator.setColorOpaque_F(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopRight);
+            tessellator.setColorOpaque3f(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
             tessellator.addVertexWithUV(d12, d14, d16, d4, d6);
         } else {
             tessellator.addVertexWithUV(d12, d15, d16, d8, d10);
@@ -675,11 +673,11 @@ public final class RenderBlocks {
         }
     }
 
-    public void renderSouthFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
+    public void renderSouthFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
         renderSouthFace(tessellator, bounds, tilePos.x(), tilePos.y(), tilePos.z(), tex);
     }
 
-    public void renderSouthFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
+    public void renderSouthFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
         if (this.overrideBlockTexture != null) tex = this.overrideBlockTexture;
         if (tex == null) return;
         double d3 = tex.getSubIconU(bounds.minX());
@@ -741,17 +739,17 @@ public final class RenderBlocks {
         double y1 = y + bounds.maxY();
         double z0 = z + bounds.maxZ();
         if (this.enableAO) {
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopLeft);
-            tessellator.setColorOpaque_F(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopLeft);
+            tessellator.setColorOpaque3f(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
             tessellator.addVertexWithUV(x0, y1, z0, d3, d5);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomLeft);
-            tessellator.setColorOpaque_F(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomLeft);
+            tessellator.setColorOpaque3f(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
             tessellator.addVertexWithUV(x0, y0, z0, d9, d11);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomRight);
-            tessellator.setColorOpaque_F(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomRight);
+            tessellator.setColorOpaque3f(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
             tessellator.addVertexWithUV(x1, y0, z0, d4, d6);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopRight);
-            tessellator.setColorOpaque_F(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopRight);
+            tessellator.setColorOpaque3f(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
             tessellator.addVertexWithUV(x1, y1, z0, d8, d10);
         } else {
             tessellator.addVertexWithUV(x0, y1, z0, d3, d5);
@@ -761,11 +759,11 @@ public final class RenderBlocks {
         }
     }
 
-    public void renderWestFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
+    public void renderWestFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
         renderWestFace(tessellator, bounds, tilePos.x(), tilePos.y(), tilePos.z(), tex);
     }
 
-    public void renderWestFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
+    public void renderWestFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
         if (this.overrideBlockTexture != null) tex = this.overrideBlockTexture;
         if (tex == null) return;
         double d3 = tex.getSubIconU(bounds.minZ());
@@ -827,17 +825,17 @@ public final class RenderBlocks {
         double d15 = z + bounds.minZ();
         double d16 = z + bounds.maxZ();
         if (this.enableAO) {
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopLeft);
-            tessellator.setColorOpaque_F(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopLeft);
+            tessellator.setColorOpaque3f(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
             tessellator.addVertexWithUV(d12, d14, d16, d8, d10);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomLeft);
-            tessellator.setColorOpaque_F(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomLeft);
+            tessellator.setColorOpaque3f(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
             tessellator.addVertexWithUV(d12, d14, d15, d3, d5);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomRight);
-            tessellator.setColorOpaque_F(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomRight);
+            tessellator.setColorOpaque3f(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
             tessellator.addVertexWithUV(d12, d13, d15, d9, d11);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopRight);
-            tessellator.setColorOpaque_F(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopRight);
+            tessellator.setColorOpaque3f(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
             tessellator.addVertexWithUV(d12, d13, d16, d4, d6);
         } else {
             tessellator.addVertexWithUV(d12, d14, d16, d8, d10);
@@ -847,11 +845,11 @@ public final class RenderBlocks {
         }
     }
 
-    public void renderEastFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
+    public void renderEastFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, @NotNull TilePosc tilePos, @Nullable IconCoordinate tex) {
         renderEastFace(tessellator, bounds, tilePos.x(), tilePos.y(), tilePos.z(), tex);
     }
 
-    public void renderEastFace(@NotNull Tessellator tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
+    public void renderEastFace(@NotNull TessellatorTerrain tessellator, @NotNull AABBdc bounds, double x, double y, double z, @Nullable IconCoordinate tex) {
         if (this.overrideBlockTexture != null) tex = this.overrideBlockTexture;
         if (tex == null) return;
         double uMin = tex.getSubIconU(bounds.minZ());
@@ -914,17 +912,17 @@ public final class RenderBlocks {
         double zMax = z + bounds.maxZ();
 
         if (this.enableAO) {
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopLeft);
-            tessellator.setColorOpaque_F(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopLeft);
+            tessellator.setColorOpaque3f(this.colorRedTopLeft, this.colorGreenTopLeft, this.colorBlueTopLeft);
             tessellator.addVertexWithUV(xMax, yMin, zMax, uMin2, vMax2);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomLeft);
-            tessellator.setColorOpaque_F(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomLeft);
+            tessellator.setColorOpaque3f(this.colorRedBottomLeft, this.colorGreenBottomLeft, this.colorBlueBottomLeft);
             tessellator.addVertexWithUV(xMax, yMin, zMin, uMax, vMax);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordBottomRight);
-            tessellator.setColorOpaque_F(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordBottomRight);
+            tessellator.setColorOpaque3f(this.colorRedBottomRight, this.colorGreenBottomRight, this.colorBlueBottomRight);
             tessellator.addVertexWithUV(xMax, yMax, zMin, uMax2, vMin2);
-            if (LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(this.lightmapCoordTopRight);
-            tessellator.setColorOpaque_F(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
+            tessellator.setLightmapCoord1i(this.lightmapCoordTopRight);
+            tessellator.setColorOpaque3f(this.colorRedTopRight, this.colorGreenTopRight, this.colorBlueTopRight);
             tessellator.addVertexWithUV(xMax, yMax, zMax, uMin, vMin);
         } else {
             tessellator.addVertexWithUV(xMax, yMin, zMax, uMin2, vMax2);
diff --git a/game/client/src/main/java/net/minecraft/client/render/camera/EntityCamera.java b/game/client/src/main/java/net/minecraft/client/render/camera/EntityCamera.java
index 4978440b2..0e7bc9ce7 100644
--- a/game/client/src/main/java/net/minecraft/client/render/camera/EntityCamera.java
+++ b/game/client/src/main/java/net/minecraft/client/render/camera/EntityCamera.java
@@ -50,7 +50,7 @@ public abstract class EntityCamera
         if (partialTick == 1f || this.mob.isRemoved()) {
             return this.mob.y + this.mob.getHeadHeight();
         } else {
-            if (Double.isNaN(this.hhO)) this.hhO = this.mob.getHeadHeight();
+            if (!Double.isFinite(this.hhO)) this.hhO = this.mob.getHeadHeight();
             return (this.mob.yo + (this.mob.y - this.mob.yo) * partialTick) + MathHelper.lerp(this.hhO, this.mob.getHeadHeight(), partialTick);
         }
     }
@@ -86,7 +86,7 @@ public abstract class EntityCamera
 
     @Override
     public double getFov() {
-        return this.mc.gameSettings.FoV.value;
+        return this.mc.gameSettings.FoV.get();
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/culling/CameraFrustum.java b/game/client/src/main/java/net/minecraft/client/render/culling/CameraFrustum.java
index e580aa5d3..f7d88dc6a 100644
--- a/game/client/src/main/java/net/minecraft/client/render/culling/CameraFrustum.java
+++ b/game/client/src/main/java/net/minecraft/client/render/culling/CameraFrustum.java
@@ -1,29 +1,41 @@
 package net.minecraft.client.render.culling;
 
 import net.minecraft.client.render.camera.ICamera;
+import net.minecraft.client.render.renderer.GLRenderer;
 import org.jetbrains.annotations.NotNull;
+import org.joml.FrustumIntersection;
+import org.joml.Matrix4f;
 import org.joml.primitives.AABBdc;
 
 public class CameraFrustum {
     private final @NotNull ICamera camera;
-    private final @NotNull FrustumData frustum;
+    private static final @NotNull FrustumIntersection frustum = new FrustumIntersection();
+    private static final @NotNull Matrix4f matrix4f = new Matrix4f();
+
+    public static void recalcFrustrum() {
+        frustum.set(GLRenderer.projectionM4f().mul(GLRenderer.viewM4f(), matrix4f).mul(GLRenderer.modelM4f(), matrix4f));
+    }
+
+    public static @NotNull FrustumIntersection getFrustum() {
+        return frustum;
+    }
 
     public CameraFrustum(@NotNull ICamera camera) {
         this.camera = camera;
-        this.frustum = Frustum.getFrustum();
     }
 
-    public boolean cubeInFrustum(double x0, double y0, double z0, double x1, double y1, double z1, float partialTick) {
-        return this.frustum.cubeInFrustum(x0 - this.camera.getX(partialTick),
-            y0 - this.camera.getY(partialTick),
-            z0 - this.camera.getZ(partialTick),
-            x1 - this.camera.getX(partialTick),
-            y1 - this.camera.getY(partialTick),
-            z1 - this.camera.getZ(partialTick)
+    public boolean cubeInFrustum(@NotNull AABBdc aabb, float partialTick) {
+        return frustum.testAab(
+            (float) (aabb.minX() - this.camera.getX(partialTick)),
+            (float) (aabb.minY() - this.camera.getY(partialTick)),
+            (float) (aabb.minZ() - this.camera.getZ(partialTick)),
+            (float) (aabb.maxX() - this.camera.getX(partialTick)),
+            (float) (aabb.maxY() - this.camera.getY(partialTick)),
+            (float) (aabb.maxZ() - this.camera.getZ(partialTick))
         );
     }
 
     public boolean isVisible(@NotNull AABBdc aabb, float partialTick) {
-        return cubeInFrustum(aabb.minX(), aabb.minY(), aabb.minZ(), aabb.maxX(), aabb.maxY(), aabb.maxZ(), partialTick);
+        return cubeInFrustum(aabb, partialTick);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/culling/Frustum.java b/game/client/src/main/java/net/minecraft/client/render/culling/Frustum.java
deleted file mode 100644
index a02e8e7df..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/culling/Frustum.java
+++ /dev/null
@@ -1,96 +0,0 @@
-package net.minecraft.client.render.culling;
-
-import java.nio.FloatBuffer;
-
-import net.minecraft.core.util.helper.MathHelper;
-import net.minecraft.client.GLAllocation;
-import org.lwjgl.opengl.GL11;
-
-public class Frustum extends FrustumData
-{
-    private static final Frustum FRUSTUM = new Frustum();
-    private final FloatBuffer _proj;
-    private final FloatBuffer _modl;
-    private final FloatBuffer _clip;
-
-    public Frustum()
-    {
-        _proj = GLAllocation.createDirectFloatBuffer(16);
-        _modl = GLAllocation.createDirectFloatBuffer(16);
-        _clip = GLAllocation.createDirectFloatBuffer(16);
-    }
-
-    public static FrustumData getFrustum()
-    {
-        FRUSTUM.calculateFrustum();
-        return FRUSTUM;
-    }
-
-    private void normalizePlane(float[][] af, int i)
-    {
-        float f = MathHelper.sqrt_float(af[i][0] * af[i][0] + af[i][1] * af[i][1] + af[i][2] * af[i][2]);
-        af[i][0] /= f;
-        af[i][1] /= f;
-        af[i][2] /= f;
-        af[i][3] /= f;
-    }
-
-    private void calculateFrustum()
-    {
-        _proj.clear();
-        _modl.clear();
-        _clip.clear();
-        GL11.glGetFloatv(GL11.GL_PROJECTION_MATRIX, _proj);
-        GL11.glGetFloatv(GL11.GL_MODELVIEW_MATRIX, _modl);
-        _proj.flip().limit(16);
-        _proj.get(projectionMatrix);
-        _modl.flip().limit(16);
-        _modl.get(modelViewMatrix);
-        clip[0] = modelViewMatrix[0] * projectionMatrix[0] + modelViewMatrix[1] * projectionMatrix[4] + modelViewMatrix[2] * projectionMatrix[8] + modelViewMatrix[3] * projectionMatrix[12];
-        clip[1] = modelViewMatrix[0] * projectionMatrix[1] + modelViewMatrix[1] * projectionMatrix[5] + modelViewMatrix[2] * projectionMatrix[9] + modelViewMatrix[3] * projectionMatrix[13];
-        clip[2] = modelViewMatrix[0] * projectionMatrix[2] + modelViewMatrix[1] * projectionMatrix[6] + modelViewMatrix[2] * projectionMatrix[10] + modelViewMatrix[3] * projectionMatrix[14];
-        clip[3] = modelViewMatrix[0] * projectionMatrix[3] + modelViewMatrix[1] * projectionMatrix[7] + modelViewMatrix[2] * projectionMatrix[11] + modelViewMatrix[3] * projectionMatrix[15];
-        clip[4] = modelViewMatrix[4] * projectionMatrix[0] + modelViewMatrix[5] * projectionMatrix[4] + modelViewMatrix[6] * projectionMatrix[8] + modelViewMatrix[7] * projectionMatrix[12];
-        clip[5] = modelViewMatrix[4] * projectionMatrix[1] + modelViewMatrix[5] * projectionMatrix[5] + modelViewMatrix[6] * projectionMatrix[9] + modelViewMatrix[7] * projectionMatrix[13];
-        clip[6] = modelViewMatrix[4] * projectionMatrix[2] + modelViewMatrix[5] * projectionMatrix[6] + modelViewMatrix[6] * projectionMatrix[10] + modelViewMatrix[7] * projectionMatrix[14];
-        clip[7] = modelViewMatrix[4] * projectionMatrix[3] + modelViewMatrix[5] * projectionMatrix[7] + modelViewMatrix[6] * projectionMatrix[11] + modelViewMatrix[7] * projectionMatrix[15];
-        clip[8] = modelViewMatrix[8] * projectionMatrix[0] + modelViewMatrix[9] * projectionMatrix[4] + modelViewMatrix[10] * projectionMatrix[8] + modelViewMatrix[11] * projectionMatrix[12];
-        clip[9] = modelViewMatrix[8] * projectionMatrix[1] + modelViewMatrix[9] * projectionMatrix[5] + modelViewMatrix[10] * projectionMatrix[9] + modelViewMatrix[11] * projectionMatrix[13];
-        clip[10] = modelViewMatrix[8] * projectionMatrix[2] + modelViewMatrix[9] * projectionMatrix[6] + modelViewMatrix[10] * projectionMatrix[10] + modelViewMatrix[11] * projectionMatrix[14];
-        clip[11] = modelViewMatrix[8] * projectionMatrix[3] + modelViewMatrix[9] * projectionMatrix[7] + modelViewMatrix[10] * projectionMatrix[11] + modelViewMatrix[11] * projectionMatrix[15];
-        clip[12] = modelViewMatrix[12] * projectionMatrix[0] + modelViewMatrix[13] * projectionMatrix[4] + modelViewMatrix[14] * projectionMatrix[8] + modelViewMatrix[15] * projectionMatrix[12];
-        clip[13] = modelViewMatrix[12] * projectionMatrix[1] + modelViewMatrix[13] * projectionMatrix[5] + modelViewMatrix[14] * projectionMatrix[9] + modelViewMatrix[15] * projectionMatrix[13];
-        clip[14] = modelViewMatrix[12] * projectionMatrix[2] + modelViewMatrix[13] * projectionMatrix[6] + modelViewMatrix[14] * projectionMatrix[10] + modelViewMatrix[15] * projectionMatrix[14];
-        clip[15] = modelViewMatrix[12] * projectionMatrix[3] + modelViewMatrix[13] * projectionMatrix[7] + modelViewMatrix[14] * projectionMatrix[11] + modelViewMatrix[15] * projectionMatrix[15];
-        frustumData[0][0] = clip[3] - clip[0];
-        frustumData[0][1] = clip[7] - clip[4];
-        frustumData[0][2] = clip[11] - clip[8];
-        frustumData[0][3] = clip[15] - clip[12];
-        normalizePlane(frustumData, 0);
-        frustumData[1][0] = clip[3] + clip[0];
-        frustumData[1][1] = clip[7] + clip[4];
-        frustumData[1][2] = clip[11] + clip[8];
-        frustumData[1][3] = clip[15] + clip[12];
-        normalizePlane(frustumData, 1);
-        frustumData[2][0] = clip[3] + clip[1];
-        frustumData[2][1] = clip[7] + clip[5];
-        frustumData[2][2] = clip[11] + clip[9];
-        frustumData[2][3] = clip[15] + clip[13];
-        normalizePlane(frustumData, 2);
-        frustumData[3][0] = clip[3] - clip[1];
-        frustumData[3][1] = clip[7] - clip[5];
-        frustumData[3][2] = clip[11] - clip[9];
-        frustumData[3][3] = clip[15] - clip[13];
-        normalizePlane(frustumData, 3);
-        frustumData[4][0] = clip[3] - clip[2];
-        frustumData[4][1] = clip[7] - clip[6];
-        frustumData[4][2] = clip[11] - clip[10];
-        frustumData[4][3] = clip[15] - clip[14];
-        normalizePlane(frustumData, 4);
-        frustumData[5][0] = clip[3] + clip[2];
-        frustumData[5][1] = clip[7] + clip[6];
-        frustumData[5][2] = clip[11] + clip[10];
-        frustumData[5][3] = clip[15] + clip[14];
-        normalizePlane(frustumData, 5);
-    }
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/culling/FrustumCuller.java b/game/client/src/main/java/net/minecraft/client/render/culling/FrustumCuller.java
deleted file mode 100644
index 4f40349be..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/culling/FrustumCuller.java
+++ /dev/null
@@ -1,30 +0,0 @@
-package net.minecraft.client.render.culling;
-
-
-import org.jetbrains.annotations.NotNull;
-import org.joml.primitives.AABBdc;
-
-public class FrustumCuller {
-    private final FrustumData frustum;
-    private double xOff;
-    private double yOff;
-    private double zOff;
-
-    public FrustumCuller() {
-        this.frustum = Frustum.getFrustum();
-    }
-
-    public void prepare(double xOff, double yOff, double zOff) {
-        this.xOff = xOff;
-        this.yOff = yOff;
-        this.zOff = zOff;
-    }
-
-    public boolean cubeInFrustum(double x0, double y0, double z0, double x1, double y1, double z1) {
-        return this.frustum.cubeInFrustum(x0 - this.xOff, y0 - this.yOff, z0 - this.zOff, x1 - this.xOff, y1 - this.yOff, z1 - this.zOff);
-    }
-
-    public boolean isVisible(@NotNull AABBdc aabb) {
-        return cubeInFrustum(aabb.minX(), aabb.minY(), aabb.minZ(), aabb.maxX(), aabb.maxY(), aabb.maxZ());
-    }
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/culling/FrustumData.java b/game/client/src/main/java/net/minecraft/client/render/culling/FrustumData.java
deleted file mode 100644
index 22de5a3b0..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/culling/FrustumData.java
+++ /dev/null
@@ -1,38 +0,0 @@
-package net.minecraft.client.render.culling;
-
-
-public class FrustumData
-{
-    public float[][] frustumData;
-    public float[] projectionMatrix;
-    public float[] modelViewMatrix;
-    public float[] clip;
-
-    public FrustumData()
-    {
-        frustumData = new float[16][16];
-        projectionMatrix = new float[16];
-        modelViewMatrix = new float[16];
-        clip = new float[16];
-    }
-
-    public boolean cubeInFrustum(double x0, double y0, double z0, double x1, double y1, double z1)
-    {
-        for(int i = 0; i < 6; i++)
-        {
-            if((double) frustumData[i][0] * x0 + (double) frustumData[i][1] * y0 + (double) frustumData[i][2] * z0 + (double) frustumData[i][3] <= 0.0D &&
-                (double) frustumData[i][0] * x1 + (double) frustumData[i][1] * y0 + (double) frustumData[i][2] * z0 + (double) frustumData[i][3] <= 0.0D &&
-                (double) frustumData[i][0] * x0 + (double) frustumData[i][1] * y1 + (double) frustumData[i][2] * z0 + (double) frustumData[i][3] <= 0.0D &&
-                (double) frustumData[i][0] * x1 + (double) frustumData[i][1] * y1 + (double) frustumData[i][2] * z0 + (double) frustumData[i][3] <= 0.0D &&
-                (double) frustumData[i][0] * x0 + (double) frustumData[i][1] * y0 + (double) frustumData[i][2] * z1 + (double) frustumData[i][3] <= 0.0D &&
-                (double) frustumData[i][0] * x1 + (double) frustumData[i][1] * y0 + (double) frustumData[i][2] * z1 + (double) frustumData[i][3] <= 0.0D &&
-                (double) frustumData[i][0] * x0 + (double) frustumData[i][1] * y1 + (double) frustumData[i][2] * z1 + (double) frustumData[i][3] <= 0.0D &&
-                (double) frustumData[i][0] * x1 + (double) frustumData[i][1] * y1 + (double) frustumData[i][2] * z1 + (double) frustumData[i][3] <= 0.0D)
-            {
-                return false;
-            }
-        }
-
-        return true;
-    }
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/culling/IsometricCameraFrustum.java b/game/client/src/main/java/net/minecraft/client/render/culling/IsometricCameraFrustum.java
deleted file mode 100644
index e554ab3b3..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/culling/IsometricCameraFrustum.java
+++ /dev/null
@@ -1,26 +0,0 @@
-package net.minecraft.client.render.culling;
-
-import net.minecraft.client.render.camera.ICamera;
-import org.jetbrains.annotations.NotNull;
-import org.joml.primitives.AABBdc;
-
-public class IsometricCameraFrustum
-        extends CameraFrustum
-{
-    public IsometricCameraFrustum(ICamera camera)
-    {
-        super(camera);
-    }
-
-    @Override
-    public boolean cubeInFrustum(double x0, double y0, double z0, double x1, double y1, double z1, float partialTick)
-    {
-        return true;
-    }
-
-    @Override
-    public boolean isVisible(@NotNull AABBdc aabb, float partialTick)
-    {
-        return true;
-    }
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRenderer.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRenderer.java
index 0d39a788f..b0922931b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRenderer.java
@@ -1,20 +1,24 @@
 package net.minecraft.client.render.entity;
 
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.entity.EntityDispatcher;
 import net.minecraft.core.util.collection.NamespaceID;
 import org.jetbrains.annotations.NotNull;
+import org.joml.Math;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
 
-import net.minecraft.client.render.EntityRenderDispatcher;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import net.minecraft.client.render.ImageParser;
 import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.Global;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.entity.Entity;
@@ -29,7 +33,7 @@ import java.util.Map;
 public abstract class EntityRenderer<T extends Entity> {
     public static boolean renderShadows = true;
     private final @NotNull Map<@NotNull String, @NotNull StaticEntityModel> modelMap = new HashMap<>();
-    protected EntityRenderDispatcher renderDispatcher = null;
+    protected EntityRendererDispatcher renderDispatcher = null;
     protected Class<? extends T> appliedClass = null;
 
     private float shadowSize;
@@ -48,10 +52,10 @@ public abstract class EntityRenderer<T extends Entity> {
         return this.shadowSize;
     }
 
-    public abstract void render(@NotNull Tessellator tessellator, @NotNull T entity, double x, double y, double z,
+    public abstract void render(@NotNull TessellatorGeneral tessellator, @NotNull T entity, double x, double y, double z,
                                 float yaw, float partialTick);
 
-    public void renderPreview(@NotNull final Tessellator tessellator, @NotNull final T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+    public void renderPreview(@NotNull final TessellatorGeneral tessellator, @NotNull final T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
         render(tessellator, entity, x, y, z, yaw, partialTick);
     }
 
@@ -69,7 +73,7 @@ public abstract class EntityRenderer<T extends Entity> {
         if (model != null) {
             return model;
         }
-        EntityDispatcher.EntityDispatcherEntry entry = EntityDispatcher.getInstance().entryForClass(this.appliedClass);
+        EntityDispatcher.EntityDispatcherEntry<? extends T> entry = EntityDispatcher.getInstance().entryForClass(this.appliedClass);
         final NamespaceID id = entry != null ? entry.namespaceID : null;
         if (id != null) {
             model = EntityGeometryMojangData.Cache.getModelForEntity(id, localId);
@@ -88,26 +92,24 @@ public abstract class EntityRenderer<T extends Entity> {
     public void onWorldChanged(final @NotNull World world) {
     }
 
-    private void renderFire(final @NotNull Tessellator tessellator, final @NotNull T entity, final double x, final double y, final double z, final float partialTick) {
-        GL11.glDisable(GL11.GL_LIGHTING);
+    private void renderFire(final @NotNull TessellatorGeneral tessellator, final @NotNull T entity, final double x, final double y, final double z, final float partialTick) {
+        GLRenderer.globalSetLightEnabled(false);
         final IconCoordinate texture = TextureRegistry.getTexture("minecraft:block/fire");
         texture.parentAtlas.bind();
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float) x, (float) y, (float) z);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
         final float f9 = entity.bbWidth * 1.4F;
-        GL11.glScalef(f9, f9, f9);
+        GLRenderer.modelM4f().scale(f9, f9, f9);
         float f10 = 0.5F;
         final float f11 = 0.0F;
         float f12 = entity.bbHeight;
         float f13 = (float) (entity.y - entity.bb.minY);
-        GL11.glRotatef(-this.renderDispatcher.viewLerpYaw, 0.0F, 1.0F, 0.0F);
-        GL11.glTranslatef(0.0F, 0.0F, -0.3F + (float) (int) f12 * 0.02F);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        if (LightmapHelper.isLightmapEnabled()) {
-            int lightmapCoord = entity.getLightmap(partialTick);
-            lightmapCoord = LightmapHelper.setBlocklightValue(lightmapCoord, 15);
-            LightmapHelper.setLightmapCoord(lightmapCoord);
-        }
+        GLRenderer.modelM4f().rotateY(Math.toRadians(-this.renderDispatcher.viewLerpYaw));
+        GLRenderer.modelM4f().translate(0.0F, 0.0F, -0.3F + (float) (int) f12 * 0.02F);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        int lightmapCoord = entity.getLightmap(partialTick);
+        lightmapCoord = LightmapHelper.setBlocklightValue(lightmapCoord, 15);
+        GLRenderer.setLightmapCoord1i(lightmapCoord);
         float f14 = 0.0F;
         int l = 0;
         tessellator.startDrawingQuads();
@@ -132,18 +134,18 @@ public abstract class EntityRenderer<T extends Entity> {
             l++;
         }
         tessellator.draw();
-        GL11.glPopMatrix();
-        GL11.glEnable(GL11.GL_LIGHTING);
+        GLRenderer.popFrame();
+        GLRenderer.globalSetLightEnabled(true);
     }
 
-    private void renderShadow(final @NotNull Tessellator tessellator, @NotNull final T entity, final double posX, final double posY, final double posZ,
+    private void renderShadow(final @NotNull TessellatorGeneral tessellator, @NotNull final T entity, final double posX, final double posY, final double posZ,
                               final float opacity, final float partialTick) {
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         final TextureManager textureManager = this.renderDispatcher.textureManager;
         textureManager.bindTexture(textureManager.loadTexture("/assets/minecraft/textures/misc/shadow.png"));
         final World world = entity.world;
-        GL11.glDepthMask(false);
+        GLRenderer.setDepthMask(false);
         final double lerpX = entity.xo + (entity.x - entity.xo) * (double) partialTick;
         final double lerpY = entity.yo + (entity.y - entity.yo) * (double) partialTick + (double) entity.getShadowHeightOffs();
         final double lerpZ = entity.zo + (entity.z - entity.zo) * (double) partialTick;
@@ -174,12 +176,12 @@ public abstract class EntityRenderer<T extends Entity> {
         }
 
         tessellator.draw();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glDepthMask(true);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.setDepthMask(true);
     }
 
-    private void renderShadowOnBlock(final @NotNull Tessellator tessellator, final @NotNull T entity, final @NotNull Block<?> block, final double d, final double d1, final double d2,
+    private void renderShadowOnBlock(final @NotNull TessellatorGeneral tessellator, final @NotNull T entity, final @NotNull Block<?> block, final double d, final double d1, final double d2,
                                      final int x, final int y, final int z, final float opacity, final float size, final double xo,
                                      final double yo, final double zo) {
         if (!block.isCubeShaped()) {
@@ -194,7 +196,7 @@ public abstract class EntityRenderer<T extends Entity> {
         if (alpha > 1.0D) {
             alpha = 1.0D;
         }
-        tessellator.setColorRGBA_F(1.0F, 1.0F, 1.0F, (float) alpha);
+        tessellator.setColor4f(1.0F, 1.0F, 1.0F, (float) alpha);
         final AABBdc aabb = block.getCollisionBoundingBoxFromPool(entity.world, x, y, z);
         if (aabb == null) {
             return;
@@ -214,9 +216,10 @@ public abstract class EntityRenderer<T extends Entity> {
         tessellator.addVertexWithUV(xMax, yMin, zMin, f3, f4);
     }
 
-    public static void renderOffsetAABB(final @NotNull Tessellator tessellator, final @NotNull AABBdc aabb, final double x, final double y, final double z) {
-        GL11.glDisable(GL11.GL_TEXTURE_2D);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+    public static void renderOffsetAABB(final @NotNull TessellatorGeneral tessellator, final @NotNull AABBdc aabb, final double x, final double y, final double z) {
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         tessellator.startDrawingQuads();
         tessellator.setTranslation(x, y, z);
         tessellator.setNormal(0.0F, 0.0F, -1F);
@@ -251,11 +254,11 @@ public abstract class EntityRenderer<T extends Entity> {
         tessellator.addVertex(aabb.maxX(), aabb.minY(), aabb.maxZ());
         tessellator.setTranslation(0.0D, 0.0D, 0.0D);
         tessellator.draw();
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
+        GLRenderer.popFrame();
     }
 
     public static void renderFlatAABB(final @NotNull AABBdc aabb) {
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
         tessellator.addVertex(aabb.minX(), aabb.maxY(), aabb.minZ());
         tessellator.addVertex(aabb.maxX(), aabb.maxY(), aabb.minZ());
@@ -289,12 +292,12 @@ public abstract class EntityRenderer<T extends Entity> {
         tessellator.draw();
     }
 
-    public void init(@NotNull final Class<? extends T> appliedClass, final @NotNull EntityRenderDispatcher dispatcher) {
+    public void init(@NotNull final Class<? extends T> appliedClass, final @NotNull EntityRendererDispatcher dispatcher) {
         this.renderDispatcher = dispatcher;
         this.appliedClass = appliedClass;
     }
 
-    public void postRender(final @NotNull Tessellator tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+    public void postRender(final @NotNull TessellatorGeneral tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
         if (renderShadows && this.renderDispatcher.settings.fancyGraphics.value == 1 && getShadowSize(entity) > 0.0F) {
             final double distance = this.renderDispatcher.distanceToLerpSquared(entity.x, entity.y, entity.z);
             final float opacity = (float) ((1.0D - distance / 256D) * (double) this.shadowOpacity);
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererArrow.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererArrow.java
index 7998bd015..bf99e95e6 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererArrow.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererArrow.java
@@ -1,48 +1,47 @@
 package net.minecraft.client.render.entity;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.projectile.ProjectileArrow;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 
-public class EntityRendererArrow extends EntityRenderer<ProjectileArrow>
-{
+public class EntityRendererArrow extends EntityRenderer<ProjectileArrow> {
     @Override
-    public void render(@NotNull Tessellator tessellator, @NotNull ProjectileArrow arrow, double x, double y, double z,
+    public void render(@NotNull TessellatorGeneral tessellator, @NotNull ProjectileArrow arrow, double x, double y, double z,
                        float yaw, float partialTick) {
         bindTexture("/assets/minecraft/textures/entity/arrows.png");
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float)x, (float)y, (float)z);
-        GL11.glRotatef((arrow.yRotO + (arrow.yRot - arrow.yRotO) * partialTick) - 90F, 0.0F, 1.0F, 0.0F);
-        GL11.glRotatef(arrow.xRotO + (arrow.xRot - arrow.xRotO) * partialTick, 0.0F, 0.0F, 1.0F);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+
+        GLRenderer.modelM4f().rotateY(Math.toRadians(Math.lerp(arrow.yRotO, arrow.yRot, partialTick) - 90F));
+        GLRenderer.modelM4f().rotateZ(Math.toRadians(Math.lerp(arrow.xRotO, arrow.xRot, partialTick)));
 
         int arrowType = arrow.getArrowType();
 
         float bodyMinU = 0F / 32F;
         float bodyMaxU = 16F / 32F;
-        float bodyMinV = (float)(arrowType * 10) / 32F;
-        float bodyMaxV = (float)(5 + arrowType * 10) / 32F;
+        float bodyMinV = (float) (arrowType * 10) / 32F;
+        float bodyMaxV = (float) (5 + arrowType * 10) / 32F;
         float tailMinU = 0F / 32F;
         float tailMaxU = 5F / 32F;
-        float tailMinV = (float)(5 + arrowType * 10) / 32F;
-        float tailMaxV = (float)(10 + arrowType * 10) / 32F;
+        float tailMinV = (float) (5 + arrowType * 10) / 32F;
+        float tailMaxV = (float) (10 + arrowType * 10) / 32F;
         float scale = 9F / 160F;
 
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        float shakeAmount = (float)arrow.shake - partialTick;
-        if(shakeAmount > 0.0F)
-        {
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        float shakeAmount = (float) arrow.shake - partialTick;
+        if (shakeAmount > 0.0F) {
             float shakeAngle = -MathHelper.sin(shakeAmount * 3F) * shakeAmount;
-            GL11.glRotatef(shakeAngle, 0.0F, 0.0F, 1.0F);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(shakeAngle));
         }
 
         // Set up arrow transformation
-        GL11.glRotatef(45F, 1.0F, 0.0F, 0.0F);
-        GL11.glScalef(scale, scale, scale);
-        GL11.glTranslatef(-4F, 0.0F, 0.0F);
-        GL11.glNormal3f(scale, 0.0F, 0.0F);
+        GLRenderer.modelM4f().rotateX(Math.toRadians(45f));
+        GLRenderer.modelM4f().scale(scale, scale, scale);
+        GLRenderer.modelM4f().translate(-4F, 0.0F, 0.0F);
+//        GL11.glNormal3f(scale, 0.0F, 0.0F);
 
         // Draw arrow tail
         tessellator.startDrawingQuads();
@@ -51,7 +50,7 @@ public class EntityRendererArrow extends EntityRenderer<ProjectileArrow>
         tessellator.addVertexWithUV(-7D, 2D, 2D, tailMaxU, tailMaxV);
         tessellator.addVertexWithUV(-7D, 2D, -2D, tailMinU, tailMaxV);
         tessellator.draw();
-        GL11.glNormal3f(-scale, 0.0F, 0.0F);
+//        GL11.glNormal3f(-scale, 0.0F, 0.0F);
         tessellator.startDrawingQuads();
         tessellator.addVertexWithUV(-7D, 2D, -2D, tailMinU, tailMinV);
         tessellator.addVertexWithUV(-7D, 2D, 2D, tailMaxU, tailMinV);
@@ -60,10 +59,9 @@ public class EntityRendererArrow extends EntityRenderer<ProjectileArrow>
         tessellator.draw();
 
         // Draw arrow body
-        for(int i = 0; i < 4; i++)
-        {
-            GL11.glRotatef(90F, 1.0F, 0.0F, 0.0F);
-            GL11.glNormal3f(0.0F, 0.0F, scale);
+        for (int i = 0; i < 4; i++) {
+            GLRenderer.modelM4f().rotateX(Math.PI_OVER_2_f);
+//            GL11.glNormal3f(0.0F, 0.0F, scale);
             tessellator.startDrawingQuads();
             tessellator.addVertexWithUV(-8D, -2D, 0.0D, bodyMinU, bodyMinV);
             tessellator.addVertexWithUV(8D, -2D, 0.0D, bodyMaxU, bodyMinV);
@@ -72,7 +70,7 @@ public class EntityRendererArrow extends EntityRenderer<ProjectileArrow>
             tessellator.draw();
         }
 
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
-        GL11.glPopMatrix();
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.popFrame();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererBoat.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererBoat.java
index b7349c67c..06c83cbdc 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererBoat.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererBoat.java
@@ -2,8 +2,9 @@ package net.minecraft.client.render.entity;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.TileEntityRenderDispatcher;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.tileentity.TileEntityRendererFlag;
 import net.minecraft.core.block.entity.TileEntityFlag;
 import net.minecraft.core.entity.vehicle.EntityBoat;
@@ -11,11 +12,9 @@ import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
 import net.minecraft.core.world.wind.WindProvider;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 
-public class EntityRendererBoat extends EntityRenderer<EntityBoat>
-{
+public class EntityRendererBoat extends EntityRenderer<EntityBoat> {
 
     private final TileEntityRendererFlag flagRenderer;
     private final Minecraft mc = Minecraft.getMinecraft();
@@ -26,25 +25,21 @@ public class EntityRendererBoat extends EntityRenderer<EntityBoat>
     }
 
     @Override
-    public void render(@NotNull final Tessellator tessellator, @NotNull final EntityBoat entity, final double x, final double y, final double z,
-                       final float yaw, final float partialTick)
-    {
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float)x, (float)y, (float)z);
-        GL11.glRotatef(180F - yaw, 0.0F, 1.0F, 0.0F);
-        final float hurt = (float)entity.boatTimeSinceHit - partialTick;
-        float dmg = (float)entity.boatCurrentDamage - partialTick;
-        if(dmg < 0.0F)
-        {
+    public void render(@NotNull final TessellatorGeneral tessellator, @NotNull final EntityBoat entity, final double x, final double y, final double z,
+                       final float yaw, final float partialTick) {
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(180F - yaw));
+        final float hurt = (float) entity.boatTimeSinceHit - partialTick;
+        float dmg = (float) entity.boatCurrentDamage - partialTick;
+        if (dmg < 0.0F) {
             dmg = 0.0F;
         }
-        if(hurt > 0.0F)
-        {
-            GL11.glRotatef(((MathHelper.sin(hurt) * hurt * dmg) / 10F) * (float)entity.boatRockDirection, 1.0F, 0.0F, 0.0F);
+        if (hurt > 0.0F) {
+            GLRenderer.modelM4f().rotateX(Math.toRadians(((MathHelper.sin(hurt) * hurt * dmg) / 10F) * (float) entity.boatRockDirection));
         }
-        if (entity.tileEntityFlag != null)
-        {
+        if (entity.tileEntityFlag != null) {
             final World theWorld = this.mc.currentWorld;
             final WindProvider theWind = theWorld.getWorldType().getWindManager();
 
@@ -54,19 +49,19 @@ public class EntityRendererBoat extends EntityRenderer<EntityBoat>
             // If boat speed is 0, windAngle is 100% and boatAngle is 0%
             // If boat speed is > 3, windAngle is 0% and boatAngle is 100%
             final float boatSpeed = MathHelper.sqrt_float((float) (entity.xd * entity.xd + entity.zd * entity.zd));
-            final float angle = MathHelper.lerp(windAngle, boatAngle, (float)MathHelper.clamp(boatSpeed, 0, 0.25) * 4);
+            final float angle = MathHelper.lerp(windAngle, boatAngle, (float) MathHelper.clamp(boatSpeed, 0, 0.25) * 4);
 
             this.flagRenderer.doRender(tessellator, entity.tileEntityFlag, -1.19, 0.187, -0.5, partialTick, false, angle, 1.0f);
         }
-        TextureRegistry.blockAtlas.bind();
+        TextureRegistry.worldAtlas.bind();
         final float f4 = 0.75F;
-        GL11.glScalef(f4, f4, f4);
-        GL11.glScalef(1.0F / f4, 1.0F / f4, 1.0F / f4);
+        GLRenderer.modelM4f().scale(f4, f4, f4);
+        GLRenderer.modelM4f().scale(1.0F / f4, 1.0F / f4, 1.0F / f4);
         bindTexture("/assets/minecraft/textures/entity/boat.png");
-        GL11.glScalef(1/16f, 1/16f, -1/16f);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        getModel("main").render(tessellator);
-        GL11.glPopMatrix();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.modelM4f().scale(1 / 16f, 1 / 16f, -1 / 16f);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        getModel("main").render();
+        GLRenderer.popFrame();
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererCannonball.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererCannonball.java
index 4210664ab..bb218c880 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererCannonball.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererCannonball.java
@@ -1,25 +1,25 @@
 package net.minecraft.client.render.entity;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.projectile.ProjectileCannonball;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
+import org.joml.Math;
 
-public class EntityRendererCannonball extends EntityRenderer<ProjectileCannonball>
-{
+public class EntityRendererCannonball extends EntityRenderer<ProjectileCannonball> {
 
     public EntityRendererCannonball() {
         super();
     }
 
     @Override
-    public void render(@NotNull final Tessellator tessellator, @NotNull final ProjectileCannonball entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float)x, (float)y, (float)z);
-        GL11.glRotatef(yaw, 0.0F, 1.0F, 0.0F);
+    public void render(@NotNull final TessellatorGeneral tessellator, @NotNull final ProjectileCannonball entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(yaw));
         bindTexture("/assets/minecraft/textures/entity/cannonball.png");
-        GL11.glScalef(1/MobRenderer.ENTITY_RENDER_SCALE, 1/MobRenderer.ENTITY_RENDER_SCALE, -1/MobRenderer.ENTITY_RENDER_SCALE);
-        getModel("main").render(tessellator);
-        GL11.glPopMatrix();
+        GLRenderer.modelM4f().scale(1 / MobRenderer.ENTITY_RENDER_SCALE, 1 / MobRenderer.ENTITY_RENDER_SCALE, -1 / MobRenderer.ENTITY_RENDER_SCALE);
+        getModel("main").render();
+        GLRenderer.popFrame();
     }
 }
\ No newline at end of file
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererDefault.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererDefault.java
index 41592bc9b..37458f6e3 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererDefault.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererDefault.java
@@ -1,16 +1,16 @@
 package net.minecraft.client.render.entity;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 public class EntityRendererDefault extends EntityRenderer<Entity> {
     @Override
-    public void render(@NotNull final Tessellator tessellator, @NotNull final Entity entity, final double x, final double y, final double z,
+    public void render(@NotNull final TessellatorGeneral tessellator, @NotNull final Entity entity, final double x, final double y, final double z,
                        final float yaw, final float partialTick) {
-        GL11.glPushMatrix();
+        GLRenderer.pushFrame();
         renderOffsetAABB(tessellator, entity.bb, x - entity.xo, y - entity.yo, z - entity.zo);
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererFallingBlock.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererFallingBlock.java
index 5a3948fa2..0bc021248 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererFallingBlock.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererFallingBlock.java
@@ -4,48 +4,46 @@ import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.TileEntityRenderDispatcher;
 import net.minecraft.client.render.Lighting;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.tileentity.TileEntityRenderer;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.block.entity.TileEntity;
 import net.minecraft.core.entity.EntityFallingBlock;
 import net.minecraft.core.world.BlocksContainer;
 import net.minecraft.core.world.pos.TilePos;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
-public class EntityRendererFallingBlock extends EntityRenderer<EntityFallingBlock>
-{
+public class EntityRendererFallingBlock extends EntityRenderer<EntityFallingBlock> {
     private final Minecraft mc;
     private BlocksContainer container = null;
 
 
-    public EntityRendererFallingBlock()
-    {
+    public EntityRendererFallingBlock() {
         super(0.5f);
         this.mc = Minecraft.getMinecraft();
     }
 
     @Override
-    public void render(@NotNull Tessellator tessellator, @NotNull EntityFallingBlock fallingBlock, double x, double y, double z, float yaw, float partialTick) {
+    public void render(@NotNull TessellatorGeneral tessellator, @NotNull EntityFallingBlock fallingBlock, double x, double y, double z, float yaw, float partialTick) {
         if (this.container == null || this.container.world != fallingBlock.world) {
             this.container = new BlocksContainer(fallingBlock.world);
         }
-        GL11.glPushMatrix();
-        GL11.glTranslated(x, y, z);
-        TextureRegistry.blockAtlas.bind();
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+        TextureRegistry.worldAtlas.bind();
         Lighting.disable();
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glDisable(GL11.GL_CULL_FACE);
-        if(this.mc.isAmbientOcclusionEnabled())
-        {
-            GL11.glShadeModel(GL11.GL_SMOOTH);
-        } else
-        {
-            GL11.glShadeModel(GL11.GL_FLAT);
-        }
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.disableState(State.CULL_FACE);
+//        if (this.mc.isAmbientOcclusionEnabled()) {
+//            GL11.glShadeModel(GL11.GL_SMOOTH);
+//        } else {
+//            GL11.glShadeModel(GL11.GL_FLAT);
+//        }
 
         TilePos blockPos = new TilePos(fallingBlock);
 
@@ -54,7 +52,7 @@ public class EntityRendererFallingBlock extends EntityRenderer<EntityFallingBloc
 
         this.container.setLightReferenceEntity(fallingBlock);
         this.container.setBlock(blockPos.x, blockPos.y, blockPos.z, fallingBlock.carriedBlock.blockId, fallingBlock.carriedBlock.metadata, fallingBlock.carriedBlock.entity);
-        BlockModelDispatcher.getInstance().getDispatch(Blocks.getBlock(fallingBlock.carriedBlock.blockId)).renderNoCulling(Tessellator.instance, this.container, blockPos);
+        BlockModelDispatcher.getInstance().getDispatch(Blocks.getBlock(fallingBlock.carriedBlock.blockId)).renderNoCulling(GLRenderer.getTessellator(), this.container, blockPos);
         this.container.setLightReferenceEntity(null);
         this.container.clear();
 
@@ -62,13 +60,13 @@ public class EntityRendererFallingBlock extends EntityRenderer<EntityFallingBloc
         tessellator.draw();
 
         Lighting.enableLight();
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
 
         TileEntityRenderer<TileEntity> renderer = TileEntityRenderDispatcher.instance.getRenderer(fallingBlock.carriedBlock.entity);
         if (renderer != null) {
-            GL11.glPushMatrix();
+            GLRenderer.pushFrame();
             renderer.doRender(tessellator, fallingBlock.carriedBlock.entity, x - 0.5, y - 0.5, z - 0.5, partialTick);
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererFishingBobber.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererFishingBobber.java
index 58317c50e..01795afdd 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererFishingBobber.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererFishingBobber.java
@@ -1,7 +1,9 @@
 package net.minecraft.client.render.entity;
 
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.EntityFishingBobber;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
@@ -15,7 +17,7 @@ public class EntityRendererFishingBobber extends EntityRendererSprite<EntityFish
     }
 
     @Override
-    public void render(@NotNull Tessellator tessellator, @NotNull EntityFishingBobber entity, double x, double y, double z, float yaw, float partialTick) {
+    public void render(@NotNull TessellatorGeneral tessellator, @NotNull EntityFishingBobber entity, double x, double y, double z, float yaw, float partialTick) {
         super.render(tessellator, entity, x, y, z, yaw, partialTick);
         if (entity.owner != null) {
             int handedNess = entity.owner.isLeftHanded() ? -1 : 1;
@@ -44,16 +46,16 @@ public class EntityRendererFishingBobber extends EntityRendererSprite<EntityFish
             double ya = (float) (yp - yh);
             double za = (float) (zp - zh);
             GL11.glDisable(GL11.GL_TEXTURE_2D);
-            GL11.glDisable(GL11.GL_LIGHTING);
-            tessellator.startDrawing(3);
-            tessellator.setColorOpaque_I(0);
+            GLRenderer.globalSetLightEnabled(false);
+            tessellator.startDrawing(DrawMode.LINE_STRIP);
+            tessellator.setColorOpaque1i(0);
             for (int i = 0, steps = 16; i <= steps; i++) {
                 final float aa = (float) i / (float) steps;
                 tessellator.addVertex(x + xa * (double) aa, y + ya * (double) (aa * aa + aa) * 0.5D + 0.25D, z + za * (double) aa);
             }
 
             tessellator.draw();
-            GL11.glEnable(GL11.GL_LIGHTING);
+            GLRenderer.globalSetLightEnabled(true);
             GL11.glEnable(GL11.GL_TEXTURE_2D);
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererGeneric.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererGeneric.java
index 62aa77466..2b6397bc3 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererGeneric.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererGeneric.java
@@ -1,24 +1,26 @@
 package net.minecraft.client.render.entity;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
-public class EntityRendererGeneric<T extends Entity> extends EntityRenderer<T>{
+public class EntityRendererGeneric<T extends Entity> extends EntityRenderer<T> {
     public final @NotNull StaticEntityModel entityModel;
+
     public EntityRendererGeneric(final @NotNull StaticEntityModel entityModel, final float shadowSize) {
         super(shadowSize);
         this.entityModel = entityModel;
     }
+
     @Override
-    public void render(final @NotNull Tessellator tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        GL11.glPushMatrix();
+    public void render(final @NotNull TessellatorGeneral tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+        GLRenderer.pushFrame();
         bindTexture("/assets/minecraft/textures/entity/creeper/0.png");
-        GL11.glTranslated(x, y, z);
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
         this.entityModel.resetBones();
-        this.entityModel.render(tessellator);
-        GL11.glPopMatrix();
+        this.entityModel.render();
+        GLRenderer.popFrame();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererItem.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererItem.java
index c9861e379..58e1e346d 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererItem.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererItem.java
@@ -1,56 +1,43 @@
 package net.minecraft.client.render.entity;
 
 import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.entity.EntityItem;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
-
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.item.Item;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.util.helper.MathHelper;
 
-import static org.lwjgl.opengl.GL11.glPushMatrix;
-
-public class EntityRendererItem extends EntityRenderer<EntityItem>
-{
-
+public class EntityRendererItem extends EntityRenderer<EntityItem> {
 
-	public EntityRendererItem() {
-		super(0.15f);
-		shadowOpacity = 0.75F;
-	}
+    public EntityRendererItem() {
+        super(0.15f);
+        this.shadowOpacity = 0.75F;
+    }
 
-	public void render(@NotNull Tessellator tessellator, final @NotNull EntityItem entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
-		float brightness = 1.0f;
-		if(!LightmapHelper.isLightmapEnabled()) {
-			brightness = entity.getBrightness(partialTick);
-		}
-		final ItemStack itemstack = entity.item;
-		if(itemstack == null) {
-			return;
-		}
-		Item item = itemstack.getItem();
-		if(item == null) {
-			return;
-		}
-		glPushMatrix();
-		final float bobbingOffset = MathHelper.sin((entity.age + partialTick) / 10F + entity.bobOffset) * 0.1F + 0.1F;
-		final float yw = (float) Math.toDegrees(((entity.age + partialTick) / 20F + entity.bobOffset));
-		byte renderCount = 1;
-		if (entity.item.stackSize > 1) {
-			renderCount = 2;
-		}
-		if (entity.item.stackSize > 5) {
-			renderCount = 3;
-		}
-		if (entity.item.stackSize > 20) {
-			renderCount = 4;
-		}
-		GL11.glTranslated(x, y + bobbingOffset, z);
-		ItemModelDispatcher.getInstance().getDispatch(item).renderItemEntity(tessellator, itemstack, Minecraft.getMinecraft().gameSettings.items3D.value, renderCount, entity.age, yw, brightness, 1f, partialTick);
-		GL11.glPopMatrix();
-	}
+    public void render(@NotNull TessellatorGeneral tessellator, final @NotNull EntityItem entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+        final ItemStack itemstack = entity.item;
+        if (itemstack == null) {
+            return;
+        }
+        Item item = itemstack.getItem();
+        GLRenderer.pushFrame();
+        final float bobbingOffset = MathHelper.sin((entity.age + partialTick) / 10F + entity.bobOffset) * 0.1F + 0.1F;
+        final float yw = (float) Math.toDegrees(((entity.age + partialTick) / 20F + entity.bobOffset));
+        byte renderCount = 1;
+        if (entity.item.stackSize > 1) {
+            renderCount = 2;
+        }
+        if (entity.item.stackSize > 5) {
+            renderCount = 3;
+        }
+        if (entity.item.stackSize > 20) {
+            renderCount = 4;
+        }
+        GLRenderer.modelM4f().translate((float) x, (float) (y + bobbingOffset), (float) z);
+        ItemModelDispatcher.getInstance().getDispatch(item).renderItemEntity(tessellator, itemstack, Minecraft.getMinecraft().gameSettings.items3D.value, renderCount, entity.age, yw, entity.getLightmap(partialTick), partialTick);
+        GLRenderer.popFrame();
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererLightningBolt.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererLightningBolt.java
index 75c6ff44a..ad6a23eae 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererLightningBolt.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererLightningBolt.java
@@ -2,106 +2,92 @@ package net.minecraft.client.render.entity;
 
 import java.util.Random;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.EntityLightning;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.opengl.GL11;
 
-public class EntityRendererLightningBolt extends EntityRenderer<EntityLightning>
-{
+public class EntityRendererLightningBolt extends EntityRenderer<EntityLightning> {
 
-    public EntityRendererLightningBolt()
-    {
+    public EntityRendererLightningBolt() {
     }
 
     @Override
-    public void render(@NotNull Tessellator tessellator, @NotNull EntityLightning lightning, double x, double y, double z,
-                       float yaw, float partialTick)
-    {
+    public void render(@NotNull TessellatorGeneral tessellator, @NotNull EntityLightning lightning, double x, double y, double z,
+                       float yaw, float partialTick) {
         GL11.glDisable(GL11.GL_TEXTURE_2D);
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glEnable(GL11.GL_BLEND);
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.enableState(State.BLEND);
         GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE);
         double ad[] = new double[8];
         double ad1[] = new double[8];
         double d3 = 0.0D;
         double d4 = 0.0D;
         Random random = new Random(lightning.seed);
-        for(int j = 7; j >= 0; j--)
-        {
+        for (int j = 7; j >= 0; j--) {
             ad[j] = d3;
             ad1[j] = d4;
             d3 += random.nextInt(11) - 5;
             d4 += random.nextInt(11) - 5;
         }
 
-        for(int i = 0; i < 4; i++)
-        {
+        for (int i = 0; i < 4; i++) {
             random.setSeed(lightning.seed);
-            for(int k = 0; k < 3; k++)
-            {
+            for (int k = 0; k < 3; k++) {
                 int l = 7;
                 int i1 = 0;
-                if(k > 0)
-                {
+                if (k > 0) {
                     l = 7 - k;
                 }
-                if(k > 0)
-                {
+                if (k > 0) {
                     i1 = l - 2;
                 }
                 double d5 = ad[l] - d3;
                 double d6 = ad1[l] - d4;
-                for(int j1 = l; j1 >= i1; j1--)
-                {
+                for (int j1 = l; j1 >= i1; j1--) {
                     double d7 = d5;
                     double d8 = d6;
-                    if(k == 0)
-                    {
+                    if (k == 0) {
                         d5 += random.nextInt(11) - 5;
                         d6 += random.nextInt(11) - 5;
-                    } else
-                    {
+                    } else {
                         d5 += random.nextInt(31) - 15;
                         d6 += random.nextInt(31) - 15;
                     }
-                    tessellator.startDrawing(5);
+                    tessellator.startDrawing(DrawMode.TRIANGLE_STRIP);
                     float f2 = 0.5F;
-                    tessellator.setColorRGBA_F(0.9F * f2, 0.9F * f2, 1.0F * f2, 0.3F);
-                    double d9 = 0.1D + (double)i * 0.2D;
-                    if(k == 0)
-                    {
-                        d9 *= (double)j1 * 0.1D + 1.0D;
+                    tessellator.setColor4f(0.9F * f2, 0.9F * f2, 1.0F * f2, 0.3F);
+                    double d9 = 0.1D + (double) i * 0.2D;
+                    if (k == 0) {
+                        d9 *= (double) j1 * 0.1D + 1.0D;
                     }
-                    double d10 = 0.1D + (double)i * 0.2D;
-                    if(k == 0)
-                    {
-                        d10 *= (double)(j1 - 1) * 0.1D + 1.0D;
+                    double d10 = 0.1D + (double) i * 0.2D;
+                    if (k == 0) {
+                        d10 *= (double) (j1 - 1) * 0.1D + 1.0D;
                     }
-                    for(int k1 = 0; k1 < 5; k1++)
-                    {
+                    for (int k1 = 0; k1 < 5; k1++) {
                         double d11 = (x + 0.5D) - d9;
                         double d12 = (z + 0.5D) - d9;
-                        if(k1 == 1 || k1 == 2)
-                        {
+                        if (k1 == 1 || k1 == 2) {
                             d11 += d9 * 2D;
                         }
-                        if(k1 == 2 || k1 == 3)
-                        {
+                        if (k1 == 2 || k1 == 3) {
                             d12 += d9 * 2D;
                         }
                         double d13 = (x + 0.5D) - d10;
                         double d14 = (z + 0.5D) - d10;
-                        if(k1 == 1 || k1 == 2)
-                        {
+                        if (k1 == 1 || k1 == 2) {
                             d13 += d10 * 2D;
                         }
-                        if(k1 == 2 || k1 == 3)
-                        {
+                        if (k1 == 2 || k1 == 3) {
                             d14 += d10 * 2D;
                         }
-                        tessellator.addVertex(d13 + d5, y + (double)(j1 * 16), d14 + d6);
-                        tessellator.addVertex(d11 + d7, y + (double)((j1 + 1) * 16), d12 + d8);
+                        tessellator.addVertex(d13 + d5, y + (double) (j1 * 16), d14 + d6);
+                        tessellator.addVertex(d11 + d7, y + (double) ((j1 + 1) * 16), d12 + d8);
                     }
 
                     tessellator.draw();
@@ -111,9 +97,9 @@ public class EntityRendererLightningBolt extends EntityRenderer<EntityLightning>
 
         }
 
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glEnable(GL11.GL_LIGHTING);
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.globalSetLightEnabled(true);
         GL11.glEnable(GL11.GL_TEXTURE_2D);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererMinecart.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererMinecart.java
index 639b54edf..7a37bb233 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererMinecart.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererMinecart.java
@@ -1,19 +1,18 @@
 package net.minecraft.client.render.entity;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.Blocks;
-import net.minecraft.core.Global;
 import net.minecraft.core.entity.vehicle.EntityMinecart;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.joml.Vector3d;
 import org.joml.Vector3dc;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 
 public class EntityRendererMinecart extends EntityRenderer<EntityMinecart> {
     public EntityRendererMinecart() {
@@ -21,9 +20,9 @@ public class EntityRendererMinecart extends EntityRenderer<EntityMinecart> {
     }
 
     @Override
-    public void render(@NotNull final Tessellator tessellator, @NotNull final EntityMinecart minecart, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glPushMatrix();
+    public void render(@NotNull final TessellatorGeneral tessellator, @NotNull final EntityMinecart minecart, final double x, final double y, final double z, final float yaw, final float partialTick) {
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.pushFrame();
 
         final double lerpX = MathHelper.lerp(minecart.xo, minecart.x, partialTick);
         final double lerpY = MathHelper.lerp(minecart.yo, minecart.y, partialTick);
@@ -67,34 +66,29 @@ public class EntityRendererMinecart extends EntityRenderer<EntityMinecart> {
 
 //            drawDebugVec(tessellator, Vec3.fromPool(x, y + 1.8, z), Vec3.fromPool(velVec.x, velVec.y, velVec.z), 1.5, 0, 1, 1, 1);
         }
-        GL11.glTranslated(renderX, renderY, renderZ);
-        GL11.glRotated(180F - renderYaw, 0.0F, 1.0F, 0.0F);
-        GL11.glRotated(-lerpXRot, 0.0F, 0.0F, 1.0F);
+        GLRenderer.modelM4f().translate((float) renderX, (float) renderY, (float) renderZ);
+        GLRenderer.modelM4f().rotateY((float) org.joml.Math.toRadians(180F - renderYaw));
+        GLRenderer.modelM4f().rotateZ((float) org.joml.Math.toRadians(-lerpXRot));
         final double hurtAngle = minecart.timeSinceHit - partialTick;
         double currentDamage = minecart.currentDamage - partialTick;
         if (currentDamage < 0.0F) {
             currentDamage = 0.0F;
         }
         if (hurtAngle > 0.0F) {
-            GL11.glRotated(((Math.sin(hurtAngle) * hurtAngle * currentDamage) / 10F) * (float) minecart.hurtDirection, 1.0F, 0.0F, 0.0F);
+            GLRenderer.modelM4f().rotateX((float) org.joml.Math.toRadians(((Math.sin(hurtAngle) * hurtAngle * currentDamage) / 10F) * (float) minecart.hurtDirection));
         }
         // Render block in cart
         if (minecart.getType() != EntityMinecart.PASSENGER_CART) {
-            TextureRegistry.blockAtlas.bind();
+            TextureRegistry.worldAtlas.bind();
             final float scale = 0.75F;
-            GL11.glScalef(scale, scale, scale);
-            GL11.glTranslatef(0.0F, 0.3125F, 0.0F);
-            GL11.glRotatef(90F, 0.0F, 1.0F, 0.0F);
-            float brightness = 1.0f;
-            if (LightmapHelper.isLightmapEnabled()) {
-                LightmapHelper.setLightmapCoord(minecart.getLightmap(partialTick));
-            } else if (!Global.accessor.isFullbrightEnabled()) {
-                brightness = minecart.getBrightness(partialTick);
-            }
+            GLRenderer.modelM4f().scale(scale, scale, scale);
+            GLRenderer.modelM4f().translate(0.0F, 0.3125F, 0.0F);
+            GLRenderer.modelM4f().rotateY(org.joml.Math.PI_OVER_2_f);
+            GLRenderer.setLightmapCoord1i(minecart.getLightmap(partialTick));
 
-            GL11.glPushMatrix();
+            GLRenderer.pushFrame();
             if (doAFlip) {
-                GL11.glRotatef(180, 0, 1, 0);
+                GLRenderer.modelM4f().rotateY(org.joml.Math.PI_f);
             }
             switch (minecart.getType()) {
                 case EntityMinecart.CHEST_CART:
@@ -104,41 +98,42 @@ public class EntityRendererMinecart extends EntityRenderer<EntityMinecart> {
                     } else {
                         block = Blocks.CHEST_PLANKS_OAK;
                     }
-                    BlockModelDispatcher.getInstance().getDispatch(block).renderStandalone(tessellator, minecart.getMeta(), brightness, 1, null);
+                    BlockModelDispatcher.getInstance().getDispatch(block).renderStandalone(tessellator, minecart.getMeta(), minecart.getLightmap(partialTick));
                     break;
                 case EntityMinecart.FURNACE_CART:
                     if (minecart.getFuel() > 0) {
-                        BlockModelDispatcher.getInstance().getDispatch(Blocks.FURNACE_STONE_ACTIVE).renderStandalone(tessellator, 0, brightness, 1, null);
+                        BlockModelDispatcher.getInstance().getDispatch(Blocks.FURNACE_STONE_ACTIVE).renderStandalone(tessellator, 0, minecart.getLightmap(partialTick));
                     } else {
-                        BlockModelDispatcher.getInstance().getDispatch(Blocks.FURNACE_STONE_IDLE).renderStandalone(tessellator, 0, brightness, 1, null);
+                        BlockModelDispatcher.getInstance().getDispatch(Blocks.FURNACE_STONE_IDLE).renderStandalone(tessellator, 0, minecart.getLightmap(partialTick));
                     }
                     break;
             }
-            GL11.glPopMatrix();
-            GL11.glRotatef(-90F, 0.0F, 1.0F, 0.0F);
-            GL11.glTranslatef(0.0F, -0.3125F, 0.0F);
-            GL11.glScalef(1.0F / scale, 1.0F / scale, 1.0F / scale);
+            GLRenderer.popFrame();
+            GLRenderer.modelM4f().rotateY(-org.joml.Math.PI_OVER_2_f);
+            GLRenderer.modelM4f().translate(0.0F, -0.3125F, 0.0F);
+            GLRenderer.modelM4f().scale(1.0F / scale, 1.0F / scale, 1.0F / scale);
         }
         bindTexture("/assets/minecraft/textures/entity/cart.png");
-        GL11.glScalef(1 / 16f, 1 / 16f, -1 / 16f);
-        getModel("main").render(tessellator);
-        GL11.glPopMatrix();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.modelM4f().scale(1 / 16f, 1 / 16f, -1 / 16f);
+        getModel("main").render();
+        GLRenderer.popFrame();
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 
-    private static void drawDebugVec(final @NotNull Tessellator tessellator, final @NotNull Vector3dc start, final @NotNull Vector3dc end, final double scale, final float r, final float g, final float b, final float a) {
-        GL11.glLineWidth(10);
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_TEXTURE_2D);
-        tessellator.startDrawing(GL11.GL_LINES);
-        tessellator.setColorRGBA_F(r, g, b, a);
+    private static void drawDebugVec(final @NotNull TessellatorGeneral tessellator, final @NotNull Vector3dc start, final @NotNull Vector3dc end, final double scale, final float r, final float g, final float b, final float a) {
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.LINES);
+        GLRenderer.setLineWidth(10);
+        tessellator.startDrawing(DrawMode.LINES);
+        tessellator.setColor4f(r, g, b, a);
         tessellator.addVertex(start.x(), start.y(), start.z());
         tessellator.addVertex(
             start.x() + end.x() * scale,
             start.y() + end.y() * scale,
             start.z() + end.z() * scale);
         tessellator.draw();
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
-        GL11.glEnable(GL11.GL_LIGHTING);
+        GLRenderer.popFrame();
+        GLRenderer.globalSetLightEnabled(true);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererPainting.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererPainting.java
index 4f240d56e..cb0ba48cd 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererPainting.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererPainting.java
@@ -1,52 +1,48 @@
 package net.minecraft.client.render.entity;
 
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.core.Global;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.EntityPainting;
 import net.minecraft.core.enums.ArtType;
 import net.minecraft.core.item.ItemStack;
-import net.minecraft.core.util.collection.NamespaceID;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 
 import java.util.Random;
 
-public class EntityRendererPainting extends EntityRenderer<EntityPainting>
-{
+public class EntityRendererPainting extends EntityRenderer<EntityPainting> {
     private static final IconCoordinate paintingBack = TextureRegistry.getTexture("minecraft:art/backing");
-    public EntityRendererPainting()
-    {
-        rand = new Random();
+
+    public EntityRendererPainting() {
+        this.rand = new Random();
     }
 
-    private void renderArt(Tessellator tessellator, EntityPainting entity, int sizeX, int sizeY, IconCoordinate iconCoordinate) {
+    private void renderArt(TessellatorGeneral tessellator, EntityPainting entity, int sizeX, int sizeY, IconCoordinate iconCoordinate) {
         iconCoordinate.parentAtlas.bind();
-        final float negCenterX = (float)(-sizeX) / 2.0F;
-        final float negCenterY = (float)(-sizeY) / 2.0F;
+        final float negCenterX = (float) (-sizeX) / 2.0F;
+        final float negCenterY = (float) (-sizeY) / 2.0F;
         final float minZ = -0.5F;
         final float maxZ = 0.5F;
 
         final int tilesX = sizeX / 16;
         final int tilesY = sizeY / 16;
 
-        for(int x = 0; x < tilesX; x++)
-        {
-            for(int y = 0; y < tilesY; y++)
-            {
-                final float maxX = negCenterX + (float)((x + 1) * 16);
-                final float minX = negCenterX + (float)(x * 16);
-                final float maxY = negCenterY + (float)((y + 1) * 16);
-                final float minY = negCenterY + (float)(y * 16);
+        for (int x = 0; x < tilesX; x++) {
+            for (int y = 0; y < tilesY; y++) {
+                final float maxX = negCenterX + (float) ((x + 1) * 16);
+                final float minX = negCenterX + (float) (x * 16);
+                final float maxY = negCenterY + (float) ((y + 1) * 16);
+                final float minY = negCenterY + (float) (y * 16);
                 setupPaintingBrightness(entity, (maxX + minX) / 2.0F, (maxY + minY) / 2.0F);
-                final double frontMinU = iconCoordinate.getSubIconU((tilesX - x) / (sizeX/16f));
-                final double frontMaxU = iconCoordinate.getSubIconU((tilesX - x - 1) / (sizeX/16f));
-                final double frontMinV = iconCoordinate.getSubIconV((tilesY - y) / (sizeY/16f));
-                final double frontMaxV = iconCoordinate.getSubIconV((tilesY - y - 1) / (sizeY/16f));
+                final double frontMinU = iconCoordinate.getSubIconU((tilesX - x) / (sizeX / 16f));
+                final double frontMaxU = iconCoordinate.getSubIconU((tilesX - x - 1) / (sizeX / 16f));
+                final double frontMinV = iconCoordinate.getSubIconV((tilesY - y) / (sizeY / 16f));
+                final double frontMaxV = iconCoordinate.getSubIconV((tilesY - y - 1) / (sizeY / 16f));
                 final double backMinU = paintingBack.getIconUMin();
                 final double backMaxU = paintingBack.getIconUMax();
                 final double backMinV = paintingBack.getIconVMin();
@@ -63,7 +59,7 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
                 tessellator.addVertexWithUV(minX, minY, maxZ, backMaxU, backMaxV);
                 tessellator.addVertexWithUV(maxX, minY, maxZ, backMinU, backMaxV);
 
-                if (y == tilesY - 1){
+                if (y == tilesY - 1) {
                     tessellator.setNormal(0.0F, 1.0F, 0.0F);
                     final double subV = paintingBack.getSubIconV(1 / 16f);
                     tessellator.addVertexWithUV(minX, maxY, minZ, backMaxU, backMinV);
@@ -71,7 +67,7 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
                     tessellator.addVertexWithUV(maxX, maxY, maxZ, backMinU, subV);
                     tessellator.addVertexWithUV(maxX, maxY, minZ, backMinU, backMinV);
                 }
-                if (y == 0){
+                if (y == 0) {
                     tessellator.setNormal(0.0F, -1F, 0.0F);
                     final double subV = paintingBack.getSubIconV(15 / 16f);
                     tessellator.addVertexWithUV(minX, minY, minZ, backMaxU, subV);
@@ -79,7 +75,7 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
                     tessellator.addVertexWithUV(maxX, minY, maxZ, backMinU, backMaxV);
                     tessellator.addVertexWithUV(minX, minY, maxZ, backMaxU, backMaxV);
                 }
-                if (x == tilesX - 1){
+                if (x == tilesX - 1) {
                     tessellator.setNormal(-1F, 0.0F, 0.0F);
                     final double subU = paintingBack.getSubIconU(1 / 16f);
                     tessellator.addVertexWithUV(maxX, maxY, maxZ, backMinU, backMinV);
@@ -87,7 +83,7 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
                     tessellator.addVertexWithUV(maxX, minY, minZ, subU, backMaxV);
                     tessellator.addVertexWithUV(maxX, maxY, minZ, subU, backMinV);
                 }
-                if (x == 0){
+                if (x == 0) {
                     tessellator.setNormal(1.0F, 0.0F, 0.0F);
                     final double subU = paintingBack.getSubIconU(15 / 16f);
                     tessellator.addVertexWithUV(minX, maxY, maxZ, subU, backMinV);
@@ -102,82 +98,74 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
 
     }
 
-    private void setupPaintingBrightness(EntityPainting entity, float centerX, float centerY)
-    {
+    private void setupPaintingBrightness(EntityPainting entity, float centerX, float centerY) {
         int worldX = MathHelper.floor(entity.x);
-        int worldY = MathHelper.floor(entity.y + (double)(centerY / 16F));
+        int worldY = MathHelper.floor(entity.y + (double) (centerY / 16F));
         int worldZ = MathHelper.floor(entity.z);
-        if(entity.direction == 0)
-        {
-            worldX = MathHelper.floor(entity.x + (double)(centerX / 16F));
-        }
-        if(entity.direction == 1)
-        {
-            worldZ = MathHelper.floor(entity.z - (double)(centerX / 16F));
+        if (entity.direction == 0) {
+            worldX = MathHelper.floor(entity.x + (double) (centerX / 16F));
         }
-        if(entity.direction == 2)
-        {
-            worldX = MathHelper.floor(entity.x - (double)(centerX / 16F));
+        if (entity.direction == 1) {
+            worldZ = MathHelper.floor(entity.z - (double) (centerX / 16F));
         }
-        if(entity.direction == 3)
-        {
-            worldZ = MathHelper.floor(entity.z + (double)(centerX / 16F));
+        if (entity.direction == 2) {
+            worldX = MathHelper.floor(entity.x - (double) (centerX / 16F));
         }
-        float brightness = entity.world.getLightBrightness(worldX, worldY, worldZ);
-        if (Global.accessor.isFullbrightEnabled() || LightmapHelper.isLightmapEnabled()) {
-            LightmapHelper.setLightmapCoord(entity.world.getLightmapCoord(worldX, worldY, worldZ, entity.world.getBlockLightValue(worldX, worldY, worldZ)));
-        	brightness = 1.0f;
+        if (entity.direction == 3) {
+            worldZ = MathHelper.floor(entity.z + (double) (centerX / 16F));
         }
-        GL11.glColor3f(brightness, brightness, brightness);
+        GLRenderer.setLightmapCoord1i(entity.world.getLightmapCoord(worldX, worldY, worldZ, entity.world.getBlockLightValue(worldX, worldY, worldZ)));
+        GLRenderer.setColor3f(1f, 1f, 1f);
     }
 
     @Override
-    public void render(@NotNull Tessellator tessellator, @NotNull EntityPainting entity, double x, double y, double z, float yaw, float partialTick) {
-        rand.setSeed(187L);
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float)x, (float)y, (float)z);
-        GL11.glRotatef(yaw, 0.0F, 1.0F, 0.0F);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+    public void render(@NotNull TessellatorGeneral tessellator, @NotNull EntityPainting entity, double x, double y, double z, float yaw, float partialTick) {
+        this.rand.setSeed(187L);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(yaw));
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
         ArtType art = entity.art;
         float scale = 0.0625F;
-        GL11.glScalef(scale, scale, scale);
+        GLRenderer.modelM4f().scale(scale, scale, scale);
         renderArt(tessellator, entity, art.sizeX, art.sizeY, TextureRegistry.getTexture(art.texture));
         ItemStack borderStack = entity.getBorderStack();
-        if (borderStack != null){
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glBlendFunc(770, 771);
-            GL11.glColor4f(1f, 1f, 1f, 1f);
+        if (borderStack != null) {
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.setColor4f(1f, 1f, 1f, 1f);
             bindTexture(EntityPainting.getBorder(borderStack));
             renderBorder(entity, entity.art.sizeX, entity.art.sizeY);
-            GL11.glDisable(GL11.GL_BLEND);
+            GLRenderer.disableState(State.BLEND);
         }
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
-        GL11.glPopMatrix();
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.popFrame();
     }
+
     private void renderBorder(EntityPainting entity, int sizeX, int sizeY) {
-        float negCenterX = (float)(-sizeX) / 2.0f;
-        float negCenterY = (float)(-sizeY) / 2.0f;
+        float negCenterX = (float) (-sizeX) / 2.0f;
+        float negCenterY = (float) (-sizeY) / 2.0f;
         float minZ = -0.6f;
         float maxZ = 0.5f;
         int width = sizeX / 16;
         int height = sizeY / 16;
         for (int x = 0; x < width; ++x) {
             for (int y = 0; y < height; ++y) {
-                float maxX = negCenterX + (float)((x + 1) * 16);
-                float minX = negCenterX + (float)(x * 16);
-                float maxY = negCenterY + (float)((y + 1) * 16);
-                float minY = negCenterY + (float)(y * 16);
+                float maxX = negCenterX + (float) ((x + 1) * 16);
+                float minX = negCenterX + (float) (x * 16);
+                float maxY = negCenterY + (float) ((y + 1) * 16);
+                float minY = negCenterY + (float) (y * 16);
 
-                if (x == width-1){
+                if (x == width - 1) {
                     maxX += 0.1f;
                 }
-                if (x == 0){
+                if (x == 0) {
                     minX -= 0.1f;
                 }
-                if (y == height-1){
+                if (y == height - 1) {
                     maxY += 0.1f;
                 }
-                if (y == 0){
+                if (y == 0) {
                     minY -= 0.1f;
                 }
 
@@ -185,15 +173,15 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
 
                 int index = getIndex(width - x - 1, height - y - 1, width, height);
 
-                float u = (index%4)/4f;
-                float v = (index/4)/4f;
+                float u = (index % 4) / 4f;
+                float v = (index / 4) / 4f;
 
                 float minU = u + 0.25f;
                 float maxU = u;
                 float minV = v + 0.25f;
                 float maxV = v;
 
-                Tessellator tessellator = Tessellator.instance;
+                TessellatorGeneral tessellator = GLRenderer.getTessellator();
                 tessellator.startDrawingQuads();
                 tessellator.setNormal(0.0f, 0.0f, 1.0f);
                 tessellator.addVertexWithUV(maxX, minY, minZ, maxU, minV);
@@ -201,9 +189,9 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
                 tessellator.addVertexWithUV(minX, maxY, minZ, minU, maxV);
                 tessellator.addVertexWithUV(maxX, maxY, minZ, maxU, maxV);
 
-                float f = 1/64f;
+                float f = 1 / 64f;
 
-                if (y == 0){
+                if (y == 0) {
                     minU = u;
                     maxU = u + 0.25f;
                     minV = v + 0.25f - f;
@@ -216,7 +204,7 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
                     tessellator.addVertexWithUV(maxX, minY, minZ, minU, maxV);
 
                 }
-                if (y == height-1){
+                if (y == height - 1) {
                     minU = u;
                     maxU = u + 0.25f;
                     minV = v + f;
@@ -228,7 +216,7 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
                     tessellator.addVertexWithUV(minX, maxY, maxZ, maxU, maxV);
                     tessellator.addVertexWithUV(maxX, maxY, maxZ, minU, maxV);
                 }
-                if (x == 0){
+                if (x == 0) {
                     minU = u + 0.25f - f;
                     maxU = u + 0.25f;
                     minV = v;
@@ -240,7 +228,7 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
                     tessellator.addVertexWithUV(minX, minY, maxZ, minU, maxV);
                     tessellator.addVertexWithUV(minX, maxY, maxZ, minU, minV);
                 }
-                if (x == width-1){
+                if (x == width - 1) {
                     minU = u + f;
                     maxU = u;
                     minV = v;
@@ -258,53 +246,54 @@ public class EntityRendererPainting extends EntityRenderer<EntityPainting>
         }
     }
 
-    private int getIndex(int x, int y, int width, int height){
-        if (width == 1 && height == 1){ // 1x1
+    private int getIndex(int x, int y, int width, int height) {
+        if (width == 1 && height == 1) { // 1x1
             return 15;
         }
-        if (width == 1){ // Short
-            if (y == 0){
+        if (width == 1) { // Short
+            if (y == 0) {
                 return 3;
             }
-            if (y == height-1){
+            if (y == height - 1) {
                 return 11;
             }
             return 7;
         }
-        if (height == 1){ // Skinny
-            if (x == 0){
+        if (height == 1) { // Skinny
+            if (x == 0) {
                 return 12;
             }
-            if (x == width-1){
+            if (x == width - 1) {
                 return 14;
             }
             return 13;
         }
-        if (x == 0 && y == 0){
+        if (x == 0 && y == 0) {
             return 0;
         }
-        if (x == 0 && y == height-1){
+        if (x == 0 && y == height - 1) {
             return 8;
         }
-        if (x == width-1 && y == 0){
+        if (x == width - 1 && y == 0) {
             return 2;
         }
-        if (x == width-1 && y == height-1){
+        if (x == width - 1 && y == height - 1) {
             return 10;
         }
-        if (x == 0){
+        if (x == 0) {
             return 4;
         }
-        if (x == width-1){
+        if (x == width - 1) {
             return 6;
         }
-        if (y == 0){
+        if (y == 0) {
             return 1;
         }
-        if (y == height-1){
+        if (y == height - 1) {
             return 9;
         }
         return 5;
     }
+
     private final Random rand;
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererSprite.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererSprite.java
index f513d37cb..579c03eeb 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererSprite.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererSprite.java
@@ -2,62 +2,59 @@ package net.minecraft.client.render.entity;
 
 import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.item.Item;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 
-public class EntityRendererSprite<T extends Entity> extends EntityRenderer<T>
-{
-    private IconCoordinate itemIconIndex;
+public class EntityRendererSprite<T extends Entity> extends EntityRenderer<T> {
+    private final IconCoordinate itemIconIndex;
     private float scale = 1;
     private boolean fullBright = false;
 
-    public EntityRendererSprite(Item item){
+    public EntityRendererSprite(Item item) {
         this(ItemModelDispatcher.getInstance().getDispatch(item).getIcon(null, item.getDefaultStack()));
     }
-    public EntityRendererSprite(IconCoordinate i)
-    {
-        itemIconIndex = i;
+
+    public EntityRendererSprite(IconCoordinate i) {
+        this.itemIconIndex = i;
     }
 
-    public EntityRendererSprite<T> setFullBright(){
-        fullBright = true;
+    public EntityRendererSprite<T> setFullBright() {
+        this.fullBright = true;
         return this;
     }
-    public EntityRendererSprite<T> setScale(float scale){
+
+    public EntityRendererSprite<T> setScale(float scale) {
         this.scale = scale;
         return this;
     }
 
     @Override
-    public void render(@NotNull Tessellator tessellator, @NotNull T entity, double x, double y, double z,
-                       float yaw, float partialTick)
-    {
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float) x, (float) y, (float) z);
-        if (fullBright){
-            GL11.glDisable(GL11.GL_LIGHTING);
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-            if (LightmapHelper.isLightmapEnabled()){
-                LightmapHelper.setLightmapCoord(LightmapHelper.getLightmapCoord(15, 15));
-            }
+    public void render(@NotNull TessellatorGeneral tessellator, @NotNull T entity, double x, double y, double z,
+                       float yaw, float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+        if (this.fullBright) {
+            GLRenderer.globalSetLightEnabled(false);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            GLRenderer.setLightmapCoord1i(LightmapHelper.getLightmapCoord(15, 15));
         }
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glScalef(0.5F * scale, 0.5F * scale, 0.5F * scale);
-        itemIconIndex.parentAtlas.bind();
-        float f2 = (float) itemIconIndex.getIconUMin();
-        float f3 = (float) itemIconIndex.getIconUMax();
-        float f4 = (float) itemIconIndex.getIconVMin();
-        float f5 = (float) itemIconIndex.getIconVMax();
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.modelM4f().scale(0.5F * this.scale, 0.5F * this.scale, 0.5F * this.scale);
+        this.itemIconIndex.parentAtlas.bind();
+        float f2 = (float) this.itemIconIndex.getIconUMin();
+        float f3 = (float) this.itemIconIndex.getIconUMax();
+        float f4 = (float) this.itemIconIndex.getIconVMin();
+        float f5 = (float) this.itemIconIndex.getIconVMax();
         float f6 = 1.0F;
         float f7 = 0.5F;
         float f8 = 0.25F;
-        GL11.glRotatef(180F - renderDispatcher.viewLerpYaw, 0.0F, 1.0F, 0.0F);
-        GL11.glRotatef(-renderDispatcher.viewLerpPitch, 1.0F, 0.0F, 0.0F);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(180F - this.renderDispatcher.viewLerpYaw));
+        GLRenderer.modelM4f().rotateX(Math.toRadians(-this.renderDispatcher.viewLerpPitch));
         tessellator.startDrawingQuads();
         tessellator.setNormal(0.0F, 1.0F, 0.0F);
         tessellator.addVertexWithUV(0.0F - f7, 0.0F - f8, 0.0D, f2, f5);
@@ -65,10 +62,10 @@ public class EntityRendererSprite<T extends Entity> extends EntityRenderer<T>
         tessellator.addVertexWithUV(f6 - f7, 1.0F - f8, 0.0D, f3, f4);
         tessellator.addVertexWithUV(0.0F - f7, 1.0F - f8, 0.0D, f2, f4);
         tessellator.draw();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
-        GL11.glPopMatrix();
-        if (fullBright){
-            GL11.glEnable(GL11.GL_LIGHTING);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.popFrame();
+        if (this.fullBright) {
+            GLRenderer.globalSetLightEnabled(true);
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererTNT.java b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererTNT.java
index 3121e5187..f166ff51f 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererTNT.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/EntityRendererTNT.java
@@ -2,61 +2,53 @@ package net.minecraft.client.render.entity;
 
 import net.minecraft.client.render.block.model.BlockModel;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.EntityPrimedTNT;
-import net.minecraft.core.Global;
 import net.minecraft.core.block.Blocks;
 import org.jetbrains.annotations.NotNull;
 import org.lwjgl.opengl.GL11;
 
-public class EntityRendererTNT extends EntityRenderer<EntityPrimedTNT>
-{
-    public EntityRendererTNT()
-    {
+public class EntityRendererTNT extends EntityRenderer<EntityPrimedTNT> {
+    public EntityRendererTNT() {
         super(0.5f);
     }
 
     @Override
-    public void render(@NotNull Tessellator tessellator, @NotNull EntityPrimedTNT tnt, double x, double y, double z, float yaw, float partialTick)
-    {
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float)x, (float)y, (float)z);
-        if(((float)tnt.fuse - partialTick) + 1.0F < 10F)
-        {
-            float f2 = 1.0F - (((float)tnt.fuse - partialTick) + 1.0F) / 10F;
-            if(f2 < 0.0F)
-            {
+    public void render(@NotNull TessellatorGeneral tessellator, @NotNull EntityPrimedTNT tnt, double x, double y, double z, float yaw, float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+        if (((float) tnt.fuse - partialTick) + 1.0F < 10F) {
+            float f2 = 1.0F - (((float) tnt.fuse - partialTick) + 1.0F) / 10F;
+            if (f2 < 0.0F) {
                 f2 = 0.0F;
             }
-            if(f2 > 1.0F)
-            {
+            if (f2 > 1.0F) {
                 f2 = 1.0F;
             }
             f2 *= f2;
             f2 *= f2;
             float f4 = 1.0F + f2 * 0.3F;
-            GL11.glScalef(f4, f4, f4);
+            GLRenderer.modelM4f().scale(f4, f4, f4);
         }
-        float f3 = (1.0F - (((float)tnt.fuse - partialTick) + 1.0F) / 100F) * 0.8F;
-        TextureRegistry.blockAtlas.bind();
-        float brightness = tnt.getBrightness(partialTick);
-        if (Global.accessor.isFullbrightEnabled()) brightness = 1.0f;
+        float f3 = (1.0F - (((float) tnt.fuse - partialTick) + 1.0F) / 100F) * 0.8F;
+        TextureRegistry.worldAtlas.bind();
         BlockModel<?> model = BlockModelDispatcher.getInstance().getDispatch(Blocks.TNT);
-        model.renderStandalone(tessellator, 0, brightness, 1, null);
-        if((tnt.fuse / 5) % 2 == 0)
-        {
+        model.renderStandalone(tessellator, 0, tnt.getLightmap(partialTick));
+        if ((tnt.fuse / 5) % 2 == 0) {
             GL11.glDisable(GL11.GL_TEXTURE_2D);
-            GL11.glDisable(GL11.GL_LIGHTING);
-            GL11.glEnable(GL11.GL_BLEND);
+            GLRenderer.globalSetLightEnabled(false);
+            GLRenderer.enableState(State.BLEND);
             GL11.glBlendFunc(770, 772);
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, f3);
-            model.renderStandalone(tessellator, 0, 1.0F, 1, null);
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-            GL11.glDisable(GL11.GL_BLEND);
-            GL11.glEnable(GL11.GL_LIGHTING);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, f3);
+            model.renderStandalone(tessellator, 0, tnt.getLightmap(partialTick));
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            GLRenderer.disableState(State.BLEND);
+            GLRenderer.globalSetLightEnabled(true);
             GL11.glEnable(GL11.GL_TEXTURE_2D);
         }
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRenderer.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRenderer.java
index 7b1d79f9c..89fca765b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRenderer.java
@@ -2,134 +2,136 @@ package net.minecraft.client.render.entity;
 
 import com.mojang.logging.LogUtils;
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.core.Global;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.CompareFunc;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.AgedMob;
 import net.minecraft.core.entity.Mob;
 import net.minecraft.core.util.helper.Color;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
+import org.joml.Math;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 import org.slf4j.Logger;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
 import java.util.ArrayList;
 import java.util.List;
 
-public abstract class MobRenderer<T extends Mob> extends EntityRenderer<T>{
+public abstract class MobRenderer<T extends Mob> extends EntityRenderer<T> {
     public static final float ENTITY_RENDER_SCALE = 16f;
     private static final Logger LOGGER = LogUtils.getLogger();
     private final @NotNull List<@Nullable StaticEntityModel> setupModels = new ArrayList<>();
+
     public MobRenderer(final float shadowSize) {
         super(shadowSize);
     }
+
     @Override
-    public void render(final @NotNull Tessellator tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+    public void render(final @NotNull TessellatorGeneral tessellator, final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
         loadEntityTexture(entity);
 //        bindTexture("/assets/minecraft/textures/entity/creeper/debug.png");
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glDisable(GL11.GL_CULL_FACE);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.disableState(State.CULL_FACE);
 
-        GL11.glPushMatrix();
+        GLRenderer.pushFrame();
         preRenderTransform(entity, x, y, z, yaw, partialTick);
 
-        float brightness = entity.getBrightness(partialTick);
-        if (Global.accessor.isFullbrightEnabled() || LightmapHelper.isLightmapEnabled()) brightness = 1.0f;
-
         this.setupModels.clear();
         final int maxRenderLayer = maxRenderLayer(entity);
-        for(int layer = 0; layer <= maxRenderLayer; layer++) {
+        for (int layer = 0; layer <= maxRenderLayer; layer++) {
             try {
-                final StaticEntityModel model = getAndSetupModelForLayer(entity, brightness, partialTick, layer);
+                GLRenderer.pushFrame();
+                final StaticEntityModel model = getAndSetupModelForLayer(entity, 1f, partialTick, layer);
                 this.setupModels.add(model);
                 if (model != null) {
-                    model.render(tessellator);
+                    model.render();
                 }
+                GLRenderer.popFrame();
             } catch (final Exception e) {
                 LOGGER.error("Error setting up model on layer '{}' in renderer '{}'", layer, getClass().getSimpleName(), e);
             }
         }
         renderAdditional(tessellator, entity, partialTick);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
 
-        final int argb = getOverlayColor(entity, brightness, partialTick);
+        final int argb = getOverlayColor(entity, 1f, partialTick);
         final boolean hasOverlayAlpha = Color.alphaFromInt(argb) > 0;
-        if(hasOverlayAlpha || entity.hurtTime > 0 || entity.deathTime > 0) {
-            GL11.glDisable(GL11.GL_TEXTURE_2D);
-            GL11.glDisable(GL11.GL_ALPHA_TEST);
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-            GL11.glDepthFunc(GL11.GL_EQUAL);
-            if(entity.hurtTime > 0 || entity.deathTime > 0) {
-                for(int layer = 0; layer <= maxRenderLayer; layer++) {
+        if (hasOverlayAlpha || entity.hurtTime > 0 || entity.deathTime > 0) {
+            GLRenderer.pushFrame();
+            GLRenderer.setShader(Shaders.COLOR_WORLD);
+//            GL11.glDisable(GL11.GL_ALPHA_TEST);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.setDepthFunc(CompareFunc.EQUAL);
+            if (entity.hurtTime > 0 || entity.deathTime > 0) {
+                for (int layer = 0; layer <= maxRenderLayer; layer++) {
                     final StaticEntityModel model = this.setupModels.get(layer);
                     if (model != null) {
-                        GL11.glColor4f(brightness, 0.0F, 0.0F, 0.4F);
-                        model.render(tessellator);
+                        GLRenderer.setColor4f(1f, 0.0F, 0.0F, 0.4F);
+                        model.render();
                     }
                 }
 
             }
-            if(hasOverlayAlpha) {
-                final float r = Color.redFromInt(argb)/255f;
-                final float g = Color.greenFromInt(argb)/255f;
-                final float b = Color.blueFromInt(argb)/255f;
-                final float a = Color.alphaFromInt(argb)/255f;
-                for(int layer = 0; layer < maxRenderLayer; layer++) {
+            if (hasOverlayAlpha) {
+                final float r = Color.redFromInt(argb) / 255f;
+                final float g = Color.greenFromInt(argb) / 255f;
+                final float b = Color.blueFromInt(argb) / 255f;
+                final float a = Color.alphaFromInt(argb) / 255f;
+                for (int layer = 0; layer < maxRenderLayer; layer++) {
                     final StaticEntityModel model = this.setupModels.get(layer);
                     if (model != null) {
-                        GL11.glColor4f(r, g, b, a);
-                        model.render(tessellator);
+                        GLRenderer.setColor4f(r, g, b, a);
+                        model.render();
                     }
                 }
             }
-            GL11.glDepthFunc(GL11.GL_LEQUAL);
-            GL11.glDisable(GL11.GL_BLEND);
-            GL11.glEnable(GL11.GL_ALPHA_TEST);
-            GL11.glEnable(GL11.GL_TEXTURE_2D);
+            GLRenderer.setDepthFunc(CompareFunc.LESS_EQUAL);
+            GLRenderer.disableState(State.BLEND);
+//            GL11.glEnable(GL11.GL_ALPHA_TEST);
+            GLRenderer.popFrame();
         }
 
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
 
-        GL11.glEnable(GL11.GL_CULL_FACE);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.disableState(State.BLEND);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
         renderSpecials(tessellator, entity, x, y, z);
     }
 
     protected void preRenderTransform(final @NotNull T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        GL11.glTranslated(x, y, z);
-        GL11.glRotatef(-getBodyYaw(entity, partialTick) * MathHelper.RAD_TO_DEG, 0, 1, 0);
-        GL11.glScalef(1/ENTITY_RENDER_SCALE, 1/ENTITY_RENDER_SCALE, -1/ENTITY_RENDER_SCALE);
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+        GLRenderer.modelM4f().rotateY(-getBodyYaw(entity, partialTick));
+        GLRenderer.modelM4f().scale(1 / ENTITY_RENDER_SCALE, 1 / ENTITY_RENDER_SCALE, -1 / ENTITY_RENDER_SCALE);
 
-        if(entity.deathTime > 0) {
+        if (entity.deathTime > 0) {
             float rotationProgress = (((entity.deathTime + partialTick) - 1.0F) / 20F) * 1.6F;
             rotationProgress = MathHelper.sqrt_float(rotationProgress);
-            if(rotationProgress > 1.0F) {
+            if (rotationProgress > 1.0F) {
                 rotationProgress = 1.0F;
             }
-            GL11.glRotatef(rotationProgress * getMaxDeathRotation(entity), 0.0F, 0.0F, 1.0F);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(rotationProgress * getMaxDeathRotation(entity)));
         }
 
-        if (entity instanceof AgedMob) {
-            final AgedMob agedMob = (AgedMob) entity;
+        if (entity instanceof AgedMob agedMob) {
             final float ageScale = agedMob.getMobAge().getAgeScale();
-            GL11.glScalef(ageScale, ageScale, ageScale);
+            GLRenderer.modelM4f().scale(ageScale, ageScale, ageScale);
         }
     }
 
     @Override
     public float getShadowSize(final @NotNull T entity) {
         final float baseSize = super.getShadowSize(entity);
-        if (entity instanceof AgedMob) {
-            final AgedMob agedMob = (AgedMob) entity;
+        if (entity instanceof AgedMob agedMob) {
             final float ageScale = agedMob.getMobAge().getAgeScale();
             return baseSize * ageScale;
         }
@@ -143,7 +145,7 @@ public abstract class MobRenderer<T extends Mob> extends EntityRenderer<T>{
 
     protected float getLimbYaw(final @NotNull T entity, final float partialTick) {
         float limbYaw = MathHelper.lerp(entity.walkAnimSpeedO, entity.walkAnimSpeed, partialTick);
-        if(limbYaw > 1.0F) {
+        if (limbYaw > 1.0F) {
             limbYaw = 1.0F;
         }
         return limbYaw;
@@ -165,64 +167,60 @@ public abstract class MobRenderer<T extends Mob> extends EntityRenderer<T>{
         return MathHelper.lerp(entity.xRotO, entity.xRot, partialTick) * MathHelper.DEG_TO_RAD;
     }
 
-    protected void renderSpecials(final @NotNull Tessellator tessellator, final @NotNull T entity, final double x, final double y, final double z)
-    {
-        if(Minecraft.getMinecraft().canRenderEntityLabel()) {
+    protected void renderSpecials(final @NotNull TessellatorGeneral tessellator, final @NotNull T entity, final double x, final double y, final double z) {
+        if (Minecraft.getMinecraft().canRenderEntityLabel()) {
             renderLivingLabel(tessellator, entity, Integer.toString(entity.id), x, y, z, 64, false);
-        }
-        else if (!entity.nickname.isEmpty()) {
+        } else if (!entity.nickname.isEmpty()) {
             renderLivingLabel(tessellator, entity, entity.getDisplayName(), x, y, z, 64, true);
         }
     }
 
-    protected void renderLivingLabel(final @NotNull Tessellator t, final @NotNull T entity, final @NotNull CharSequence text, final double x, final double y, final double z, final int maxDistance, final boolean depthTest)
-    {
+    protected void renderLivingLabel(final @NotNull TessellatorGeneral t, final @NotNull T entity, final @NotNull CharSequence text, final double x, final double y, final double z, final int maxDistance, final boolean depthTest) {
         final float cameraDistance = (float) this.renderDispatcher.camera.distanceTo(entity);
-        if (cameraDistance > maxDistance)
-        {
+        if (cameraDistance > maxDistance) {
             return;
         }
         final FontRenderer sr = getFont();
-        final float scale = 1.6f/60f;
-
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float) x, (float) y + entity.getHeadHeight() + 0.8f, (float) z);
-        GL11.glNormal3f(0.0F, 1.0F, 0.0F);
-        GL11.glRotatef(-this.renderDispatcher.viewLerpYaw, 0.0F, 1.0F, 0.0F);
-        GL11.glRotatef(this.renderDispatcher.viewLerpPitch, 1.0F, 0.0F, 0.0F);
-        GL11.glScalef(-scale, -scale, scale);
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glDepthMask(false);
-        if (!depthTest) GL11.glDisable(GL11.GL_DEPTH_TEST);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glDisable(GL11.GL_TEXTURE_2D);
-
+        final float scale = 1.6f / 60f;
+
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y + entity.getHeadHeight() + 0.8f, (float) z);
+//        GL11.glNormal3f(0.0F, 1.0F, 0.0F);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(-this.renderDispatcher.viewLerpYaw));
+        GLRenderer.modelM4f().rotateX(Math.toRadians(this.renderDispatcher.viewLerpPitch));
+        GLRenderer.modelM4f().scale(-scale, -scale, scale);
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.setDepthMask(false);
+        if (!depthTest) GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.COLOR);
         t.startDrawingQuads();
         final int halfTextWidth = sr.stringWidth(text) / 2;
-        t.setColorRGBA_F(0.0F, 0.0F, 0.0F, 0.25F);
+        t.setColor4f(0.0F, 0.0F, 0.0F, 0.25F);
         t.addVertex(-halfTextWidth - 1, -1, 0.0D);
-        t.addVertex(-halfTextWidth - 1,  8, 0.0D);
-        t.addVertex( halfTextWidth,      8, 0.0D);
-        t.addVertex( halfTextWidth,     -1, 0.0D);
+        t.addVertex(-halfTextWidth - 1, 8, 0.0D);
+        t.addVertex(halfTextWidth, 8, 0.0D);
+        t.addVertex(halfTextWidth, -1, 0.0D);
         t.draw();
+        GLRenderer.popFrame();
 
-        GL11.glEnable(GL11.GL_TEXTURE_2D);
-        sr.render(t, text, -halfTextWidth, 0).setColor(0x20ffffff).call();
-        if (!depthTest) GL11.glEnable(GL11.GL_DEPTH_TEST);
-        GL11.glDepthMask(true);
-        sr.render(t, text, -halfTextWidth, 0).setColor(0xFFFFFF).call();
-        GL11.glEnable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glPopMatrix();
+        sr.render(text, -halfTextWidth, 0).setColor(0x20ffffff).call();
+        if (!depthTest) GLRenderer.enableState(State.DEPTH_TEST);
+        GLRenderer.setDepthMask(true);
+        sr.render(text, -halfTextWidth, 0).setColor(0xFFFFFF).call();
+        GLRenderer.globalSetLightEnabled(true);
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.popFrame();
     }
 
     protected int getOverlayColor(final @NotNull T entity, final float brightness, final float partialTick) {
         return 0;
     }
 
-    protected float getMaxDeathRotation(final @NotNull T entity)
-    {
+    protected float getMaxDeathRotation(final @NotNull T entity) {
         return 90F;
     }
 
@@ -232,16 +230,13 @@ public abstract class MobRenderer<T extends Mob> extends EntityRenderer<T>{
 
     protected abstract @Nullable StaticEntityModel getAndSetupModelForLayer(final @NotNull T entity, float brightness, final float partialTick, final int layer);
 
-    protected void renderAdditional(@NotNull final Tessellator tessellator, final @NotNull T entity, final float partialTick)
-    {
+    protected void renderAdditional(@NotNull final TessellatorGeneral tessellator, final @NotNull T entity, final float partialTick) {
     }
 
-    public void loadEntityTexture(final @NotNull T entity)
-    {
+    public void loadEntityTexture(final @NotNull T entity) {
         if (!Minecraft.getMinecraft().gameSettings.mobVariants.value) {
             bindTexture(entity.getDefaultEntityTexture());
-        }
-        else {
+        } else {
             bindTexture(entity.getEntityTexture());
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererBiped.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererBiped.java
index 885cf0526..1a1f57bca 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererBiped.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererBiped.java
@@ -2,14 +2,14 @@ package net.minecraft.client.render.entity;
 
 import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.IItemHolding;
 import net.minecraft.core.entity.Mob;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
@@ -24,7 +24,7 @@ public abstract class MobRendererBiped<T extends Mob> extends MobRenderer<T> {
 
     @Override
     protected @Nullable StaticEntityModel getAndSetupModelForLayer(@NotNull final T entity, final float brightness, final float partialTick, final int layer) {
-       return setupAnimations(entity, getActiveModel(entity), partialTick, layer);
+        return setupAnimations(entity, getActiveModel(entity), partialTick, layer);
     }
 
     protected @Nullable StaticEntityModel setupAnimations(@NotNull final T entity, @Nullable final StaticEntityModel model, final float partialTick, final int layer) {
@@ -59,8 +59,7 @@ public abstract class MobRendererBiped<T extends Mob> extends MobRenderer<T> {
         }
         rightLeg.rotX = Math.cos(limbSwing * 0.6662F) * 1.4F * limbYaw;
         leftLeg.rotX = Math.cos(limbSwing * 0.6662F + Math.PI) * 1.4F * limbYaw;
-        if(entity.vehicle != null)
-        {
+        if (entity.vehicle != null) {
             rightArm.rotX += -36 * MathHelper.DEG_TO_RAD;
             leftArm.rotX += -36 * MathHelper.DEG_TO_RAD;
             rightLeg.rotX = -72 * MathHelper.DEG_TO_RAD;
@@ -83,8 +82,7 @@ public abstract class MobRendererBiped<T extends Mob> extends MobRenderer<T> {
             final double rotX = Math.sin(Math.sqrt(swingProgress) * Math.PI * -2.0F) * 0.4F;
             rightArm.rotX += rotX;
             leftArm.rotX += rotX;
-        }
-        else if (entity instanceof IItemHolding && ((IItemHolding) entity).isLeftHanded()) {
+        } else if (entity instanceof IItemHolding && ((IItemHolding) entity).isLeftHanded()) {
             torso.rotY = Math.sin(Math.sqrt(swingProgress) * Math.PI * -2.0F) * 0.2F;
 
             float f6 = 1.0F - swingProgress;
@@ -112,8 +110,7 @@ public abstract class MobRendererBiped<T extends Mob> extends MobRenderer<T> {
             rightArm.rotZ = Math.sin(swingProgress * Math.PI) * -0.4F;
         }
 
-        if(entity.isSneaking())
-        {
+        if (entity.isSneaking()) {
             waist.posY -= 2;
             leftLeg.posZ += 5;
             rightLeg.posZ += 5;
@@ -138,37 +135,38 @@ public abstract class MobRendererBiped<T extends Mob> extends MobRenderer<T> {
     }
 
     @Override
-    protected void renderAdditional(@NotNull final Tessellator tessellator, final @NotNull T entity, final float partialTick) {
-        if (entity instanceof IItemHolding) {
-            final IItemHolding itemHolder = (IItemHolding) entity;
+    protected void renderAdditional(@NotNull final TessellatorGeneral tessellator, final @NotNull T entity, final float partialTick) {
+        if (entity instanceof IItemHolding itemHolder) {
             final ItemStack itemstack = itemHolder.getHeldItem();
 
             final StaticEntityModel model = getActiveModel(entity);
 
-            if(itemstack != null) {
-                GL11.glPushMatrix();
-                if (((IItemHolding) entity).isLeftHanded()) {
+            if (itemstack != null) {
+                GLRenderer.pushFrame();
+                if (itemHolder.isLeftHanded()) {
                     if (model != null) model.translateToBone("leftItem");
-                    GL11.glScalef(-1, 1, -1);
-                    GL11.glScalef(MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE);
+                    GLRenderer.modelM4f().scale(-1, 1, -1);
+                    GLRenderer.modelM4f().scale(MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE);
                     ItemModelDispatcher.getInstance().getDispatch(itemstack)
-                        .render(tessellator, entity, itemstack, DisplayPos.THIRD_PERSON_LEFT_HAND, true, 1, LightmapHelper.isLightmapEnabled() ? 1f : entity.getBrightness(partialTick), 1f, partialTick, true);
+                        .render(tessellator, entity, itemstack, DisplayPos.THIRD_PERSON_LEFT_HAND, true, 1,
+                            LightmapHelper.getLightmapCoord(GLRenderer.getLightmapSky(), GLRenderer.getLightmapBlock()), partialTick, true);
                 } else {
 
                     if (model != null) model.translateToBone("rightItem");
-                    GL11.glScalef(-1, 1, 1);
-                    GL11.glScalef(MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE);
+                    GLRenderer.modelM4f().scale(-1, 1, 1);
+                    GLRenderer.modelM4f().scale(MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE);
                     ItemModelDispatcher.getInstance().getDispatch(itemstack)
-                        .render(tessellator, entity, itemstack, DisplayPos.THIRD_PERSON_RIGHT_HAND, true, 1, LightmapHelper.isLightmapEnabled() ? 1f : entity.getBrightness(partialTick), 1f, partialTick, false);
+                        .render(tessellator, entity, itemstack, DisplayPos.THIRD_PERSON_RIGHT_HAND, true, 1,
+                            LightmapHelper.getLightmapCoord(GLRenderer.getLightmapSky(), GLRenderer.getLightmapBlock()), partialTick, false);
                 }
-                GL11.glPopMatrix();
+                GLRenderer.popFrame();
             }
         }
     }
 
     @Override
-    public void renderPreview(@NotNull final Tessellator tessellator, @NotNull final T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        if (entity.isSneaking()) GL11.glTranslatef(0, 2/16f, 4/16f);
+    public void renderPreview(@NotNull final TessellatorGeneral tessellator, @NotNull final T entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+        if (entity.isSneaking()) GLRenderer.modelM4f().translate(0, 2 / 16f, 4 / 16f);
         super.renderPreview(tessellator, entity, x, y, z, yaw, partialTick);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererBipedArmored.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererBipedArmored.java
index 72bc573ce..7dabe22d0 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererBipedArmored.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererBipedArmored.java
@@ -2,7 +2,9 @@ package net.minecraft.client.render.entity;
 
 import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.IArmorWearing;
 import net.minecraft.core.entity.Mob;
 import net.minecraft.core.enums.HumanArmorShape;
@@ -14,11 +16,10 @@ import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.item.Items;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
-public abstract class MobRendererBipedArmored<T extends Mob & IArmorWearing<HumanArmorShape>> extends MobRendererBiped<T>{
+public abstract class MobRendererBipedArmored<T extends Mob & IArmorWearing<HumanArmorShape>> extends MobRendererBiped<T> {
     public MobRendererBipedArmored(final float shadowSize) {
         super(shadowSize);
     }
@@ -36,8 +37,7 @@ public abstract class MobRendererBipedArmored<T extends Mob & IArmorWearing<Huma
             bindTexture("/assets/minecraft/textures/armor/quiver_golden.png");
         } else if (item == Items.ARMOR_BOOTS_ICESKATES) {
             bindTexture("/assets/minecraft/textures/armor/skates.png");
-        } else if (item instanceof IArmorItem) {
-            final IArmorItem armorItem = (IArmorItem) item;
+        } else if (item instanceof IArmorItem<?> armorItem) {
             if (armorItem.getArmorMaterial() == null) return null;
             bindTexture(String.format("/assets/%s/textures/armor/%s_%d.png", armorItem.getArmorMaterial().identifier.namespace(), armorItem.getArmorMaterial().identifier.value(), (layer != 3 ? 1 : 2)));
         } else {
@@ -94,25 +94,26 @@ public abstract class MobRendererBipedArmored<T extends Mob & IArmorWearing<Huma
         return model1;
     }
 
-    protected void renderAdditional(@NotNull final Tessellator tessellator, final @NotNull T entity, final float partialTick) {
+    protected void renderAdditional(@NotNull final TessellatorGeneral tessellator, final @NotNull T entity, final float partialTick) {
         final @Nullable ItemStack stack = entity.getItemInArmorSlot(HumanArmorShape.HEAD);
 
         final StaticEntityModel model = getActiveModel(entity);
 
-        if(stack != null) {
-            GL11.glPushMatrix();
+        if (stack != null) {
+            GLRenderer.pushFrame();
             if (model != null) model.translateToBone("head");
             if (!(stack.getItem() instanceof IArmorItem)) {
-                GL11.glPushMatrix();
-                GL11.glEnable(GL11.GL_CULL_FACE);
-                GL11.glScalef(-16, 16, 16);
-                GL11.glScalef(0.6f, 0.6f, 0.6f);
-                GL11.glTranslatef(0, 7/16f, 0);
-                ItemModelDispatcher.getInstance().getDispatch(stack).render(Tessellator.instance, null, stack, DisplayPos.HEAD, true, 1, LightmapHelper.isLightmapEnabled() ? 1f : entity.getBrightness(partialTick), 1f, partialTick, true);
-                GL11.glDisable(GL11.GL_CULL_FACE);
-                GL11.glPopMatrix();
+                GLRenderer.pushFrame();
+                GLRenderer.enableState(State.CULL_FACE);
+                GLRenderer.modelM4f().scale(-16, 16, 16);
+                GLRenderer.modelM4f().scale(0.6f, 0.6f, 0.6f);
+                GLRenderer.modelM4f().translate(0, 7 / 16f, 0);
+                ItemModelDispatcher.getInstance().getDispatch(stack).render(GLRenderer.getTessellator(), null, stack, DisplayPos.HEAD, true, 1,
+                    LightmapHelper.getLightmapCoord(GLRenderer.getLightmapSky(), GLRenderer.getLightmapBlock()), partialTick, true);
+                GLRenderer.disableState(State.CULL_FACE);
+                GLRenderer.popFrame();
             }
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         }
 
         super.renderAdditional(tessellator, entity, partialTick);
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererButterfly.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererButterfly.java
index 491d6b2fa..f6b94890b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererButterfly.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererButterfly.java
@@ -2,19 +2,21 @@ package net.minecraft.client.render.entity;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.TextureManager;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.animal.MobButterfly;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 
 import java.util.Random;
 
 public class MobRendererButterfly extends EntityRenderer<MobButterfly> {
     private static final Random sizeRandom = new Random();
+
     @Override
-    public void render(@NotNull final Tessellator tessellator, @NotNull final MobButterfly butterfly, final double x, final double y, final double z, final float yaw, final float partialTick) {
+    public void render(@NotNull final TessellatorGeneral tessellator, @NotNull final MobButterfly butterfly, final double x, final double y, final double z, final float yaw, final float partialTick) {
         // 0.45 -> 0.8
         sizeRandom.setSeed((long) butterfly.getSkinVariant() << 16);
         final float scale = 0.45f + (sizeRandom.nextFloat() * 0.35f);
@@ -23,53 +25,53 @@ public class MobRendererButterfly extends EntityRenderer<MobButterfly> {
     }
 
     @Override
-    public void renderPreview(@NotNull final Tessellator tessellator, @NotNull final MobButterfly butterfly, final double x, final double y, final double z, final float yaw, final float partialTick) {
+    public void renderPreview(@NotNull final TessellatorGeneral tessellator, @NotNull final MobButterfly butterfly, final double x, final double y, final double z, final float yaw, final float partialTick) {
         final float yRot = MathHelper.lerp(butterfly.yRotO, butterfly.yRot, partialTick);
         drawButterfly(tessellator, butterfly.tickCount, 1.25f, -yRot, x, y + 0.5, z, partialTick, this.renderDispatcher.textureManager, getTexture(butterfly));
     }
 
-    public static void drawButterfly(final Tessellator tessellator, final int ticksAlive, final float scale, final float yRot, final double x, final double y, final double z, final float partialTick, final TextureManager textureManager, final String texture) {
+    public static void drawButterfly(final TessellatorGeneral tessellator, final int ticksAlive, final float scale, final float yRot, final double x, final double y, final double z, final float partialTick, final TextureManager textureManager, final String texture) {
         textureManager.bindTexture(textureManager.loadTexture(texture));
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float) x, (float) y + 0.25f, (float) z);
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glDisable(GL11.GL_CULL_FACE);
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glScalef(0.5F * scale, 0.5F * scale, 0.5F * scale);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x, (float) y + 0.25f, (float) z);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.disableState(State.CULL_FACE);
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.modelM4f().scale(0.5F * scale, 0.5F * scale, 0.5F * scale);
 
-        GL11.glRotatef(yRot, 0, 1, 0);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(yRot));
 
-        GL11.glRotatef(-22.5f, 1, 0, 0);
+        GLRenderer.modelM4f().rotateX(Math.toRadians(-22.5f));
 
         final float xOff = -0.5F;
         final float zOff = -0.5F;
 
         final float flapAngle = (MathHelper.sin(ticksAlive + partialTick) + 1) * 22.5f + 5;
 
-        GL11.glPushMatrix();
-        GL11.glRotatef(-flapAngle, 0, 0, 1);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().rotateZ(Math.toRadians(-flapAngle));
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(xOff,       0.0D, zOff,       0,   1);
-        tessellator.addVertexWithUV(xOff + 0.5, 0.0D, zOff,       0.5, 1);
+        tessellator.addVertexWithUV(xOff, 0.0D, zOff, 0, 1);
+        tessellator.addVertexWithUV(xOff + 0.5, 0.0D, zOff, 0.5, 1);
         tessellator.addVertexWithUV(xOff + 0.5, 0.0D, zOff + 1.0, 0.5, 0);
-        tessellator.addVertexWithUV(xOff,       0.0D, zOff + 1.0, 0,   0);
+        tessellator.addVertexWithUV(xOff, 0.0D, zOff + 1.0, 0, 0);
         tessellator.draw();
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
 
-        GL11.glPushMatrix();
-        GL11.glRotatef(flapAngle, 0, 0, 1);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().rotateZ(Math.toRadians(flapAngle));
         tessellator.startDrawingQuads();
-        tessellator.addVertexWithUV(xOff + 0.5, 0.0D, zOff,       0.5, 1);
-        tessellator.addVertexWithUV(xOff + 1.0, 0.0D, zOff,       1.0, 1);
+        tessellator.addVertexWithUV(xOff + 0.5, 0.0D, zOff, 0.5, 1);
+        tessellator.addVertexWithUV(xOff + 1.0, 0.0D, zOff, 1.0, 1);
         tessellator.addVertexWithUV(xOff + 1.0, 0.0D, zOff + 1.0, 1.0, 0);
         tessellator.addVertexWithUV(xOff + 0.5, 0.0D, zOff + 1.0, 0.5, 0);
         tessellator.draw();
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
 
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
-        GL11.glEnable(GL11.GL_CULL_FACE);
-        GL11.glEnable(GL11.GL_LIGHTING);
-        GL11.glPopMatrix();
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.globalSetLightEnabled(true);
+        GLRenderer.popFrame();
     }
 
     public static String getTexture(final MobButterfly butterfly) {
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererChicken.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererChicken.java
index df1117655..ce391d692 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererChicken.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererChicken.java
@@ -1,10 +1,10 @@
 package net.minecraft.client.render.entity;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.entity.animal.MobChicken;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
@@ -46,6 +46,6 @@ public class MobRendererChicken extends MobRenderer<MobChicken> {
     @Override
     protected void preRenderTransform(@NotNull MobChicken entity, double x, double y, double z, float yaw, float partialTick) {
         super.preRenderTransform(entity, x, y, z, yaw, partialTick);
-        GL11.glTranslatef(0, 0.3f, 0);
+        GLRenderer.modelM4f().translate(0, 0.3f, 0);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererCreeper.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererCreeper.java
index b0c75003f..97ee97b94 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererCreeper.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererCreeper.java
@@ -1,5 +1,7 @@
 package net.minecraft.client.render.entity;
 
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.entity.monster.MobCreeper;
 import net.minecraft.core.util.helper.Color;
 import net.minecraft.core.util.helper.MathHelper;
@@ -18,8 +20,10 @@ public class MobRendererCreeper extends MobRenderer<MobCreeper> {
     @Override
     protected int getOverlayColor(final @NotNull MobCreeper creeper, final float brightness, final float partialTick) {
         final float step = creeper.getSwelling(partialTick);
-        if ((int)(step * 10.0f) % 2 == 0) { return 0; }
-        return Color.intToIntARGB(MathHelper.clamp((int)(step * 0.2f * 255.0f), 0, 255), 255, 255,255);
+        if ((int) (step * 10.0f) % 2 == 0) {
+            return 0;
+        }
+        return Color.intToIntARGB(MathHelper.clamp((int) (step * 0.2f * 255.0f), 0, 255), 255, 255, 255);
     }
 
     @Override
@@ -33,18 +37,18 @@ public class MobRendererCreeper extends MobRenderer<MobCreeper> {
             GL11.glLoadIdentity();
             final float _x = ticks * 0.01F;
             final float _y = ticks * 0.01F;
-            GL11.glTranslatef(_x, _y, 0.0F);
+            GLRenderer.modelM4f().translate(_x, _y, 0.0F);
             GL11.glMatrixMode(GL11.GL_MODELVIEW);
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glColor4f(0.5f, 0.5f, 0.5f, 1.0F);
-            GL11.glDisable(GL11.GL_LIGHTING);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setColor4f(0.5f, 0.5f, 0.5f, 1.0F);
+            GLRenderer.globalSetLightEnabled(false);
             GL11.glBlendFunc(GL11.GL_ONE, GL11.GL_ONE);
         } else if (layer == 2) { // Reset funky powered rendering
             GL11.glMatrixMode(GL11.GL_TEXTURE);
             GL11.glLoadIdentity();
             GL11.glMatrixMode(GL11.GL_MODELVIEW);
-            GL11.glEnable(GL11.GL_LIGHTING);
-            GL11.glDisable(GL11.GL_BLEND);
+            GLRenderer.globalSetLightEnabled(true);
+            GLRenderer.disableState(State.BLEND);
             return null;
         } else {
             model = getModel("main");
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererDeer.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererDeer.java
index 93a18ff0f..20c4a2338 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererDeer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererDeer.java
@@ -1,10 +1,10 @@
 package net.minecraft.client.render.entity;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.entity.animal.MobDeer;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
@@ -21,7 +21,7 @@ public class MobRendererDeer extends MobRenderer<MobDeer> {
     @Override
     protected void preRenderTransform(@NotNull final MobDeer entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
         super.preRenderTransform(entity, x, y, z, yaw, partialTick);
-        GL11.glScalef(1.1F, 1.1F, 1.1F);
+        GLRenderer.modelM4f().scale(1.1F, 1.1F, 1.1F);
     }
 
     @Override
@@ -42,9 +42,7 @@ public class MobRendererDeer extends MobRenderer<MobDeer> {
         final float limbSwing = getLimbSwing(entity, partialTick);
         final float limbYaw = getLimbYaw(entity, partialTick);
 
-        if (entity.brainState instanceof MobDeer.SniffingBrainState) {
-            final @NotNull MobDeer.SniffingBrainState brainState = (MobDeer.SniffingBrainState) entity.brainState;
-
+        if (entity.brainState instanceof @NotNull MobDeer.SniffingBrainState brainState) {
             final float neckRotX = MathHelper.lerp(MIN_NECK_ROT_X_SNIFF, MAX_NECK_ROT_X_SNIFF, brainState.leanPercentage);
             final float headRotX = MathHelper.lerp(MIN_HEAD_ROT_X_SNIFF, MAX_HEAD_ROT_X_SNIFF, brainState.leanPercentage);
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererFireflyCluster.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererFireflyCluster.java
index ac8050f04..6c56a558b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererFireflyCluster.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererFireflyCluster.java
@@ -1,77 +1,77 @@
 package net.minecraft.client.render.entity;
 
 import net.minecraft.client.render.Lighting;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.world.WorldClient;
 import net.minecraft.core.entity.animal.MobFireflyCluster;
 import net.minecraft.client.render.particle.ParticleFirefly;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 import java.util.ArrayList;
 import java.util.List;
 import java.util.Random;
 
 public class MobRendererFireflyCluster extends EntityRenderer<MobFireflyCluster> {
-	private final List<ParticleFirefly> fireflies = new ArrayList<>();
+    private final List<ParticleFirefly> fireflies = new ArrayList<>();
     private final Random rand = new Random(0);
-	private long lastTick;
+    private long lastTick;
 
-	public MobRendererFireflyCluster() {
-		for (int i = 0; i < 20; i++) {
-			final ParticleFirefly fx = new ParticleFirefly(WorldClient.EMPTY_WORLD, this.rand.nextFloat() - 0.5f, this.rand.nextFloat() - 0.5f, 0, 0, 0, 0, 0);
-			fx.noPhysics = true;
-			fx.setAge(this.rand.nextInt(20));
+    public MobRendererFireflyCluster() {
+        for (int i = 0; i < 20; i++) {
+            final ParticleFirefly fx = new ParticleFirefly(WorldClient.EMPTY_WORLD, this.rand.nextFloat() - 0.5f, this.rand.nextFloat() - 0.5f, 0, 0, 0, 0, 0);
+            fx.noPhysics = true;
+            fx.setAge(this.rand.nextInt(20));
             this.fireflies.add(fx);
-		}
+        }
         this.lastTick = System.currentTimeMillis();
-	}
+    }
 
-	@Override
-	public void render(@NotNull final Tessellator tessellator, @NotNull final MobFireflyCluster parent, final double x, final double y, final double z, final float yaw, final float partialTick) {
-		// Fireflies are rendered as particles which are spawned in the entity class
-	}
+    @Override
+    public void render(@NotNull final TessellatorGeneral tessellator, @NotNull final MobFireflyCluster parent, final double x, final double y, final double z, final float yaw, final float partialTick) {
+        // Fireflies are rendered as particles which are spawned in the entity class
+    }
 
-	@Override
-	public void renderPreview(@NotNull final Tessellator tessellator, @NotNull final MobFireflyCluster entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
-		super.renderPreview(tessellator, entity, x, y, z, yaw, partialTick);
+    @Override
+    public void renderPreview(@NotNull final TessellatorGeneral tessellator, @NotNull final MobFireflyCluster entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
+        super.renderPreview(tessellator, entity, x, y, z, yaw, partialTick);
 
-		final long currentTick = System.currentTimeMillis();
-		final int storedTicks = (int) ((currentTick - this.lastTick) / 50.0f);
+        final long currentTick = System.currentTimeMillis();
+        final int storedTicks = (int) ((currentTick - this.lastTick) / 50.0f);
 
-		GL11.glPushMatrix();
-		GL11.glTranslatef(0, 0.75f, 0);
-		GL11.glEnable(GL11.GL_TEXTURE_2D);
-		GL11.glEnable(GL11.GL_BLEND);
-		Lighting.disable();
-		TextureRegistry.particleAtlas.bind();
-		final Tessellator t = Tessellator.instance;
-		t.startDrawingQuads();
-		for (int i = 0; i < this.fireflies.size(); i++) {
-			final ParticleFirefly firefly = this.fireflies.get(i);
-			firefly.renderParticleInGui(t, partialTick);
-			for (int j = 0; j < storedTicks; j++) {
-				firefly.tickGui();
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate(0, 0.75f, 0);
+        GLRenderer.enableState(State.BLEND);
+        Lighting.disable();
+        TextureRegistry.worldAtlas.bind();
+        final TessellatorGeneral t = GLRenderer.getTessellator();
+        t.startDrawingQuads();
+        for (int i = 0; i < this.fireflies.size(); i++) {
+            final ParticleFirefly firefly = this.fireflies.get(i);
+            firefly.renderParticleInGui(t, partialTick);
+            for (int j = 0; j < storedTicks; j++) {
+                firefly.tickGui();
                 this.lastTick = currentTick;
-			}
-			if (firefly.removed) {
+            }
+            if (firefly.removed) {
                 this.fireflies.remove(i);
-				i--;
-			}
-		}
-		t.draw();
-		GL11.glEnable(GL11.GL_CULL_FACE);
-		GL11.glPopMatrix();
+                i--;
+            }
+        }
+        t.draw();
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.popFrame();
 
-		if (this.fireflies.size() < 20) {
-			for (int i = this.fireflies.size(); i < 20; i++) {
-				if (this.rand.nextInt(4) == 0) continue;
-				final ParticleFirefly fx = new ParticleFirefly(WorldClient.EMPTY_WORLD, this.rand.nextFloat() - 0.5f, this.rand.nextFloat() - 0.5f, 0, 0, 0, 0, entity.getColor().getId());
-				fx.noPhysics = true;
-				fx.setAge(this.rand.nextInt(20));
+        if (this.fireflies.size() < 20) {
+            for (int i = this.fireflies.size(); i < 20; i++) {
+                if (this.rand.nextInt(4) == 0) continue;
+                final ParticleFirefly fx = new ParticleFirefly(WorldClient.EMPTY_WORLD, this.rand.nextFloat() - 0.5f, this.rand.nextFloat() - 0.5f, 0, 0, 0, 0, entity.getColor().getId());
+                fx.noPhysics = true;
+                fx.setAge(this.rand.nextInt(20));
                 this.fireflies.add(fx);
-			}
-		}
-	}
+            }
+        }
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererGhast.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererGhast.java
index 441354d2f..926381e15 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererGhast.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererGhast.java
@@ -1,11 +1,11 @@
 package net.minecraft.client.render.entity;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.monster.MobGhast;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
@@ -23,7 +23,9 @@ public class MobRendererGhast extends MobRenderer<MobGhast> {
         final BoneTransform body = model.getTransform("body");
 
         float charge = MathHelper.lerp(entity.attackChargeO, entity.attackCharge, partialTick) / 20F;
-        if(charge < 0.0F) { charge = 0.0F; }
+        if (charge < 0.0F) {
+            charge = 0.0F;
+        }
         charge = 1.0F / (charge * charge * charge * charge * charge * 2.0F + 1.0F);
         final float sHeight = (8F + charge) / 2.0F;
         final float sWidth = (8F + 1.0F / charge) / 2.0F;
@@ -48,10 +50,11 @@ public class MobRendererGhast extends MobRenderer<MobGhast> {
     }
 
     @Override
-    public void renderPreview(@NotNull final Tessellator tessellator, @NotNull final MobGhast mobGhast, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        GL11.glPushMatrix();
-        GL11.glScalef(0.25f, 0.25f, 0.25f);
+    public void renderPreview(@NotNull final TessellatorGeneral tessellator, @NotNull final MobGhast mobGhast, final double x, final double y, final double z, final float yaw, final float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate(0, 1f, 0f);
+        GLRenderer.modelM4f().scale(0.25f, 0.25f, 0.25f);
         super.renderPreview(tessellator, mobGhast, x, y, z, yaw, partialTick);
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererGiant.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererGiant.java
index 3912d9bbc..c179f9e7c 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererGiant.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererGiant.java
@@ -1,8 +1,8 @@
 package net.minecraft.client.render.entity;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.entity.monster.MobZombie;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 public class MobRendererGiant extends MobRendererZombie
 {
@@ -17,7 +17,7 @@ public class MobRendererGiant extends MobRendererZombie
     @Override
     protected void preRenderTransform(@NotNull final MobZombie entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
         super.preRenderTransform(entity, x, y, z, yaw, partialTick);
-        GL11.glScalef(this.scale, this.scale, this.scale);
+        GLRenderer.modelM4f().scale(this.scale, this.scale, this.scale);
     }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererHuman.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererHuman.java
index a4abf18bf..7d72ad752 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererHuman.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererHuman.java
@@ -1,41 +1,40 @@
 package net.minecraft.client.render.entity;
 
 import net.minecraft.client.render.PlayerSkinParser;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.entity.monster.MobHuman;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
+import org.joml.Math;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
-public class MobRendererHuman extends MobRendererBiped<MobHuman>
-{
+public class MobRendererHuman extends MobRendererBiped<MobHuman> {
     public MobRendererHuman() {
         super(0.5f);
     }
 
     @Override
     protected void preRenderTransform(@NotNull final MobHuman entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        GL11.glTranslated(x, y, z);
-        GL11.glRotatef(-getBodyYaw(entity, partialTick) * MathHelper.RAD_TO_DEG, 0, 1, 0);
-        GL11.glScalef(1/ENTITY_RENDER_SCALE, 1/ENTITY_RENDER_SCALE, -1/ENTITY_RENDER_SCALE);
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+        GLRenderer.modelM4f().rotateY(-getBodyYaw(entity, partialTick));
+        GLRenderer.modelM4f().scale(1 / ENTITY_RENDER_SCALE, 1 / ENTITY_RENDER_SCALE, -1 / ENTITY_RENDER_SCALE);
 
         final float scale = 0.9375F;
-        GL11.glScalef(scale, scale, scale);
+        GLRenderer.modelM4f().scale(scale, scale, scale);
 
-        if(entity.deathTime > 0) {
+        if (entity.deathTime > 0) {
             float rotationProgress = (((entity.deathTime + partialTick) - 1.0F) / 20F) * 1.6F;
             rotationProgress = MathHelper.sqrt_float(rotationProgress);
-            if(rotationProgress > 1.0F) {
+            if (rotationProgress > 1.0F) {
                 rotationProgress = 1.0F;
             }
-            GL11.glRotatef(rotationProgress * getMaxDeathRotation(entity), 0.0F, 0.0F, 1.0F);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(rotationProgress * getMaxDeathRotation(entity)));
         }
     }
 
     @Override
-    public void loadEntityTexture(final @NotNull MobHuman entity)
-    {
+    public void loadEntityTexture(final @NotNull MobHuman entity) {
         bindDownloadableTexture(entity.skinUrl, entity.getEntityTexture(), entity.slimModel ? PlayerSkinParser.instanceAlex : PlayerSkinParser.instanceSteve);
     }
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererPlayer.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererPlayer.java
index d8640e467..a73472626 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererPlayer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererPlayer.java
@@ -2,13 +2,16 @@ package net.minecraft.client.render.entity;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.Lighting;
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.PlayerSkinParser;
 import net.minecraft.client.render.TileEntityRenderDispatcher;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
 import net.minecraft.client.render.camera.EntityCamera;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.render.tileentity.TileEntityRenderer;
 import net.minecraft.core.Global;
@@ -22,25 +25,17 @@ import net.minecraft.core.world.BlocksContainer;
 import net.minecraft.core.world.pos.TilePos;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
 import java.util.UUID;
 
-import static org.lwjgl.opengl.GL11.GL_COLOR_MATERIAL;
-import static org.lwjgl.opengl.GL11.GL_LIGHT0;
-import static org.lwjgl.opengl.GL11.GL_LIGHT1;
-import static org.lwjgl.opengl.GL11.GL_LIGHTING;
-
-public class MobRendererPlayer extends MobRendererBipedArmored<Player>
-{
+public class MobRendererPlayer extends MobRendererBipedArmored<Player> {
 
 
     private BlocksContainer container = null;
 
-    public MobRendererPlayer()
-    {
+    public MobRendererPlayer() {
         super(0.5F);
     }
 
@@ -55,8 +50,7 @@ public class MobRendererPlayer extends MobRendererBipedArmored<Player>
         }
     }
 
-    public void drawFirstPersonHand(final @NotNull Tessellator tessellator, final @NotNull Player player, final boolean isLeft)
-    {
+    public void drawFirstPersonHand(final @NotNull TessellatorGeneral tessellator, final @NotNull Player player, final boolean isLeft) {
         // TODO rework the transform nightmare that surround these method calls
         final StaticEntityModel activeModel = getActiveModel(player, true);
         activeModel.resetBones();
@@ -64,12 +58,12 @@ public class MobRendererPlayer extends MobRendererBipedArmored<Player>
         activeModel.getTransform("leftSleeve").visible = player.playerConfig.sleeveLeftEnabled();
         activeModel.getTransform("rightSleeve").visible = player.playerConfig.sleeveRightEnabled();
 
-        if (isLeft){
+        if (isLeft) {
             activeModel.getTransform("rightArm").visible = false;
         } else {
             activeModel.getTransform("leftArm").visible = false;
         }
-        activeModel.render(tessellator);
+        activeModel.render();
     }
 
     public void drawHeldObject(final Player player, final float partialTick) {
@@ -78,31 +72,31 @@ public class MobRendererPlayer extends MobRendererBipedArmored<Player>
                 this.container = new BlocksContainer(player.world);
             }
 
-            final Tessellator tessellator = Tessellator.instance;
-            final Minecraft mc = Minecraft.getMinecraft();
-            TextureRegistry.blockAtlas.bind();
-            GL11.glPushMatrix();
+            final TessellatorGeneral tessellator = GLRenderer.getTessellator();
+            TextureRegistry.worldAtlas.bind();
+            GLRenderer.pushFrame();
             Lighting.disable();
 
-            GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glDisable(GL11.GL_CULL_FACE);
-            if(mc.isAmbientOcclusionEnabled()) {
-                GL11.glShadeModel(GL11.GL_SMOOTH);
-            } else {
-                GL11.glShadeModel(GL11.GL_FLAT);
-            }
-            GL11.glScalef(0.55f, -0.55f, 0.55f);
-            GL11.glTranslatef(0, -0.75f, -0.75f);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.disableState(State.CULL_FACE);
+//            if (mc.isAmbientOcclusionEnabled()) {
+//                GL11.glShadeModel(GL11.GL_SMOOTH);
+//            } else {
+//                GL11.glShadeModel(GL11.GL_FLAT);
+//            }
+            GLRenderer.modelM4f().scale(0.55f, -0.55f, 0.55f);
+            GLRenderer.modelM4f().translate(0, -0.75f, -0.75f);
 
             final TilePos blockPos = new TilePos(player.x, player.y + 1, player.z);
 
             tessellator.startDrawingQuads();
-            tessellator.setTranslation(-blockPos.x -0.5, -blockPos.y -0.5, -blockPos.z -0.5);
+            tessellator.setTranslation(-blockPos.x - 0.5, -blockPos.y - 0.5, -blockPos.z - 0.5);
 
             this.container.setLightReferenceEntity(player);
+            this.container.partialTick = partialTick;
             this.container.setBlock(blockPos.x, blockPos.y, blockPos.z, carriedBlock.blockId, carriedBlock.metadata, carriedBlock.entity);
-            BlockModelDispatcher.getInstance().getDispatch(carriedBlock.block()).renderNoCulling(Tessellator.instance, this.container, blockPos);
+            BlockModelDispatcher.getInstance().getDispatch(carriedBlock.block()).renderNoCulling(GLRenderer.getTessellator(), this.container, blockPos);
             tessellator.draw();
             tessellator.setTranslation(0, 0, 0);
             this.container.setLightReferenceEntity(null);
@@ -115,71 +109,66 @@ public class MobRendererPlayer extends MobRendererBipedArmored<Player>
                 carriedBlock.entity.worldObj = null;
             }
 
-            GL11.glPopMatrix();
-            GL11.glEnable(GL_LIGHTING);
-            GL11.glEnable(GL_LIGHT0);
-            GL11.glEnable(GL_LIGHT1);
-            GL11.glEnable(GL_COLOR_MATERIAL);
+            GLRenderer.popFrame();
+//            GL11.glEnable(GL_LIGHTING);
+//            GL11.glEnable(GL_LIGHT0);
+//            GL11.glEnable(GL_LIGHT1);
+//            GL11.glEnable(GL_COLOR_MATERIAL);
         }
     }
+
     @Override
-    protected void renderSpecials(final @NotNull Tessellator t, final @NotNull Player entity, final double x, final double y, final double z)
-    {
+    protected void renderSpecials(final @NotNull TessellatorGeneral t, final @NotNull Player entity, final double x, final double y, final double z) {
         if (Minecraft.getMinecraft().thePlayer.getGamemode() != Gamemode.spectator && entity.getGamemode() == Gamemode.spectator) {
             return;
         }
-        if(Minecraft.getMinecraft().gameSettings.immersiveMode.drawNames() && this.renderDispatcher.camera != null) // Render name
+        if (Minecraft.getMinecraft().gameSettings.immersiveMode.drawNames() && this.renderDispatcher.camera != null) // Render name
         {
-            if (this.renderDispatcher.camera instanceof EntityCamera && ((EntityCamera) this.renderDispatcher.camera).mob == entity)
-            {
+            if (this.renderDispatcher.camera instanceof EntityCamera && ((EntityCamera) this.renderDispatcher.camera).mob == entity) {
                 return;
             }
             final float f = 1.6F;
             final float f1 = 0.01666667F * f;
             final float f2 = (float) this.renderDispatcher.camera.distanceTo(entity); //getting lost on renderManager.livingPlayer
             final float f3 = entity.isSneaking() ? 32F : 64F;
-            if(f2 < f3)
-            {
+            if (f2 < f3) {
                 final String s = entity.getDisplayName();
-                if(!entity.isSneaking())
-                {
-                    if(entity.isPlayerSleeping())
-                    {
+                if (!entity.isSneaking()) {
+                    if (entity.isPlayerSleeping()) {
                         renderLivingLabel(t, entity, s, x, y - 1.5D, z, 64, false);
-                    } else
-                    {
+                    } else {
                         renderLivingLabel(t, entity, s, x, y, z, 64, false);
                     }
-                } else
-                {
+                } else {
                     final FontRenderer font = getFont();
-                    GL11.glPushMatrix();
-                    GL11.glTranslatef((float) x + 0.0F, (float) y + 2.3F, (float) z);
-                    GL11.glNormal3f(0.0F, 1.0F, 0.0F);
-                    GL11.glRotatef(-this.renderDispatcher.viewLerpYaw, 0.0F, 1.0F, 0.0F);
-                    GL11.glRotatef(this.renderDispatcher.viewLerpPitch, 1.0F, 0.0F, 0.0F);
-                    GL11.glScalef(-f1, -f1, f1);
-                    GL11.glDisable(GL11.GL_LIGHTING);
-                    GL11.glTranslatef(0.0F, 0.25F / f1, 0.0F);
-                    GL11.glDepthMask(false);
-                    GL11.glEnable(GL11.GL_BLEND);
-                    GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-                    GL11.glDisable(GL11.GL_TEXTURE_2D);
+                    GLRenderer.pushFrame();
+                    GLRenderer.modelM4f().translate((float) x + 0.0F, (float) y + 2.3F, (float) z);
+//                    GL11.glNormal3f(0.0F, 1.0F, 0.0F);
+                    GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(-this.renderDispatcher.viewLerpYaw));
+                    GLRenderer.modelM4f().rotateX(org.joml.Math.toRadians(this.renderDispatcher.viewLerpPitch));
+                    GLRenderer.modelM4f().scale(-f1, -f1, f1);
+                    GLRenderer.globalSetLightEnabled(false);
+                    GLRenderer.modelM4f().translate(0.0F, 0.25F / f1, 0.0F);
+                    GLRenderer.setDepthMask(false);
+                    GLRenderer.enableState(State.BLEND);
+                    GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+                    GLRenderer.pushFrame();
+                    GLRenderer.setShader(Shaders.COLOR);
                     t.startDrawingQuads();
                     final int halfWidth = font.stringWidth(s) / 2;
-                    t.setColorRGBA_F(0.0F, 0.0F, 0.0F, 0.25F);
+                    t.setColor4f(0.0F, 0.0F, 0.0F, 0.25F);
                     t.addVertex(-halfWidth - 1, -1D, 0.0D);
                     t.addVertex(-halfWidth - 1, 8D, 0.0D);
                     t.addVertex(halfWidth + 1, 8D, 0.0D);
                     t.addVertex(halfWidth + 1, -1D, 0.0D);
                     t.draw();
-                    GL11.glEnable(GL11.GL_TEXTURE_2D);
-                    GL11.glDepthMask(true);
-                    font.renderCentered(t, s, 0, 0).setColor(0x20ffffff).call();
-                    GL11.glEnable(GL11.GL_LIGHTING);
-                    GL11.glDisable(GL11.GL_BLEND);
-                    GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-                    GL11.glPopMatrix();
+                    GLRenderer.popFrame();
+                    GLRenderer.setDepthMask(true);
+                    font.renderCentered(s, 0, 0).setColor(0x20ffffff).call();
+                    GLRenderer.globalSetLightEnabled(true);
+                    GLRenderer.disableState(State.BLEND);
+                    GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+                    GLRenderer.popFrame();
                 }
             }
         }
@@ -187,83 +176,80 @@ public class MobRendererPlayer extends MobRendererBipedArmored<Player>
 
     @Override
     protected void preRenderTransform(@NotNull final Player entity, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        GL11.glTranslated(x, y, z);
+        GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
 
-        if(entity.isAlive() && (entity.isPlayerSleeping())) {
-            GL11.glTranslatef(entity.sleepOffX, entity.sleepOffY, entity.sleepOffZ);
+        if (entity.isAlive() && (entity.isPlayerSleeping())) {
+            GLRenderer.modelM4f().translate(entity.sleepOffX, entity.sleepOffY, entity.sleepOffZ);
 
-            GL11.glScalef(1/ENTITY_RENDER_SCALE, 1/ENTITY_RENDER_SCALE, -1/ENTITY_RENDER_SCALE);
-            GL11.glTranslatef(0, -4.5f, 0);
+            GLRenderer.modelM4f().scale(1 / ENTITY_RENDER_SCALE, 1 / ENTITY_RENDER_SCALE, -1 / ENTITY_RENDER_SCALE);
+            GLRenderer.modelM4f().translate(0, -4.5f, 0);
 
-            GL11.glRotatef(-entity.getBedOrientationInDegrees(), 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(getMaxDeathRotation(entity), 0.0F, 0.0F, 1.0F);
-            GL11.glRotatef(270F, 0.0F, 1.0F, 0.0F);
+            GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(-entity.getBedOrientationInDegrees()));
+            GLRenderer.modelM4f().rotateZ(org.joml.Math.toRadians(getMaxDeathRotation(entity)));
+            GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(270F));
 
         } else {
-            GL11.glRotatef(-getBodyYaw(entity, partialTick) * MathHelper.RAD_TO_DEG, 0, 1, 0);
-            GL11.glScalef(1/ENTITY_RENDER_SCALE, 1/ENTITY_RENDER_SCALE, -1/ENTITY_RENDER_SCALE);
+            GLRenderer.modelM4f().rotateY(-getBodyYaw(entity, partialTick));
+            GLRenderer.modelM4f().scale(1 / ENTITY_RENDER_SCALE, 1 / ENTITY_RENDER_SCALE, -1 / ENTITY_RENDER_SCALE);
         }
 
-        if(entity.deathTime > 0) {
+        if (entity.deathTime > 0) {
             float rotationProgress = (((entity.deathTime + partialTick) - 1.0F) / 20F) * 1.6F;
             rotationProgress = MathHelper.sqrt_float(rotationProgress);
-            if(rotationProgress > 1.0F) {
+            if (rotationProgress > 1.0F) {
                 rotationProgress = 1.0F;
             }
-            GL11.glRotatef(rotationProgress * getMaxDeathRotation(entity), 0.0F, 0.0F, 1.0F);
+            GLRenderer.modelM4f().rotateZ(org.joml.Math.toRadians(rotationProgress * getMaxDeathRotation(entity)));
         }
 
 
         final float scale = 0.9375F;
-        GL11.glScalef(scale, scale, scale);
+        GLRenderer.modelM4f().scale(scale, scale, scale);
 
         if (entity.isDwarf()) {
-            GL11.glScalef(0.6f, 0.5f, 0.6f);
+            GLRenderer.modelM4f().scale(0.6f, 0.5f, 0.6f);
         }
 
         if (Specials.getSpecialsForPlayer(entity) == Specials.MELON || Specials.getSpecialsForPlayer(entity) == Specials.WATERMELON) {
-            GL11.glScalef(0.9f, 0.9f, 0.9f);
+            GLRenderer.modelM4f().scale(0.9f, 0.9f, 0.9f);
         }
 
 
     }
 
     @Override
-    protected void renderAdditional(@NotNull final Tessellator tessellator, final @NotNull Player player, final float partialTick)
-    {
+    protected void renderAdditional(@NotNull final TessellatorGeneral tessellator, final @NotNull Player player, final float partialTick) {
         final StaticEntityModel activeModel = getActiveModel(player, false);
 
         super.renderAdditional(tessellator, player, partialTick);
 
         if (player.playerConfig.capeEnabled()) {
             boolean renderCape = bindDownloadableTexture("https://api.betterthanadventure.net/capes?username=" + player.username, null, null);
-            if (!renderCape)
-            {
+            if (!renderCape) {
                 renderCape = bindDownloadableTexture(player.capeURL, null, null);
             }
 
-            if(renderCape) {
-                GL11.glPushMatrix();
-                final float brightness = (Global.accessor.isFullbrightEnabled() || LightmapHelper.isLightmapEnabled()) ? 1 : player.getBrightness(partialTick);
-                GL11.glColor4f(brightness, brightness, brightness, 1f);
-                GL11.glTranslatef(0.0F, 0.0F, 0.125F);
+            if (renderCape) {
+                GLRenderer.pushFrame();
+                GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+                GLRenderer.modelM4f().translate(0.0F, 0.0F, 0.125F);
                 final float yawOff = player.yBodyRotO + (player.yBodyRot - player.yBodyRotO) * partialTick;
                 final float bodyAngle = 5;
                 final double xd = MathHelper.lerp(player.xdO, player.xd, partialTick);
                 final double yd = Math.min(MathHelper.lerp(player.ydO, player.yd, partialTick), 0);
                 final double zd = MathHelper.lerp(player.zdO, player.zd, partialTick);
-                final double vel = -1/(3 * Math.hypot(xd, zd) + 1) + 1;
+                final double vel = -1 / (3 * Math.hypot(xd, zd) + 1) + 1;
                 final double moveAng = Math.atan2(xd, zd);
                 final double yawRad = Math.toRadians(yawOff);
-                final double multiplier = 1 - Math.abs((((Math.cos(yawRad) + 1) - (Math.cos(moveAng) + 1) + 2)/2) -1); // Hell code, basically measures how similar the angle you're facing is to the angle you're moving, with it returning 1 if the same angle and 0 if opposite angles
-                player.wobbleTimer += (float) (((player.tickCount + partialTick) - player.lastRenderTick)/(30 - 29 * MathHelper.clamp(vel, 0, 1)));
+                final double multiplier = 1 - Math.abs((((Math.cos(yawRad) + 1) - (Math.cos(moveAng) + 1) + 2) / 2) - 1); // Hell code, basically measures how similar the angle you're facing is to the angle you're moving, with it returning 1 if the same angle and 0 if opposite angles
+                player.wobbleTimer += (float) (((player.tickCount + partialTick) - player.lastRenderTick) / (30 - 29 * MathHelper.clamp(vel, 0, 1)));
                 player.lastRenderTick = player.tickCount;
                 final double wobble = Math.sin(player.wobbleTimer) * (1.5 + 4.5 * vel * multiplier);
                 activeModel.translateToBone("cape");
                 final StaticEntityModel cape = getModel("cape");
                 cape.getTransform("cape").rotX = -MathHelper.clamp((MathHelper.clamp(bodyAngle + vel * 100 * multiplier, bodyAngle, 100f) + wobble) - yd * 60, 0, 180) * MathHelper.DEG_TO_RAD;
-                cape.render(tessellator);
-                GL11.glPopMatrix();
+                cape.render();
+                GLRenderer.popFrame();
             }
         }
 
@@ -272,12 +258,12 @@ public class MobRendererPlayer extends MobRendererBipedArmored<Player>
             final float walkProgress = player.walkAnimPos - player.walkAnimSpeed * (1.0F - partialTick);
             final float swingProgress = player.getSwingProgress(partialTick);
             final float swing = MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * -2.0F) * 0.4F;
-            GL11.glTranslatef(0, (MathHelper.cos(walkProgress/2 * 2/3f + MathHelper.PI)/12f * walkSpeed + 0.1f - swing/4f) * ENTITY_RENDER_SCALE, 0);
-            GL11.glTranslatef(0, 1.25f * ENTITY_RENDER_SCALE, 0);
+            GLRenderer.modelM4f().translate(0, (MathHelper.cos(walkProgress / 2 * 2 / 3f + MathHelper.PI) / 12f * walkSpeed + 0.1f - swing / 4f) * ENTITY_RENDER_SCALE, 0);
+            GLRenderer.modelM4f().translate(0, 1.25f * ENTITY_RENDER_SCALE, 0);
             if (player.isSneaking()) {
-                GL11.glTranslatef(0, 0, 4);
+                GLRenderer.modelM4f().translate(0, 0, 4);
             }
-            GL11.glScalef(-ENTITY_RENDER_SCALE, -ENTITY_RENDER_SCALE, ENTITY_RENDER_SCALE);
+            GLRenderer.modelM4f().scale(-ENTITY_RENDER_SCALE, -ENTITY_RENDER_SCALE, ENTITY_RENDER_SCALE);
             drawHeldObject(player, partialTick);
         }
     }
@@ -341,7 +327,8 @@ public class MobRendererPlayer extends MobRendererBipedArmored<Player>
         }
 
         public static @Nullable Specials getSpecialsForPlayer(final @NotNull Player player) {
-            if (!Minecraft.getMinecraft().gameSettings.devModels.value || !player.playerConfig.devModelEnabled()) return null;
+            if (!Minecraft.getMinecraft().gameSettings.devModels.value || !player.playerConfig.devModelEnabled())
+                return null;
             if (player.uuid.equals(SHIGN.uuid) || player.username.equals(SHIGN.username)) return SHIGN;
             if (player.uuid.equals(COOKIE.uuid) || player.username.equals(COOKIE.username)) return COOKIE;
             if (player.uuid.equals(THA_BOAR.uuid) || player.username.equals(THA_BOAR.username)) return THA_BOAR;
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSheep.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSheep.java
index a10ef2547..fa28ac2ce 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSheep.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSheep.java
@@ -1,10 +1,10 @@
 package net.minecraft.client.render.entity;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.entity.animal.MobSheep;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
@@ -20,7 +20,7 @@ public class MobRendererSheep extends MobRenderer<MobSheep> {
         switch (layer) {
             case 1:
                 final int colorIndex = entity.getFleeceColor().blockMeta;
-                GL11.glColor3f(brightness * MobSheep.FLEECE_COLOR_TABLE[colorIndex][0], brightness * MobSheep.FLEECE_COLOR_TABLE[colorIndex][1], brightness * MobSheep.FLEECE_COLOR_TABLE[colorIndex][2]);
+                GLRenderer.setColor3f(brightness * MobSheep.FLEECE_COLOR_TABLE[colorIndex][0], brightness * MobSheep.FLEECE_COLOR_TABLE[colorIndex][1], brightness * MobSheep.FLEECE_COLOR_TABLE[colorIndex][2]);
                 model = getModel("main");
                 bindTexture("/assets/minecraft/textures/entity/sheep/wool_overlay.png");
                 break;
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSlime.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSlime.java
index 7276fbd6a..e493129a8 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSlime.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSlime.java
@@ -1,16 +1,16 @@
 package net.minecraft.client.render.entity;
 
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.entity.monster.MobSlime;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
-public class MobRendererSlime extends MobRenderer<MobSlime>
-{
+public class MobRendererSlime extends MobRenderer<MobSlime> {
 
     public MobRendererSlime(final float shadowSize) {
         super(shadowSize);
@@ -19,9 +19,9 @@ public class MobRendererSlime extends MobRenderer<MobSlime>
     @Override
     protected @Nullable StaticEntityModel getAndSetupModelForLayer(@NotNull final MobSlime entity, final float brightness, final float partialTick, final int layer) {
         final StaticEntityModel model = getModel("main");
-        GL11.glEnable(GL12.GL_NORMALIZE);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+//        GL11.glEnable(GL12.GL_NORMALIZE);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
 
         model.resetBones();
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSpider.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSpider.java
index 27c354d3b..fb07dd858 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSpider.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSpider.java
@@ -1,6 +1,9 @@
 package net.minecraft.client.render.entity;
 
 import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.entity.monster.MobSpider;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
@@ -19,15 +22,10 @@ public class MobRendererSpider extends MobRenderer<MobSpider> {
     protected @Nullable StaticEntityModel getAndSetupModelForLayer(@NotNull final MobSpider entity, final float brightness, final float partialTick, final int layer) {
         if (layer == 1) {
             bindTexture("/assets/minecraft/textures/entity/spider/eyes/" + entity.getTextureReference() + ".png");
-            if(LightmapHelper.isLightmapEnabled()) LightmapHelper.setLightmapCoord(LightmapHelper.getOverbrightLightmapCoord(15));
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glDisable(GL11.GL_ALPHA_TEST);
-            GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, (1.0F - entity.getBrightness(partialTick)) * 0.5F);
-        } else if (layer == 2) {
-            GL11.glDisable(GL11.GL_BLEND);
-            GL11.glEnable(GL11.GL_ALPHA_TEST);
-            return null;
+            GLRenderer.setLightmapCoord1i(LightmapHelper.getOverbrightLightmapCoord(15));
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, (1.0F - entity.getBrightness(partialTick)) * 0.5F);
         }
 
         final StaticEntityModel model = getModel("main");
@@ -55,22 +53,22 @@ public class MobRendererSpider extends MobRenderer<MobSpider> {
 
         final double rZ = 45 * MathHelper.DEG_TO_RAD;
         leg0.rotZ = -rZ;
-        leg1.rotZ =  rZ;
+        leg1.rotZ = rZ;
         leg2.rotZ = -rZ * 0.74F;
-        leg3.rotZ =  rZ * 0.74F;
+        leg3.rotZ = rZ * 0.74F;
         leg4.rotZ = -rZ * 0.74F;
-        leg5.rotZ =  rZ * 0.74F;
+        leg5.rotZ = rZ * 0.74F;
         leg6.rotZ = -rZ;
-        leg7.rotZ =  rZ;
+        leg7.rotZ = rZ;
         final double ry = 22.5 * MathHelper.DEG_TO_RAD;
-        leg0.rotY =  ry * 2.0F;
+        leg0.rotY = ry * 2.0F;
         leg1.rotY = -ry * 2.0F;
-        leg2.rotY =  ry;
+        leg2.rotY = ry;
         leg3.rotY = -ry;
         leg4.rotY = -ry;
-        leg5.rotY =  ry;
+        leg5.rotY = ry;
         leg6.rotY = -ry * 2.0;
-        leg7.rotY =  ry * 2.0F;
+        leg7.rotY = ry * 2.0F;
         final double pair1Y = -(MathHelper.cos(limbSwing * 0.6662F * 2.0F + 0.0F) * 0.4F) * limbYaw;
         final double pair2Y = -(MathHelper.cos(limbSwing * 0.6662F * 2.0F + MathHelper.PI) * 0.4F) * limbYaw;
         final double pair3Y = -(MathHelper.cos(limbSwing * 0.6662F * 2.0F + MathHelper.PI / 2F) * 0.4F) * limbYaw;
@@ -105,6 +103,6 @@ public class MobRendererSpider extends MobRenderer<MobSpider> {
 
     @Override
     protected int maxRenderLayer(@NotNull final MobSpider entity) {
-        return 2;
+        return 1;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSquid.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSquid.java
index ddd6858d4..87a2d73b9 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSquid.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererSquid.java
@@ -1,11 +1,12 @@
 package net.minecraft.client.render.entity;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.animal.MobSquid;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
+import org.joml.Math;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
 public class MobRendererSquid extends MobRenderer<MobSquid> {
@@ -33,32 +34,31 @@ public class MobRendererSquid extends MobRenderer<MobSquid> {
     }
 
     @Override
-    protected float getLimbPitch(final @NotNull MobSquid squid, final float partialTick)
-    {
+    protected float getLimbPitch(final @NotNull MobSquid squid, final float partialTick) {
         return MathHelper.lerp(squid.oldTentacleAngle, squid.tentacleAngle, partialTick);
     }
 
     @Override
     protected void preRenderTransform(@NotNull final MobSquid entity, final double x, final double y, final double z, final float _yaw, final float partialTick) {
         if (entity.isSpecial()) {
-            GL11.glTranslated(0, 1.5, 0);
+            GLRenderer.modelM4f().translate(0, 1.5f, 0);
             super.preRenderTransform(entity, x, y, z, _yaw, partialTick);
         } else {
-            GL11.glTranslated(x, y + 0.5, z);
-            GL11.glScalef(1/ MobRenderer.ENTITY_RENDER_SCALE, 1/ MobRenderer.ENTITY_RENDER_SCALE, 1/ MobRenderer.ENTITY_RENDER_SCALE);
+            GLRenderer.modelM4f().translate((float) x, (float) (y + 0.5), (float) z);
+            GLRenderer.modelM4f().scale(1 / MobRenderer.ENTITY_RENDER_SCALE, 1 / MobRenderer.ENTITY_RENDER_SCALE, 1 / MobRenderer.ENTITY_RENDER_SCALE);
             final float pitch = entity.xBodyRotO + (entity.xBodyRot - entity.xBodyRotO) * partialTick;
             final float yaw = entity.zBodyRotO + (entity.zBodyRot - entity.zBodyRotO) * partialTick;
-            GL11.glRotatef(180 - getBodyYaw(entity, partialTick) * MathHelper.RAD_TO_DEG, 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(pitch, 1.0F, 0.0F, 0.0F);
-            GL11.glRotatef(yaw, 0.0F, 1.0F, 0.0F);
+            GLRenderer.modelM4f().rotateY(Math.PI_f - getBodyYaw(entity, partialTick));
+            GLRenderer.modelM4f().rotateX(Math.toRadians(pitch));
+            GLRenderer.modelM4f().rotateY(Math.toRadians(yaw));
         }
     }
 
     @Override
-    public void renderPreview(@NotNull final Tessellator tessellator, @NotNull final MobSquid squid, final double x, final double y, final double z, final float yaw, final float partialTick) {
-        GL11.glPushMatrix();
-        GL11.glTranslatef(0.0f, 1.25f, 0.0f);
-        super.renderPreview(tessellator,squid, x, y, z, yaw, partialTick);
-        GL11.glPopMatrix();
+    public void renderPreview(@NotNull final TessellatorGeneral tessellator, @NotNull final MobSquid squid, final double x, final double y, final double z, final float yaw, final float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate(0.0f, 1.25f, 0.0f);
+        super.renderPreview(tessellator, squid, x, y, z, yaw, partialTick);
+        GLRenderer.popFrame();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererWolf.java b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererWolf.java
index f4f239602..6413e042e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererWolf.java
+++ b/game/client/src/main/java/net/minecraft/client/render/entity/MobRendererWolf.java
@@ -2,15 +2,15 @@ package net.minecraft.client.render.entity;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.animal.MobWolf;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.item.material.ArmorMaterial;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 import org.useless.dragonfly.DisplayPos;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
@@ -49,15 +49,12 @@ public class MobRendererWolf extends MobRenderer<MobWolf> {
         final float limbYaw = getLimbYaw(entity, partialTick);
         final float limbPitch = getLimbPitch(entity, partialTick);
 
-        if(entity.isWolfAngry())
-        {
+        if (entity.isWolfAngry()) {
             tail.rotY = 0.0F;
-        } else
-        {
+        } else {
             tail.rotY = MathHelper.cos(limbSwing * 0.6662F) * 1.4F * limbYaw;
         }
-        if(entity.isWolfSitting())
-        {
+        if (entity.isWolfSitting()) {
             body.rotX = -33.5 * MathHelper.DEG_TO_RAD;
             body.posY = -4.5;
             body.posZ = -2;
@@ -81,8 +78,7 @@ public class MobRendererWolf extends MobRenderer<MobWolf> {
 
             tail.posY = -9;
             tail.posZ = -3;
-        } else
-        {
+        } else {
             leg0.rotX = MathHelper.cos(limbSwing * 0.6662F) * 1.4F * limbYaw;
             leg1.rotX = MathHelper.cos(limbSwing * 0.6662F + MathHelper.PI) * 1.4F * limbYaw;
             leg2.rotX = MathHelper.cos(limbSwing * 0.6662F + MathHelper.PI) * 1.4F * limbYaw;
@@ -93,10 +89,9 @@ public class MobRendererWolf extends MobRenderer<MobWolf> {
         body.rotZ = entity.getShakeAngle(partialTick, -0.16F);
         tail.rotZ = entity.getShakeAngle(partialTick, -0.2F);
 
-        if(entity.getWolfShaking())
-        {
+        if (entity.getWolfShaking()) {
             final float shading = brightness * entity.getShadingWhileShaking(partialTick);
-            GL11.glColor3f(shading, shading, shading);
+            GLRenderer.setColor3f(shading, shading, shading);
         }
 
         head.rotX = headPitch;
@@ -112,35 +107,30 @@ public class MobRendererWolf extends MobRenderer<MobWolf> {
     }
 
     @Override
-    protected float getLimbPitch(final @NotNull MobWolf wolf, final float partialTick)
-    {
-        if(wolf.isWolfAngry())
-        {
+    protected float getLimbPitch(final @NotNull MobWolf wolf, final float partialTick) {
+        if (wolf.isWolfAngry()) {
             return 88 * MathHelper.DEG_TO_RAD;
-        }
-        else if(wolf.isWolfTamed())
-        {
-            return (0.55F - (float)(wolf.getMaxHealth() - wolf.getHealth()) * 0.02F) * MathHelper.PI;
-        } else
-        {
+        } else if (wolf.isWolfTamed()) {
+            return (0.55F - (float) (wolf.getMaxHealth() - wolf.getHealth()) * 0.02F) * MathHelper.PI;
+        } else {
             return 36 * MathHelper.DEG_TO_RAD;
         }
     }
 
     @Override
-    protected void renderAdditional(@NotNull final Tessellator tessellator, final @NotNull MobWolf entity, final float partialTick){
+    protected void renderAdditional(@NotNull final TessellatorGeneral tessellator, final @NotNull MobWolf entity, final float partialTick) {
         final ItemStack itemstack = entity.getHeldItem();
 
-        if(itemstack != null) {
-            GL11.glPushMatrix();
+        if (itemstack != null) {
+            GLRenderer.pushFrame();
             getModel("main").translateToBone("mouthItem");
-            GL11.glScalef(MobRenderer.ENTITY_RENDER_SCALE, -MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE);
-            GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-            GL11.glEnable(GL11.GL_BLEND);
-            ItemModelDispatcher.getInstance().getDispatch(itemstack).render(Tessellator.instance, entity, itemstack, DisplayPos.GROUND, Minecraft.getMinecraft().gameSettings.items3D.value, 1, entity.getBrightness(partialTick), 1f, partialTick, true);
-            GL11.glDisable(GL11.GL_BLEND);
-            GL11.glDisable(GL12.GL_RESCALE_NORMAL);
-            GL11.glPopMatrix();
+            GLRenderer.modelM4f().scale(MobRenderer.ENTITY_RENDER_SCALE, -MobRenderer.ENTITY_RENDER_SCALE, MobRenderer.ENTITY_RENDER_SCALE);
+//            GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+            GLRenderer.enableState(State.BLEND);
+            ItemModelDispatcher.getInstance().getDispatch(itemstack).render(GLRenderer.getTessellator(), entity, itemstack, DisplayPos.GROUND, Minecraft.getMinecraft().gameSettings.items3D.value, 1, entity.getLightmap(partialTick), partialTick, true);
+            GLRenderer.disableState(State.BLEND);
+//            GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+            GLRenderer.popFrame();
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/Font.java b/game/client/src/main/java/net/minecraft/client/render/font/Font.java
index 1cdd19a31..316a08e2a 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/Font.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/Font.java
@@ -1,6 +1,6 @@
 package net.minecraft.client.render.font;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorFont;
 import net.minecraft.client.render.texturepack.TexturePackList;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
@@ -24,5 +24,5 @@ public interface Font {
 
     int fontHeight();
 
-    double renderChar(Tessellator tessellator, char c, double x, double y, double z, boolean italics);
+    double renderChar(TessellatorFont tessellator, char c, double x, double y, double z, boolean italics);
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/FontDefault.java b/game/client/src/main/java/net/minecraft/client/render/font/FontDefault.java
index fe7abeb4b..50e03f9e1 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/FontDefault.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/FontDefault.java
@@ -1,7 +1,7 @@
 package net.minecraft.client.render.font;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorFont;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.core.util.helper.ChatAllowedCharacters;
 import org.jetbrains.annotations.NotNull;
@@ -47,7 +47,7 @@ public class FontDefault extends FontFile {
     }
 
     @Override
-    public double renderChar(final Tessellator tessellator, final char c, final double x, final double y, final double z, final boolean italics) {
+    public double renderChar(final TessellatorFont tessellator, final char c, final double x, final double y, final double z, final boolean italics) {
         if (c == ' ') return 4;
         final int fontIndex = ChatAllowedCharacters.ALLOWED_CHARACTERS.indexOf(c);
         if (fontIndex < 0) return 0;
@@ -56,28 +56,20 @@ public class FontDefault extends FontFile {
 
         final int upper = this.charWidth[fontIndex] >> 4;
         final int lower = this.charWidth[fontIndex] & 0x0F;
-        final double fUpper = upper;
-        final double fLower = (lower + 1);
+        final int fUpper = upper;
+        final int fLower = (lower + 1);
         if (fLower - fUpper == 0) return 0;
 
-        final double epsilon = 0.02/256;
-        final double u = (fontIndex % 16 * 16) + fUpper;
-        final double v = (fontIndex & 255) / 16 * 16;
-        final double uWidth = fLower - fUpper;
-        final double vHeight = 16d;
-
-        final double uMin = u / 256d;
-        final double uMax = (u + uWidth) / 256d;
-        final double vMin = v / 256d;
-        final double vMax = (v + vHeight) / 256d;
+        final int u = (fontIndex % 16 * 16) + fUpper;
+        final int v = (fontIndex & 0xff) / 16 * 16;
+        final int uWidth = fLower - fUpper;
+        final int vHeight = 16;
 
         final double width = uWidth/2d;
         final double height = vHeight/2d;
 
-        tessellator.addVertexWithUV(x + shift,          y,           z, uMin + epsilon, vMin + epsilon);
-        tessellator.addVertexWithUV(x - shift,          y + height,  z, uMin + epsilon, vMax - epsilon);
-        tessellator.addVertexWithUV(x - shift + width,  y + height,  z, uMax - epsilon, vMax - epsilon);
-        tessellator.addVertexWithUV(x + shift + width,  y,           z, uMax - epsilon, vMin + epsilon);
+        tessellator.addChar(x, y, width, height, shift, u/256d, v/256d, uWidth/256d, vHeight/256d);
+
         return (fLower - fUpper)/2d + 1;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/FontFile.java b/game/client/src/main/java/net/minecraft/client/render/font/FontFile.java
index be72ac583..58dc898fc 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/FontFile.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/FontFile.java
@@ -1,7 +1,8 @@
 package net.minecraft.client.render.font;
 
+import it.unimi.dsi.fastutil.objects.ObjectArrayList;
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorFont;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.client.render.texturepack.TexturePackList;
 import net.minecraft.core.util.helper.ChatAllowedCharacters;
@@ -18,9 +19,10 @@ public class FontFile implements Font {
      * Some characters somehow are recognized as "default" characters while their rendering is not supported.
      * Have to delete this once workarounds are found.
      */
-    protected static final List<Character> DEFAULT_BLACKLIST = Arrays.asList(
-        '\uff0c', '\u3002', '\u3001', '\u3010', '\u3011', '\uff1b', '\u2019', '\u2018', '\u201c', '\u201d', '\uff1f', '\uff01', '\u00b7'
-    );
+    protected static final List<Character> DEFAULT_BLACKLIST = new ObjectArrayList<>();
+    static {
+        DEFAULT_BLACKLIST.addAll(Arrays.asList('\uff0c', '\u3002', '\u3001', '\u3010', '\u3011', '\uff1b', '\u2019', '\u2018', '\u201c', '\u201d', '\uff1f', '\uff01', '\u00b7'));
+    }
 
     protected static final int ITALICS_SHIFT = 1;
     protected static final int GLYPHS_PER_TEXTURE = 256;
@@ -108,34 +110,26 @@ public class FontFile implements Font {
     }
 
     @Override
-    public double renderChar(final Tessellator tessellator, final char c, final double x, final double y, final double z, final boolean italics) {
+    public double renderChar(final TessellatorFont tessellator, final char c, final double x, final double y, final double z, final boolean italics) {
         if (c == ' ') return 4;
         final int shift = italics ? ITALICS_SHIFT : 0;
 
         final int upper = this.charWidth[c] >> 4;
         final int lower = this.charWidth[c] & 0x0F;
-        final double fUpper = upper;
-        final double fLower = (lower + 1);
+        final int fUpper = upper;
+        final int fLower = (lower + 1);
         if (fLower - fUpper == 0) return 0;
 
-        final double epsilon = 0.02/256;
-        final double u = (c % 16 * 16) + fUpper;
-        final double v = (c & 255) / 16 * 16;
-        final double uWidth = fLower - fUpper;
-        final double vHeight = 16d;
-
-        final double uMin = u / 256d;
-        final double uMax = (u + uWidth) / 256d;
-        final double vMin = v / 256d;
-        final double vMax = (v + vHeight) / 256d;
+        final int u = (c % 16 * 16) + fUpper;
+        final int v = (c & 255) / 16 * 16;
+        final int uWidth = fLower - fUpper;
+        final int vHeight = 16;
 
         final double width = uWidth/2d;
         final double height = vHeight/2d;
 
-        tessellator.addVertexWithUV(x + shift,          y,           z, uMin + epsilon, vMin + epsilon);
-        tessellator.addVertexWithUV(x - shift,          y + height,  z, uMin + epsilon, vMax - epsilon);
-        tessellator.addVertexWithUV(x - shift + width,  y + height,  z, uMax - epsilon, vMax - epsilon);
-        tessellator.addVertexWithUV(x + shift + width,  y,           z, uMax - epsilon, vMin + epsilon);
+        tessellator.addChar(x, y, width, height, shift, u/256d, v/256d, uWidth/256d, vHeight/256d);
+
         return (fLower - fUpper)/2d + 1;
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/FontMonospace.java b/game/client/src/main/java/net/minecraft/client/render/font/FontMonospace.java
index fbb29546b..254252278 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/FontMonospace.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/FontMonospace.java
@@ -1,6 +1,6 @@
 package net.minecraft.client.render.font;
 
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorFont;
 import net.minecraft.client.render.texturepack.TexturePackList;
 import net.minecraft.core.util.helper.ChatAllowedCharacters;
 import org.jetbrains.annotations.NotNull;
@@ -31,34 +31,25 @@ public class FontMonospace extends FontFile{
     }
 
     @Override
-    public double renderChar(final Tessellator tessellator, final char c, final double x, final double y, final double z, final boolean italics) {
+    public double renderChar(final TessellatorFont tessellator, final char c, final double x, final double y, final double z, final boolean italics) {
         if (c != ' ') {
             final int shift = italics ? ITALICS_SHIFT : 0;
             final int fontIndex = ChatAllowedCharacters.ALLOWED_CHARACTERS.indexOf(c);
             if (fontIndex < 0) return 0;
 
-            final double epsilon = 0.02/256;
             final int upper = this.charWidth[fontIndex] >> 4;
             final int lower = this.charWidth[fontIndex] & 0x0F;
-            final double fUpper = upper;
-            final double fLower = (lower + 1);
-            final double u = (fontIndex % 16 * 16) + fUpper;
-            final double v = (fontIndex & 255) / 16 * 16;
-            final double uWidth = fLower - fUpper;
-            final double vHeight = 16d;
-
-            final double uMin = u / 256d;
-            final double uMax = (u + uWidth) / 256d;
-            final double vMin = v / 256d;
-            final double vMax = (v + vHeight) / 256d;
+            final int fUpper = upper;
+            final int fLower = (lower + 1);
+            final int u = (fontIndex % 16 * 16) + fUpper;
+            final int v = (fontIndex & 255) / 16 * 16;
+            final int uWidth = fLower - fUpper;
+            final int vHeight = 16;
 
             final double width = uWidth/2d;
             final double height = vHeight/2d;
 
-            tessellator.addVertexWithUV(x + shift,          y,           z, uMin + epsilon, vMin + epsilon);
-            tessellator.addVertexWithUV(x - shift,          y + height,  z, uMin + epsilon, vMax - epsilon);
-            tessellator.addVertexWithUV(x - shift + width,  y + height,  z, uMax - epsilon, vMax - epsilon);
-            tessellator.addVertexWithUV(x + shift + width,  y,           z, uMax - epsilon, vMin + epsilon);
+            tessellator.addChar(x, y, width, height, shift, u/256d, v/256d, uWidth/256d, vHeight/256d);
         }
         return MONOSPACE_WIDTH / 2d + 1;
     }
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/FontRenderer.java b/game/client/src/main/java/net/minecraft/client/render/font/FontRenderer.java
index 9bdc88504..08c4e334a 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/FontRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/FontRenderer.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.render.font;
 
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
@@ -13,120 +12,120 @@ public abstract class FontRenderer {
     protected static final @NotNull String NULL_STRING = String.valueOf((Object) null);
 
     private static final RenderIntegerBase method_render = new RenderIntegerBase() { @Override public void call() {
-        this.fontRenderer.renderImpl(this.font, this.tessellator, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
+        this.fontRenderer.renderImpl(this.font, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
 
     private static final RenderDoubleBase method_renderDouble = new RenderDoubleBase() { @Override public void call() {
-        this.fontRenderer.renderDoubleImpl(this.font, this.tessellator, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
+        this.fontRenderer.renderDoubleImpl(this.font, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
 
     private static final RenderIntegerBase method_renderCentered = new RenderIntegerBase() { @Override public void call() {
-        this.fontRenderer.renderCenteredImpl(this.font, this.tessellator, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
+        this.fontRenderer.renderCenteredImpl(this.font, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
 
     private static final RenderDoubleBase method_renderCenteredDouble = new RenderDoubleBase() { @Override public void call() {
-        this.fontRenderer.renderCenteredDoubleImpl(this.font, this.tessellator, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
+        this.fontRenderer.renderCenteredDoubleImpl(this.font, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
 
     private static final RenderIntegerConstrainedBase method_renderWidthConstrained = new RenderIntegerConstrainedBase() { @Override public void call() {
-        this.fontRenderer.renderWidthConstrainedImpl(this.font, this.tessellator, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.maxWidth, this.alignment, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
+        this.fontRenderer.renderWidthConstrainedImpl(this.font, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.maxWidth, this.alignment, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
 
     private static final RenderDoubleConstrainedBase method_renderWidthConstrainedDouble = new RenderDoubleConstrainedBase() { @Override public void call() {
-        this.fontRenderer.renderWidthConstrainedDoubleImpl(this.font, this.tessellator, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.maxWidth, this.alignment, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
+        this.fontRenderer.renderWidthConstrainedDoubleImpl(this.font, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.maxWidth, this.alignment, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
 
     private static final RenderIntegerConstrainedBase method_renderConstrained = new RenderIntegerConstrainedBase() { @Override public void call() {
-        this.fontRenderer.renderConstrainedImpl(this.font, this.tessellator, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.maxWidth, this.maxHeight, this.alignment, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
+        this.fontRenderer.renderConstrainedImpl(this.font, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.maxWidth, this.maxHeight, this.alignment, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
 
     private static final RenderDoubleConstrainedBase method_renderConstrainedDouble = new RenderDoubleConstrainedBase() { @Override public void call() {
-        this.fontRenderer.renderConstrainedDoubleImpl(this.font, this.tessellator, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.maxWidth, this.maxHeight, this.alignment, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
+        this.fontRenderer.renderConstrainedDoubleImpl(this.font, this.chars, this.x, this.y, this.z, this.shadow, this.config, this.maxWidth, this.maxHeight, this.alignment, this.xPosBuffer, this.yPosBuffer, this.configBuffer); this.needCall = false; }};
 
     private final double @NotNull [] xPosBuffer = new double[1];
     private final double @NotNull [] yPosBuffer = new double[1];
     private final long @NotNull [] configBuffer = new long[1];
 
-    abstract void renderImpl(@NotNull Font font, @NotNull Tessellator tessellator, @NotNull CharSequence chars, int x, int y, double z, boolean shadow, long baseConfig, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, @Nullable final Object o, final int x, final int y) { return render(tessellator, String.valueOf(o), x, y); }
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, final boolean b, final int x, final int y) { return method_render.init(this, tessellator, Boolean.toString(b), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, final int i, final int x, final int y) { return method_render.init(this, tessellator, Integer.toString(i), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, final long l, final int x, final int y) { return method_render.init(this, tessellator, Long.toString(l), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, final char c, final int x, final int y) { return method_render.init(this, tessellator, String.valueOf(c), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, final float f, final int x, final int y) { return method_render.init(this, tessellator, Float.toString(f), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, final double d, final int x, final int y) { return method_render.init(this, tessellator, Double.toString(d), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, final char @Nullable [] cArr, final int x, final int y) { return method_render.init(this, tessellator, cArr == null ? NULL_STRING : new String(cArr), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase render(@NotNull final Tessellator tessellator, @Nullable final CharSequence chars, final int x, final int y) {return method_render.init(this, tessellator, chars == null ? NULL_STRING : chars, x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-
-    abstract void renderDoubleImpl(@NotNull Font font, @NotNull Tessellator tessellator, @NotNull CharSequence chars, double x, double y, double z, boolean shadow, long baseConfig, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, @Nullable final Object o, final double x, final double y) { return renderDouble(tessellator, String.valueOf(o), x, y); }
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, final boolean b, final double x, final double y) { return method_renderDouble.init(this, tessellator, Boolean.toString(b), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, final int i, final double x, final double y) { return method_renderDouble.init(this, tessellator, Integer.toString(i), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, final long l, final double x, final double y) { return method_renderDouble.init(this, tessellator, Long.toString(l), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, final char c, final double x, final double y) { return method_renderDouble.init(this, tessellator, String.valueOf(c), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, final float f, final double x, final double y) { return method_renderDouble.init(this, tessellator, Float.toString(f), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, final double d, final double x, final double y) { return method_renderDouble.init(this, tessellator, Double.toString(d), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, final char @Nullable [] cArr, final double x, final double y) { return method_renderDouble.init(this, tessellator, cArr == null ? NULL_STRING : new String(cArr), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderDouble(@NotNull final Tessellator tessellator, @Nullable final CharSequence chars, final double x, final double y) {return method_renderDouble.init(this, tessellator, chars == null ? NULL_STRING : chars, x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-
-    abstract void renderCenteredImpl(@NotNull Font font, @NotNull Tessellator tessellator, @NotNull CharSequence chars, int x, int y, double z, boolean shadow, long baseConfig, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, @Nullable final Object o, final int x, final int y) { return renderCentered(tessellator, String.valueOf(o), x, y); }
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, final boolean b, final int x, final int y) { return method_renderCentered.init(this, tessellator, Boolean.toString(b), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, final int i, final int x, final int y) { return method_renderCentered.init(this, tessellator, Integer.toString(i), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, final long l, final int x, final int y) { return method_renderCentered.init(this, tessellator, Long.toString(l), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, final char c, final int x, final int y) { return method_renderCentered.init(this, tessellator, String.valueOf(c), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, final float f, final int x, final int y) { return method_renderCentered.init(this, tessellator, Float.toString(f), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, final double d, final int x, final int y) { return method_renderCentered.init(this, tessellator, Double.toString(d), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, final char @Nullable [] cArr, final int x, final int y) { return method_renderCentered.init(this, tessellator, cArr == null ? NULL_STRING : new String(cArr), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerBase renderCentered(@NotNull final Tessellator tessellator, @Nullable final CharSequence chars, final int x, final int y) {return method_renderCentered.init(this, tessellator, chars == null ? NULL_STRING : chars, x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-
-    abstract void renderCenteredDoubleImpl(@NotNull Font font, @NotNull Tessellator tessellator, @NotNull CharSequence chars, double x, double y, double z, boolean shadow, long baseConfig, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, @Nullable final Object o, final double x, final double y) { return renderCenteredDouble(tessellator, String.valueOf(o), x, y); }
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, final boolean b, final double x, final double y) { return method_renderCenteredDouble.init(this, tessellator, Boolean.toString(b), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, final int i, final double x, final double y) { return method_renderCenteredDouble.init(this, tessellator, Integer.toString(i), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, final long l, final double x, final double y) { return method_renderCenteredDouble.init(this, tessellator, Long.toString(l), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, final char c, final double x, final double y) { return method_renderCenteredDouble.init(this, tessellator, String.valueOf(c), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, final float f, final double x, final double y) { return method_renderCenteredDouble.init(this, tessellator, Float.toString(f), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, final double d, final double x, final double y) { return method_renderCenteredDouble.init(this, tessellator, Double.toString(d), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, final char @Nullable [] cArr, final double x, final double y) { return method_renderCenteredDouble.init(this, tessellator, cArr == null ? NULL_STRING : new String(cArr), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleBase renderCenteredDouble(@NotNull final Tessellator tessellator, @Nullable final CharSequence chars, final double x, final double y) {return method_renderCenteredDouble.init(this, tessellator, chars == null ? NULL_STRING : chars, x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-
-    abstract void renderWidthConstrainedImpl(@NotNull Font font, @NotNull Tessellator tessellator, @NotNull CharSequence chars, int x, int y, double z, boolean shadow, long baseConfig, int maxWidth, @NotNull Alignment alignment, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, @Nullable final Object o, final int x, final int y, final int maxWidth) { return renderWidthConstrained(tessellator, String.valueOf(o), x, y, maxWidth); }
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, final boolean b, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, tessellator, Boolean.toString(b), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, final int i, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, tessellator, Integer.toString(i), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, final long l, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, tessellator, Long.toString(l), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, final char c, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, tessellator, String.valueOf(c), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, final float f, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, tessellator, Float.toString(f), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, final double d, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, tessellator, Double.toString(d), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, final char @Nullable [] cArr, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, tessellator, cArr == null ? NULL_STRING : new String(cArr), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@NotNull final Tessellator tessellator, @Nullable final CharSequence chars, final int x, final int y, final int maxWidth) {return method_renderWidthConstrained.init(this, tessellator, chars == null ? NULL_STRING : chars, x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-
-    abstract void renderWidthConstrainedDoubleImpl(@NotNull Font font, @NotNull Tessellator tessellator, @NotNull CharSequence chars, double x, double y, double z, boolean shadow, long baseConfig, double maxWidth, @NotNull Alignment alignment, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, @Nullable final Object o, final double x, final double y, final double maxWidth) { return renderWidthConstrainedDouble(tessellator, String.valueOf(o), x, y, maxWidth); }
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, final boolean b, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, tessellator, Boolean.toString(b), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, final int i, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, tessellator, Integer.toString(i), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, final long l, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, tessellator, Long.toString(l), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, final char c, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, tessellator, String.valueOf(c), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, final float f, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, tessellator, Float.toString(f), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, final double d, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, tessellator, Double.toString(d), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, final char @Nullable [] cArr, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, tessellator, cArr == null ? NULL_STRING : new String(cArr), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@NotNull final Tessellator tessellator, @Nullable final CharSequence chars, final double x, final double y, final double maxWidth) {return method_renderWidthConstrainedDouble.init(this, tessellator, chars == null ? NULL_STRING : chars, x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-
-    abstract void renderConstrainedImpl(@NotNull Font font, @NotNull Tessellator tessellator, @NotNull CharSequence chars, int x, int y, double z, boolean shadow, long baseConfig, int maxWidth, int maxHeight, @NotNull Alignment alignment, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, @Nullable final Object o, final int x, final int y, final int maxWidth, final int maxHeight) { return renderConstrained(tessellator, String.valueOf(o), x, y, maxWidth, maxHeight); }
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, final boolean b, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, tessellator, Boolean.toString(b), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, final int i, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, tessellator, Integer.toString(i), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, final long l, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, tessellator, Long.toString(l), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, final char c, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, tessellator, String.valueOf(c), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, final float f, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, tessellator, Float.toString(f), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, final double d, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, tessellator, Double.toString(d), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, final char @Nullable [] cArr, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, tessellator, cArr == null ? NULL_STRING : new String(cArr), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@NotNull final Tessellator tessellator, @Nullable final CharSequence chars, final int x, final int y, final int maxWidth, final int maxHeight) {return method_renderConstrained.init(this, tessellator, chars == null ? NULL_STRING : chars, x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-
-    abstract void renderConstrainedDoubleImpl(@NotNull Font font, @NotNull Tessellator tessellator, @NotNull CharSequence chars, double x, double y, double z, boolean shadow, long baseConfig, double maxWidth, double maxHeight, @NotNull Alignment alignment, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, @Nullable final Object o, final double x, final double y, final double maxWidth, final double maxHeight) { return renderConstrainedDouble(tessellator, String.valueOf(o), x, y, maxWidth, maxHeight); }
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, final boolean b, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, tessellator, Boolean.toString(b), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, final int i, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, tessellator, Integer.toString(i), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, final long l, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, tessellator, Long.toString(l), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, final char c, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, tessellator, String.valueOf(c), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, final float f, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, tessellator, Float.toString(f), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, final double d, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, tessellator, Double.toString(d), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, final char @Nullable [] cArr, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, tessellator, cArr == null ? NULL_STRING : new String(cArr), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
-    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@NotNull final Tessellator tessellator, @Nullable final CharSequence chars, final double x, final double y, final double maxWidth, final double maxHeight) {return method_renderConstrainedDouble.init(this, tessellator, chars == null ? NULL_STRING : chars, x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    abstract void renderImpl(@NotNull Font font, @NotNull CharSequence chars, int x, int y, double z, boolean shadow, long baseConfig, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
+    public final @NotNull RenderIntegerBase render(@Nullable final Object o, final int x, final int y) { return render(String.valueOf(o), x, y); }
+    public final @NotNull RenderIntegerBase render(final boolean b, final int x, final int y) { return method_render.init(this, Boolean.toString(b), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase render(final int i, final int x, final int y) { return method_render.init(this, Integer.toString(i), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase render(final long l, final int x, final int y) { return method_render.init(this, Long.toString(l), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase render(final char c, final int x, final int y) { return method_render.init(this, String.valueOf(c), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase render(final float f, final int x, final int y) { return method_render.init(this, Float.toString(f), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase render(final double d, final int x, final int y) { return method_render.init(this, Double.toString(d), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase render(final char @Nullable [] cArr, final int x, final int y) { return method_render.init(this, cArr == null ? NULL_STRING : new String(cArr), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase render(@Nullable final CharSequence chars, final int x, final int y) {return method_render.init(this, chars == null ? NULL_STRING : chars, x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+
+    abstract void renderDoubleImpl(@NotNull Font font, @NotNull CharSequence chars, double x, double y, double z, boolean shadow, long baseConfig, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
+    public final @NotNull RenderDoubleBase renderDouble(@Nullable final Object o, final double x, final double y) { return renderDouble(String.valueOf(o), x, y); }
+    public final @NotNull RenderDoubleBase renderDouble(final boolean b, final double x, final double y) { return method_renderDouble.init(this, Boolean.toString(b), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderDouble(final int i, final double x, final double y) { return method_renderDouble.init(this, Integer.toString(i), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderDouble(final long l, final double x, final double y) { return method_renderDouble.init(this, Long.toString(l), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderDouble(final char c, final double x, final double y) { return method_renderDouble.init(this, String.valueOf(c), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderDouble(final float f, final double x, final double y) { return method_renderDouble.init(this, Float.toString(f), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderDouble(final double d, final double x, final double y) { return method_renderDouble.init(this, Double.toString(d), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderDouble(final char @Nullable [] cArr, final double x, final double y) { return method_renderDouble.init(this, cArr == null ? NULL_STRING : new String(cArr), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderDouble(@Nullable final CharSequence chars, final double x, final double y) {return method_renderDouble.init(this, chars == null ? NULL_STRING : chars, x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+
+    abstract void renderCenteredImpl(@NotNull Font font, @NotNull CharSequence chars, int x, int y, double z, boolean shadow, long baseConfig, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
+    public final @NotNull RenderIntegerBase renderCentered(@Nullable final Object o, final int x, final int y) { return renderCentered(String.valueOf(o), x, y); }
+    public final @NotNull RenderIntegerBase renderCentered(final boolean b, final int x, final int y) { return method_renderCentered.init(this, Boolean.toString(b), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase renderCentered(final int i, final int x, final int y) { return method_renderCentered.init(this, Integer.toString(i), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase renderCentered(final long l, final int x, final int y) { return method_renderCentered.init(this, Long.toString(l), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase renderCentered(final char c, final int x, final int y) { return method_renderCentered.init(this, String.valueOf(c), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase renderCentered(final float f, final int x, final int y) { return method_renderCentered.init(this, Float.toString(f), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase renderCentered(final double d, final int x, final int y) { return method_renderCentered.init(this, Double.toString(d), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase renderCentered(final char @Nullable [] cArr, final int x, final int y) { return method_renderCentered.init(this, cArr == null ? NULL_STRING : new String(cArr), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerBase renderCentered(@Nullable final CharSequence chars, final int x, final int y) {return method_renderCentered.init(this, chars == null ? NULL_STRING : chars, x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+
+    abstract void renderCenteredDoubleImpl(@NotNull Font font, @NotNull CharSequence chars, double x, double y, double z, boolean shadow, long baseConfig, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
+    public final @NotNull RenderDoubleBase renderCenteredDouble(@Nullable final Object o, final double x, final double y) { return renderCenteredDouble(String.valueOf(o), x, y); }
+    public final @NotNull RenderDoubleBase renderCenteredDouble(final boolean b, final double x, final double y) { return method_renderCenteredDouble.init(this, Boolean.toString(b), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderCenteredDouble(final int i, final double x, final double y) { return method_renderCenteredDouble.init(this, Integer.toString(i), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderCenteredDouble(final long l, final double x, final double y) { return method_renderCenteredDouble.init(this, Long.toString(l), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderCenteredDouble(final char c, final double x, final double y) { return method_renderCenteredDouble.init(this, String.valueOf(c), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderCenteredDouble(final float f, final double x, final double y) { return method_renderCenteredDouble.init(this, Float.toString(f), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderCenteredDouble(final double d, final double x, final double y) { return method_renderCenteredDouble.init(this, Double.toString(d), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderCenteredDouble(final char @Nullable [] cArr, final double x, final double y) { return method_renderCenteredDouble.init(this, cArr == null ? NULL_STRING : new String(cArr), x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleBase renderCenteredDouble(@Nullable final CharSequence chars, final double x, final double y) {return method_renderCenteredDouble.init(this, chars == null ? NULL_STRING : chars, x, y, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+
+    abstract void renderWidthConstrainedImpl(@NotNull Font font, @NotNull CharSequence chars, int x, int y, double z, boolean shadow, long baseConfig, int maxWidth, @NotNull Alignment alignment, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@Nullable final Object o, final int x, final int y, final int maxWidth) { return renderWidthConstrained(String.valueOf(o), x, y, maxWidth); }
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(final boolean b, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, Boolean.toString(b), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(final int i, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, Integer.toString(i), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(final long l, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, Long.toString(l), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(final char c, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, String.valueOf(c), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(final float f, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, Float.toString(f), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(final double d, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, Double.toString(d), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(final char @Nullable [] cArr, final int x, final int y, final int maxWidth) { return method_renderWidthConstrained.init(this, cArr == null ? NULL_STRING : new String(cArr), x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderWidthConstrained(@Nullable final CharSequence chars, final int x, final int y, final int maxWidth) {return method_renderWidthConstrained.init(this, chars == null ? NULL_STRING : chars, x, y, maxWidth, Integer.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+
+    abstract void renderWidthConstrainedDoubleImpl(@NotNull Font font, @NotNull CharSequence chars, double x, double y, double z, boolean shadow, long baseConfig, double maxWidth, @NotNull Alignment alignment, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@Nullable final Object o, final double x, final double y, final double maxWidth) { return renderWidthConstrainedDouble(String.valueOf(o), x, y, maxWidth); }
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(final boolean b, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, Boolean.toString(b), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(final int i, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, Integer.toString(i), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(final long l, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, Long.toString(l), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(final char c, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, String.valueOf(c), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(final float f, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, Float.toString(f), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(final double d, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, Double.toString(d), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(final char @Nullable [] cArr, final double x, final double y, final double maxWidth) { return method_renderWidthConstrainedDouble.init(this, cArr == null ? NULL_STRING : new String(cArr), x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderWidthConstrainedDouble(@Nullable final CharSequence chars, final double x, final double y, final double maxWidth) {return method_renderWidthConstrainedDouble.init(this, chars == null ? NULL_STRING : chars, x, y, maxWidth, Double.MAX_VALUE, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+
+    abstract void renderConstrainedImpl(@NotNull Font font, @NotNull CharSequence chars, int x, int y, double z, boolean shadow, long baseConfig, int maxWidth, int maxHeight, @NotNull Alignment alignment, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@Nullable final Object o, final int x, final int y, final int maxWidth, final int maxHeight) { return renderConstrained(String.valueOf(o), x, y, maxWidth, maxHeight); }
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(final boolean b, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, Boolean.toString(b), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(final int i, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, Integer.toString(i), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(final long l, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, Long.toString(l), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(final char c, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, String.valueOf(c), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(final float f, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, Float.toString(f), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(final double d, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, Double.toString(d), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(final char @Nullable [] cArr, final int x, final int y, final int maxWidth, final int maxHeight) { return method_renderConstrained.init(this, cArr == null ? NULL_STRING : new String(cArr), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderIntegerConstrainedBase renderConstrained(@Nullable final CharSequence chars, final int x, final int y, final int maxWidth, final int maxHeight) {return method_renderConstrained.init(this, chars == null ? NULL_STRING : chars, x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+
+    abstract void renderConstrainedDoubleImpl(@NotNull Font font, @NotNull CharSequence chars, double x, double y, double z, boolean shadow, long baseConfig, double maxWidth, double maxHeight, @NotNull Alignment alignment, double @Nullable [] xPosBuffer, double @Nullable [] yPosBuffer, long @Nullable [] configBuffer);
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@Nullable final Object o, final double x, final double y, final double maxWidth, final double maxHeight) { return renderConstrainedDouble(String.valueOf(o), x, y, maxWidth, maxHeight); }
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(final boolean b, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, Boolean.toString(b), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(final int i, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, Integer.toString(i), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(final long l, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, Long.toString(l), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(final char c, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, String.valueOf(c), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(final float f, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, Float.toString(f), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(final double d, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, Double.toString(d), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(final char @Nullable [] cArr, final double x, final double y, final double maxWidth, final double maxHeight) { return method_renderConstrainedDouble.init(this, cArr == null ? NULL_STRING : new String(cArr), x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
+    public final @NotNull RenderDoubleConstrainedBase renderConstrainedDouble(@Nullable final CharSequence chars, final double x, final double y, final double maxWidth, final double maxHeight) {return method_renderConstrainedDouble.init(this, chars == null ? NULL_STRING : chars, x, y, maxWidth, maxHeight, this.xPosBuffer, this.yPosBuffer, this.configBuffer); }
 
     public final int getLastEndingX() {
         return MathHelper.ceil(this.xPosBuffer[0]);
@@ -173,4 +172,8 @@ public abstract class FontRenderer {
     public int stringWidth(final @NotNull CharSequence chars) {
         return stringWidth(getFont(), chars);
     }
+
+    public void init() {
+
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/FontRendererDefault.java b/game/client/src/main/java/net/minecraft/client/render/font/FontRendererDefault.java
index 8155d2e83..6e0d8f18e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/FontRendererDefault.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/FontRendererDefault.java
@@ -1,14 +1,23 @@
 package net.minecraft.client.render.font;
 
 import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.RenderBuffer;
 import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorBase;
+import net.minecraft.client.render.tessellator.TessellatorColor;
+import net.minecraft.client.render.tessellator.TessellatorFont;
 import net.minecraft.client.util.helper.Colors;
 import net.minecraft.core.net.command.TextFormatting;
 import net.minecraft.core.util.helper.ChatAllowedCharacters;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
+import org.lwjgl.opengl.GL41;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -41,12 +50,19 @@ public class FontRendererDefault extends FontRenderer {
         this.random = new Random();
     }
 
+    protected TessellatorFont baseStringTess;
+    protected TessellatorDecorations backgroundStringTess;
+    @Override
+    public void init() {
+        this.baseStringTess = new TessellatorFont("FontRenderDefault Base Tessellator", 0x40000);
+        this.backgroundStringTess = new TessellatorDecorations("FontRenderDefault Deco Tessellator", 0x8000);
+    }
+
     private static final StringBuilder renderStringInternal_colorValue = new StringBuilder();
-    protected void renderStringInternal(@NotNull final Font font, @NotNull final Tessellator tessellator, final @NotNull CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+    protected void renderStringInternal(@NotNull final Font font, final @NotNull CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
         double currX = x;
 
         this.random.setSeed(System.currentTimeMillis()/50);
-
         for (int i = 0; i < chars.length(); i++) {
             final char c = chars.charAt(i);
 
@@ -136,10 +152,15 @@ public class FontRendererDefault extends FontRenderer {
             final int tex = charFont.textureForChar(c);
             if (this.currentTex != tex) {
                 this.currentTex = tex;
-                GL11.glBindTexture(GL11.GL_TEXTURE_2D, tex);
+                Shaders.FONT.bind();
+                this.baseStringTess.draw(); // Render mesh on texture change
+                GL41.glBindTexture(GL41.GL_TEXTURE_2D, tex);
+                this.baseStringTess.startDrawing();
             }
 
-            currX += renderCharInternal(charFont, tessellator, c, currX, y, z, SF.getColor(this.currentConfig), shadow);
+            double off = renderCharInternal(charFont, this.baseStringTess, c, currX, y, z, SF.getColor(this.currentConfig), shadow);
+            renderCharInternalDecorations(charFont, this.backgroundStringTess, c, currX, y, z, SF.getColor(this.currentConfig), shadow);
+            currX += off;
         }
 
         if (xPosBuffer != null) {
@@ -153,11 +174,10 @@ public class FontRendererDefault extends FontRenderer {
         }
     }
 
-    protected double renderCharInternal(@NotNull final Font font, @NotNull final Tessellator tessellator, final char c, final double x, final double y, final double z, final int color, boolean shadow) {
+    protected double renderCharInternal(@NotNull final Font font, @NotNull final TessellatorFont tessellator, final char c, final double x, final double y, final double z, final int color, boolean shadow) {
         final int rgb = color & 0xFFFFFF;
         final int shadowRGB = (color & 0xFCFCFC) >> 2; // Divide RGB by 4
         final int a = (color & 0xFF_00_00_00) != 0 ? (color >> 24) & 0xFF : 0xFF;
-        tessellator.startDrawingQuads();
 
         shadow &= !SF.isOutlined(this.currentConfig);
 
@@ -171,13 +191,13 @@ public class FontRendererDefault extends FontRenderer {
             final char randomChar = font.getObfuscatedChar(c, this.random);
 
             if (shadow) {
-                tessellator.setColorRGBA_I(shadowRGB, a);
+                tessellator.setColor2i(shadowRGB, a);
                 font.renderChar(tessellator, randomChar, x + px, y + px, z, SF.isItalic(this.currentConfig));
                 if (SF.isBold(this.currentConfig)) font.renderChar(tessellator, randomChar, x + px2, y + px, z, SF.isItalic(this.currentConfig));
             }
 
             if (SF.isOutlined(this.currentConfig)) {
-                tessellator.setColorRGBA_I((rgb & 0xFCFCFC) >> 2, a);
+                tessellator.setColor2i((rgb & 0xFCFCFC) >> 2, a);
                 final double width = SF.isBold(this.currentConfig) ? 2.05 : 1.05;
                 for (double _x = -1; _x <= width; _x += 1/3d) {
                     for (double _y = -1; _y <= 1.05; _y += 1/3d) {
@@ -186,7 +206,7 @@ public class FontRendererDefault extends FontRenderer {
                 }
             }
 
-            tessellator.setColorRGBA_I(rgb, a);
+            tessellator.setColor2i(rgb, a);
             font.renderChar(tessellator, randomChar, x, y, z, SF.isItalic(this.currentConfig));
             if (SF.isBold(this.currentConfig)) {
                 font.renderChar(tessellator, randomChar, x + px, y, z, SF.isItalic(this.currentConfig));
@@ -195,13 +215,13 @@ public class FontRendererDefault extends FontRenderer {
 
         } else {
             if (shadow) {
-                tessellator.setColorRGBA_I(shadowRGB, a);
+                tessellator.setColor2i(shadowRGB, a);
                 font.renderChar(tessellator, c, x + px, y + px, z, SF.isItalic(this.currentConfig));
                 if (SF.isBold(this.currentConfig)) font.renderChar(tessellator, c, x + px2, y + px, z, SF.isItalic(this.currentConfig));
             }
 
             if (SF.isOutlined(this.currentConfig)) {
-                tessellator.setColorRGBA_I((rgb & 0xFCFCFC) >> 2, a);
+                tessellator.setColor2i((rgb & 0xFCFCFC) >> 2, a);
                 final double width = SF.isBold(this.currentConfig) ? 2.05 : 1.05;
                 for (double _x = -1; _x <= width; _x += 1/3d) {
                     for (double _y = -1; _y <= 1.05; _y += 1/3d) {
@@ -210,91 +230,130 @@ public class FontRendererDefault extends FontRenderer {
                 }
             }
 
-            tessellator.setColorRGBA_I(rgb, a);
+            tessellator.setColor2i(rgb, a);
             shift = font.renderChar(tessellator, c, x, y, z, SF.isItalic(this.currentConfig));
             if (SF.isBold(this.currentConfig)) {
                 font.renderChar(tessellator, c, x + px, y, z, SF.isItalic(this.currentConfig));
                 shift += px;
             }
         }
-        tessellator.draw();
+        return shift;
+    }
+
+    protected void renderCharInternalDecorations(@NotNull final Font font, final @NotNull TessellatorDecorations tessellator, final char c, final double x, final double y, final double z, final int color, boolean shadow) {
+        final int rgb = color & 0xFFFFFF;
+        final int shadowRGB = (color & 0xFCFCFC) >> 2; // Divide RGB by 4
+        final int a = (color & 0xFF_00_00_00) != 0 ? (color >> 24) & 0xFF : 0xFF;
+
+        boolean strikethrough = SF.isStrikethrough(this.currentConfig);
+        boolean underline = SF.isUnderline(this.currentConfig);
+        if (!strikethrough && !underline) return;
+
+        shadow &= !SF.isOutlined(this.currentConfig);
+
+        final double px = 1;
+        final double px2 = px * 2;
+
         final int fontHeight = font.fontHeight();
-        if (SF.isStrikethrough(this.currentConfig)) {
-            GL11.glDisable(GL11.GL_TEXTURE_2D);
-            tessellator.startDrawingQuads();
+        final double shift = SF.isBold(this.currentConfig) ? font.charWidth(c) + px : font.charWidth(c);
+
+        if (strikethrough) {
             if (shadow) {
-                tessellator.setColorRGBA_I(shadowRGB, a);
+                tessellator.setColor2i(shadowRGB, a);
                 tessellator.addVertex(x + px,        y + px + fontHeight / 2d,     0.0D);
                 tessellator.addVertex(x + px + shift,y + px + fontHeight / 2d,     0.0D);
                 tessellator.addVertex(x + px + shift,y + px + fontHeight / 2d - px,0.0D);
                 tessellator.addVertex(x + px,        y + px + fontHeight / 2d - px,0.0D);
             }
-            tessellator.setColorRGBA_I(rgb, a);
+            tessellator.setColor2i(rgb, a);
             tessellator.addVertex(x,        y + fontHeight / 2d,     0.0D);
             tessellator.addVertex(x + shift,y + fontHeight / 2d,     0.0D);
             tessellator.addVertex(x + shift,y + fontHeight / 2d - px,0.0D);
             tessellator.addVertex(x,        y + fontHeight / 2d - px,0.0D);
-            tessellator.draw();
-            GL11.glEnable(GL11.GL_TEXTURE_2D);
         }
 
-        if (SF.isUnderline(this.currentConfig)) {
-            GL11.glDisable(GL11.GL_TEXTURE_2D);
-            tessellator.startDrawingQuads();
+        if (underline) {
             if (shadow) {
-                tessellator.setColorRGBA_I(shadowRGB, a);
+                tessellator.setColor2i(shadowRGB, a);
                 tessellator.addVertex(x,             y + px2 + fontHeight,      0.0D);
                 tessellator.addVertex(x + px + shift,y + px2 + fontHeight,      0.0D);
                 tessellator.addVertex(x + px + shift,y + px2 + fontHeight - px, 0.0D);
                 tessellator.addVertex(x,             y + px2 + fontHeight - px, 0.0D);
             }
-            tessellator.setColorRGBA_I(rgb, a);
+            tessellator.setColor2i(rgb, a);
             tessellator.addVertex(x - px,    y + px + fontHeight,      0.0D);
             tessellator.addVertex(x + shift, y + px + fontHeight,      0.0D);
             tessellator.addVertex(x + shift, y + px + fontHeight - px, 0.0D);
             tessellator.addVertex(x - px,    y + px + fontHeight - px, 0.0D);
-            tessellator.draw();
-            GL11.glEnable(GL11.GL_TEXTURE_2D);
         }
-        return shift;
     }
+
     @Override
-    public void renderDoubleImpl(@NotNull final Font font, @NotNull final Tessellator tessellator, final @NotNull CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+    public void renderDoubleImpl(@NotNull final Font font, final @NotNull CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
         this.currentTex = -1;
         this.currentConfig = baseConfig;
         this.stackIndex = 0;
-        renderStringInternal(font, tessellator, chars, x, y, z, shadow, baseConfig, xPosBuffer, yPosBuffer, configBuffer);
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.globalSetUniforms(Shaders.FONT);
+        Shaders.FONT.bind();
+        GL41.glUniform1f(Shaders.FONT.getUniform("uZ"), (float) z);
+        GLRenderer.globalSetUniforms(Shaders.COLOR);
+
+        this.baseStringTess.startDrawing();
+        this.backgroundStringTess.startDrawingQuads();
+
+        renderStringInternal(font, chars, x, y, z, shadow, baseConfig, xPosBuffer, yPosBuffer, configBuffer);
+
+        Shaders.FONT.bind();
+        this.baseStringTess.draw();
+        Shaders.COLOR.bind();
+        this.backgroundStringTess.draw();
+
+        GLRenderer.popFrame();
     }
 
     @Override
-    public void renderImpl(@NotNull final Font font, @NotNull final Tessellator tessellator, final @NotNull CharSequence chars, final int x, final int y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
-        renderDoubleImpl(font, tessellator, chars, x, y, z, shadow, baseConfig, xPosBuffer, yPosBuffer, configBuffer);
+    public void renderImpl(@NotNull final Font font, final @NotNull CharSequence chars, final int x, final int y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+        renderDoubleImpl(font, chars, x, y, z, shadow, baseConfig, xPosBuffer, yPosBuffer, configBuffer);
     }
 
     @Override
-    public void renderCenteredDoubleImpl(@NotNull final Font font, @NotNull final Tessellator tessellator, final @NotNull CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
-        renderDoubleImpl(font, tessellator, chars, x - stringWidthDouble(chars)/2d, y, z, shadow, baseConfig, xPosBuffer, yPosBuffer, configBuffer);
+    public void renderCenteredDoubleImpl(@NotNull final Font font, final @NotNull CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+        renderDoubleImpl(font, chars, x - stringWidthDouble(chars)/2d, y, z, shadow, baseConfig, xPosBuffer, yPosBuffer, configBuffer);
     }
 
     @Override
-    public void renderCenteredImpl(@NotNull final Font font, @NotNull final Tessellator tessellator, final @NotNull CharSequence chars, final int x, final int y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
-        renderImpl(font, tessellator, chars, x - stringWidth(chars)/2, y, z, shadow, baseConfig, xPosBuffer, yPosBuffer, configBuffer);
+    public void renderCenteredImpl(@NotNull final Font font, final @NotNull CharSequence chars, final int x, final int y, final double z, final boolean shadow, final long baseConfig, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+        renderImpl(font, chars, x - stringWidth(chars)/2, y, z, shadow, baseConfig, xPosBuffer, yPosBuffer, configBuffer);
     }
 
     @Override
-    public void renderWidthConstrainedDoubleImpl(@NotNull final Font font, @NotNull final Tessellator tessellator, @NotNull final CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double maxWidth, @NotNull final Alignment alignment, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+    public void renderWidthConstrainedDoubleImpl(@NotNull final Font font, @NotNull final CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double maxWidth, @NotNull final Alignment alignment, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
         this.currentTex = -1;
         this.currentConfig = baseConfig;
         this.stackIndex = 0;
 
         final List<String> lines = splitCharsIntoLines(chars, maxWidth, this.localStringList);
 
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.globalSetUniforms(Shaders.FONT);
+        Shaders.FONT.bind();
+        GL41.glUniform1f(Shaders.FONT.getUniform("uZ"), (float) z);
+        GLRenderer.globalSetUniforms(Shaders.COLOR);
+
+        this.baseStringTess.startDrawing();
+        this.backgroundStringTess.startDrawingQuads();
+
         double currY = y;
         switch (alignment) {
             case LEFT: {
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderStringInternal(font, tessellator, line, x, currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
+                    renderStringInternal(font, line, x, currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                 }
                 break;
@@ -302,7 +361,7 @@ public class FontRendererDefault extends FontRenderer {
             case RIGHT: {
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderStringInternal(font, tessellator, line, x + (maxWidth - stringWidthDouble(line)), currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
+                    renderStringInternal(font, line, x + (maxWidth - stringWidthDouble(line)), currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                 }
                 break;
@@ -310,12 +369,17 @@ public class FontRendererDefault extends FontRenderer {
             case CENTERED: {
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderStringInternal(font, tessellator, line, x + (maxWidth - stringWidthDouble(line))/2, currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
+                    renderStringInternal(font, line, x + (maxWidth - stringWidthDouble(line))/2, currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                 }
                 break;
             }
         }
+        Shaders.FONT.bind();
+        this.baseStringTess.draw();
+        Shaders.COLOR.bind();
+        this.backgroundStringTess.draw();
+        GLRenderer.popFrame();
 
         if (xPosBuffer != null) {
             xPosBuffer[0] = x + maxWidth;
@@ -329,19 +393,30 @@ public class FontRendererDefault extends FontRenderer {
     }
 
     @Override
-    public void renderWidthConstrainedImpl(@NotNull final Font font, @NotNull final Tessellator tessellator, @NotNull final CharSequence chars, final int x, final int y, final double z, final boolean shadow, final long baseConfig, final int maxWidth, @NotNull final Alignment alignment, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+    public void renderWidthConstrainedImpl(@NotNull final Font font, @NotNull final CharSequence chars, final int x, final int y, final double z, final boolean shadow, final long baseConfig, final int maxWidth, @NotNull final Alignment alignment, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
         this.currentTex = -1;
         this.currentConfig = baseConfig;
         this.stackIndex = 0;
 
         final List<String> lines = splitCharsIntoLines(chars, maxWidth, this.localStringList);
 
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.globalSetUniforms(Shaders.FONT);
+        Shaders.FONT.bind();
+        GL41.glUniform1f(Shaders.FONT.getUniform("uZ"), (float) z);
+        GLRenderer.globalSetUniforms(Shaders.COLOR);
+
+        this.baseStringTess.startDrawing();
+        this.backgroundStringTess.startDrawingQuads();
+
         int currY = y;
         switch (alignment) {
             case LEFT: {
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderStringInternal(font, tessellator, line, x, currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
+                    renderStringInternal(font, line, x, currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                 }
                 break;
@@ -349,7 +424,7 @@ public class FontRendererDefault extends FontRenderer {
             case RIGHT: {
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderStringInternal(font, tessellator, line, x + (maxWidth - stringWidth(line)), currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
+                    renderStringInternal(font, line, x + (maxWidth - stringWidth(line)), currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                 }
                 break;
@@ -357,12 +432,17 @@ public class FontRendererDefault extends FontRenderer {
             case CENTERED: {
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderStringInternal(font, tessellator, line, (int)(x + (maxWidth - stringWidth(line))/2), currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
+                    renderStringInternal(font, line, x + (maxWidth - stringWidth(line))/2, currY, z, shadow, baseConfig, this.localXPosBuffer, this.localYPosBuffer, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                 }
                 break;
             }
         }
+        Shaders.FONT.bind();
+        this.baseStringTess.draw();
+        Shaders.COLOR.bind();
+        this.backgroundStringTess.draw();
+        GLRenderer.popFrame();
 
         if (xPosBuffer != null) {
             xPosBuffer[0] = x + maxWidth;
@@ -376,7 +456,7 @@ public class FontRendererDefault extends FontRenderer {
     }
 
     @Override
-    public void renderConstrainedDoubleImpl(@NotNull final Font font, @NotNull final Tessellator tessellator, @NotNull final CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double maxWidth, final double maxHeight, @NotNull final Alignment alignment, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+    public void renderConstrainedDoubleImpl(@NotNull final Font font, @NotNull final CharSequence chars, final double x, final double y, final double z, final boolean shadow, final long baseConfig, final double maxWidth, final double maxHeight, @NotNull final Alignment alignment, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
         this.currentTex = -1;
         this.currentConfig = baseConfig;
         this.stackIndex = 0;
@@ -387,27 +467,55 @@ public class FontRendererDefault extends FontRenderer {
         this.localConfigBuffer[0] = baseConfig;
         switch (alignment) {
             case LEFT: {
+                GLRenderer.pushFrame();
+                GLRenderer.enableState(State.BLEND);
+                GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+                GLRenderer.globalSetUniforms(Shaders.FONT);
+                Shaders.FONT.bind();
+                GL41.glUniform1f(Shaders.FONT.getUniform("uZ"), (float) z);
+                GLRenderer.globalSetUniforms(Shaders.COLOR);
+                this.baseStringTess.startDrawing();
+                this.backgroundStringTess.startDrawingQuads();
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderStringInternal(font, tessellator, line, x, currY, z, shadow, baseConfig, null, null, this.localConfigBuffer);
+                    renderStringInternal(font, line, x, currY, z, shadow, baseConfig, null, null, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                     if ((currY - y) > maxHeight) break;
                 }
+                Shaders.FONT.bind();
+                this.baseStringTess.draw();
+                Shaders.COLOR.bind();
+                this.backgroundStringTess.draw();
+                GLRenderer.popFrame();
                 break;
             }
             case RIGHT: {
+                GLRenderer.pushFrame();
+                GLRenderer.enableState(State.BLEND);
+                GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+                GLRenderer.globalSetUniforms(Shaders.FONT);
+                Shaders.FONT.bind();
+                GL41.glUniform1f(Shaders.FONT.getUniform("uZ"), (float) z);
+                GLRenderer.globalSetUniforms(Shaders.COLOR);
+                this.baseStringTess.startDrawing();
+                this.backgroundStringTess.startDrawingQuads();
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderStringInternal(font, tessellator, line, x + (maxWidth - stringWidthDouble(line)), currY, z, shadow, baseConfig, null, null, this.localConfigBuffer);
+                    renderStringInternal(font, line, x + (maxWidth - stringWidthDouble(line)), currY, z, shadow, baseConfig, null, null, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                     if ((currY - y) > maxHeight) break;
                 }
+                Shaders.FONT.bind();
+                this.baseStringTess.draw();
+                Shaders.COLOR.bind();
+                this.backgroundStringTess.draw();
+                GLRenderer.popFrame();
                 break;
             }
             case CENTERED: {
                 for (int i = 0; i < lines.size(); i++) {
                     final String line = lines.get(i);
-                    renderCenteredDoubleImpl(font, tessellator, line, x + maxWidth/2, currY, z, shadow, baseConfig, null, null, this.localConfigBuffer);
+                    renderCenteredDoubleImpl(font, line, x + maxWidth/2, currY, z, shadow, baseConfig, null, null, this.localConfigBuffer);
                     currY += font.fontHeight() + 1;
                     if ((currY - y) > maxHeight) break;
                 }
@@ -427,8 +535,8 @@ public class FontRendererDefault extends FontRenderer {
     }
 
     @Override
-    public void renderConstrainedImpl(@NotNull final Font font, @NotNull final Tessellator tessellator, @NotNull final CharSequence chars, final int x, final int y, final double z, final boolean shadow, final long baseConfig, final int maxWidth, final int maxHeight, @NotNull final Alignment alignment, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
-        renderConstrainedDoubleImpl(font, tessellator, chars, x, y, z, shadow, baseConfig, maxWidth, maxHeight, alignment, xPosBuffer, yPosBuffer, configBuffer);
+    public void renderConstrainedImpl(@NotNull final Font font, @NotNull final CharSequence chars, final int x, final int y, final double z, final boolean shadow, final long baseConfig, final int maxWidth, final int maxHeight, @NotNull final Alignment alignment, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+        renderConstrainedDoubleImpl(font, chars, x, y, z, shadow, baseConfig, maxWidth, maxHeight, alignment, xPosBuffer, yPosBuffer, configBuffer);
     }
 
     private static final StringBuilder splitLineIntoConstrainedLine_lineBuilder = new StringBuilder();
@@ -669,4 +777,131 @@ public class FontRendererDefault extends FontRenderer {
         }
         return value;
     }
+
+    protected static class TessellatorDecorations extends TessellatorBase implements TessellatorColor {
+        private static final int VERT_SIZE = Float.BYTES * 3 + 4;
+        private boolean lockColor = false;
+
+        private int color;
+
+        private final int vao;
+        private final int vbo;
+
+        private int quadVertCount = 0;
+
+        public TessellatorDecorations(@NotNull String name, int initialCapacity) {
+            super(name, initialCapacity);
+            this.vao = GL41.glGenVertexArrays();
+            this.vbo = GL41.glGenBuffers();
+
+            GL41.glBindVertexArray(this.vao);
+            GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+
+            GL41.glVertexAttribPointer(0, 3, GL41.GL_FLOAT, false, VERT_SIZE, 0);
+            GL41.glVertexAttribPointer(1, 4, GL41.GL_UNSIGNED_BYTE, true, VERT_SIZE, Float.BYTES * 3);
+            GL41.glVertexAttrib2f(2, 0f, 0f);
+            GL41.glVertexAttrib2f(3, 15.5f/16f, 15.5f/16f);
+            GL41.glVertexAttrib3f(4, 0, -1f, 0);
+
+            GL41.glEnableVertexAttribArray(0);
+            GL41.glEnableVertexAttribArray(1);
+            GL41.glBindVertexArray(0);
+        }
+
+        @Override
+        public void startDrawing(@NotNull DrawMode drawMode) {
+            super.startDrawing(drawMode);
+
+            this.lockColor = false;
+            this.quadVertCount = 0;
+            if (Tessellator.QUAD_EMULATION && drawMode == DrawMode.QUADS) {
+                this.drawMode = DrawMode.TRIANGLES;
+            }
+            setColor1i(0xFFFFFFFF);
+        }
+
+        @Override
+        public void addVertex(double x, double y, double z) {
+            checkIsDrawing();
+            checkCanFit(64);
+
+            this.data.putFloat((float) (this.offsetX + x));
+            this.data.putFloat((float) (this.offsetY + y));
+            this.data.putFloat((float) (this.offsetZ + z));
+
+            this.data.putInt(this.color);
+            this.vertexCount++;
+
+            if (Tessellator.QUAD_EMULATION && this.quadVertCount % 4 == 2) {
+                checkCanFit(128);
+                this.data.put(this.data.position(), this.data, this.data.position() - VERT_SIZE * 3, VERT_SIZE);
+                this.data.put(this.data.position() + VERT_SIZE, this.data, this.data.position() - VERT_SIZE, VERT_SIZE);
+                this.data.position(this.data.position() + VERT_SIZE * 2);
+                this.vertexCount += 2;
+            }
+
+            this.quadVertCount++;
+        }
+
+        @Override
+        public void draw() {
+            if(!this.drawing) {
+                throw new IllegalStateException(this.name + " already drawing!");
+            }
+
+            this.drawing = false;
+
+            if (this.vertexCount == 0) return;
+
+            GL41.glBindVertexArray(this.vao);
+            GL41.glVertexAttrib2f(3, GLRenderer.getLightmapBlock(), GLRenderer.getLightmapSky());
+
+            GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+            GL41.glBufferData(GL41.GL_ARRAY_BUFFER, this.data.flip(), GL41.GL_STREAM_DRAW);
+
+            GL41.glDrawArrays(this.drawMode.cap, 0, this.vertexCount);
+            GL41.glBindVertexArray(0);
+        }
+
+        @Override
+        public @NotNull RenderBuffer record(int vao, int vbo) {
+            if(!this.drawing) {
+                throw new IllegalStateException(this.name + " already drawing!");
+            }
+
+            this.drawing = false;
+
+            GL41.glBindVertexArray(this.vao);
+            GL41.glVertexAttrib2f(3, GLRenderer.getLightmapBlock(), GLRenderer.getLightmapSky());
+
+            GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+            GL41.glBufferData(GL41.GL_ARRAY_BUFFER, this.data.flip(), GL41.GL_STATIC_DRAW);
+
+            GL41.glDrawArrays(this.drawMode.cap, 0, this.vertexCount);
+            GL41.glBindVertexArray(0);
+
+            return new RenderBuffer(vao, vbo, 0, this.vertexCount, this.drawMode);
+        }
+
+        @Override
+        public void setColor1i(int argb) {
+            checkIsDrawing();
+            if (this.lockColor) {
+                return;
+            }
+
+            int a = (argb >> 24) & 0xFF;
+            int r = (argb >> 16) & 0xFF;
+            int g = (argb >> 8) & 0xFF;
+            int b = argb & 0xFF;
+
+            this.color = a << 24 | b << 16 | g << 8 | r;
+        }
+
+        @Override
+        public void lockColor() {
+            checkIsDrawing();
+            this.lockColor = true;
+        }
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/RenderDoubleBase.java b/game/client/src/main/java/net/minecraft/client/render/font/RenderDoubleBase.java
index 24e79b7a0..0f12e6d85 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/RenderDoubleBase.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/RenderDoubleBase.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.render.font;
 
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.util.helper.Color;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
@@ -8,7 +7,6 @@ import org.jetbrains.annotations.Nullable;
 @SuppressWarnings("unused")
 public abstract class RenderDoubleBase {
     protected @NotNull FontRenderer fontRenderer;
-    protected @NotNull Tessellator tessellator;
     protected @NotNull CharSequence chars;
     protected @NotNull Font font;
     protected double x;
@@ -24,11 +22,13 @@ public abstract class RenderDoubleBase {
 
     }
 
-    public @NotNull RenderDoubleBase init(@NotNull final FontRenderer fontRenderer, @NotNull final Tessellator tessellator, @NotNull final CharSequence chars, final double x, final double y, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
-        if (this.needCall) throw new IllegalStateException("Init called before prior draw call!");
+    public @NotNull RenderDoubleBase init(@NotNull final FontRenderer fontRenderer, @NotNull final CharSequence chars, final double x, final double y, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+        if (this.needCall) {
+            this.needCall = false;
+            throw new IllegalStateException("Init called before prior draw call!");
+        }
         this.fontRenderer = fontRenderer;
         this.font = this.fontRenderer.getFont();
-        this.tessellator = tessellator;
         this.chars = chars;
         this.x = x;
         this.y = y;
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/RenderDoubleConstrainedBase.java b/game/client/src/main/java/net/minecraft/client/render/font/RenderDoubleConstrainedBase.java
index 078d8ab3d..f23aef77b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/RenderDoubleConstrainedBase.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/RenderDoubleConstrainedBase.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.render.font;
 
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.util.helper.Color;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
@@ -8,7 +7,6 @@ import org.jetbrains.annotations.Nullable;
 @SuppressWarnings("unused")
 public abstract class RenderDoubleConstrainedBase {
     protected @NotNull FontRenderer fontRenderer;
-    protected @NotNull Tessellator tessellator;
     protected @NotNull CharSequence chars;
     protected @NotNull Font font;
     protected double x;
@@ -27,11 +25,13 @@ public abstract class RenderDoubleConstrainedBase {
 
     }
 
-    public @NotNull RenderDoubleConstrainedBase init(@NotNull final FontRenderer fontRenderer, @NotNull final Tessellator tessellator, @NotNull final CharSequence chars, final double x, final double y, final double maxWidth, final double maxHeight, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
-        if (this.needCall) throw new IllegalStateException("Init called before prior draw call!");
+    public @NotNull RenderDoubleConstrainedBase init(@NotNull final FontRenderer fontRenderer, @NotNull final CharSequence chars, final double x, final double y, final double maxWidth, final double maxHeight, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+        if (this.needCall) {
+            this.needCall = false;
+            throw new IllegalStateException("Init called before prior draw call!");
+        }
         this.fontRenderer = fontRenderer;
         this.font = this.fontRenderer.getFont();
-        this.tessellator = tessellator;
         this.chars = chars;
         this.x = x;
         this.y = y;
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/RenderIntegerBase.java b/game/client/src/main/java/net/minecraft/client/render/font/RenderIntegerBase.java
index 3282f48cd..d4f7d7e0d 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/RenderIntegerBase.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/RenderIntegerBase.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.render.font;
 
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.util.helper.Color;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
@@ -8,7 +7,6 @@ import org.jetbrains.annotations.Nullable;
 @SuppressWarnings("unused")
 public abstract class RenderIntegerBase {
     protected @NotNull FontRenderer fontRenderer;
-    protected @NotNull Tessellator tessellator;
     protected @NotNull CharSequence chars;
     protected @NotNull Font font;
     protected int x;
@@ -24,11 +22,13 @@ public abstract class RenderIntegerBase {
 
     }
 
-    public @NotNull RenderIntegerBase init(@NotNull final FontRenderer fontRenderer, @NotNull final Tessellator tessellator, @NotNull final CharSequence chars, final int x, final int y, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
-        if (this.needCall) throw new IllegalStateException("Init called before prior draw call!");
+    public @NotNull RenderIntegerBase init(@NotNull final FontRenderer fontRenderer, @NotNull final CharSequence chars, final int x, final int y, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+        if (this.needCall) {
+            this.needCall = false;
+            throw new IllegalStateException("Init called before prior draw call!");
+        }
         this.fontRenderer = fontRenderer;
         this.font = this.fontRenderer.getFont();
-        this.tessellator = tessellator;
         this.chars = chars;
         this.x = x;
         this.y = y;
diff --git a/game/client/src/main/java/net/minecraft/client/render/font/RenderIntegerConstrainedBase.java b/game/client/src/main/java/net/minecraft/client/render/font/RenderIntegerConstrainedBase.java
index daddc98e3..74badec98 100644
--- a/game/client/src/main/java/net/minecraft/client/render/font/RenderIntegerConstrainedBase.java
+++ b/game/client/src/main/java/net/minecraft/client/render/font/RenderIntegerConstrainedBase.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.render.font;
 
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.util.helper.Color;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
@@ -8,7 +7,6 @@ import org.jetbrains.annotations.Nullable;
 @SuppressWarnings("unused")
 public abstract class RenderIntegerConstrainedBase {
     protected @NotNull FontRenderer fontRenderer;
-    protected @NotNull Tessellator tessellator;
     protected @NotNull CharSequence chars;
     protected @NotNull Font font;
     protected int x;
@@ -27,11 +25,13 @@ public abstract class RenderIntegerConstrainedBase {
 
     }
 
-    public @NotNull RenderIntegerConstrainedBase init(@NotNull final FontRenderer fontRenderer, @NotNull final Tessellator tessellator, @NotNull final CharSequence chars, final int x, final int y, final int maxWidth, final int maxHeight, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
-        if (this.needCall) throw new IllegalStateException("Init called before prior draw call!");
+    public @NotNull RenderIntegerConstrainedBase init(@NotNull final FontRenderer fontRenderer, @NotNull final CharSequence chars, final int x, final int y, final int maxWidth, final int maxHeight, final double @Nullable [] xPosBuffer, final double @Nullable [] yPosBuffer, final long @Nullable [] configBuffer) {
+        if (this.needCall) {
+            this.needCall = false;
+            throw new IllegalStateException("Init called before prior draw call!");
+        }
         this.fontRenderer = fontRenderer;
         this.font = this.fontRenderer.getFont();
-        this.tessellator = tessellator;
         this.chars = chars;
         this.x = x;
         this.y = y;
diff --git a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModel.java b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModel.java
index 9e833c112..650aa367e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModel.java
+++ b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModel.java
@@ -1,11 +1,16 @@
 package net.minecraft.client.render.item.model;
 
-import net.minecraft.client.render.EntityRenderDispatcher;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import net.minecraft.client.render.ItemRenderer;
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.FrontFace;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.entity.player.Player;
 import net.minecraft.core.item.Item;
@@ -13,8 +18,7 @@ import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 import org.useless.dragonfly.DisplayPos;
 
 public abstract class ItemModel {
@@ -23,40 +27,41 @@ public abstract class ItemModel {
         this.item = item;
     }
 
-    public abstract void render(@NotNull Tessellator tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, @NotNull String displayPosId, boolean items3d, int clusterSize, float brightness, float alpha, float partialTick, boolean mirrorX); // TODO figure out if theres a way to not explicitly need to mirrorX in the model itself
-    public abstract void renderItemOverlayIntoGUI(@NotNull Tessellator tessellator, @NotNull FontRenderer fontRenderer, @NotNull TextureManager textureManager, @NotNull ItemStack itemstack, int x, int y, @Nullable String override, float alpha);
+    public abstract void render(@NotNull TessellatorGeneral tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, @NotNull String displayPosId, boolean items3d, int clusterSize, int lightmapCoord, float partialTick, boolean mirrorX); // TODO figure out if theres a way to not explicitly need to mirrorX in the model itself
+    public abstract void renderItemOverlayIntoGUI(@NotNull TessellatorGeneral tessellator, @NotNull FontRenderer fontRenderer, @NotNull TextureManager textureManager, @NotNull ItemStack itemstack, int x, int y, @Nullable String override, float alpha);
 
-    public void renderGui(@NotNull Tessellator tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, int x, int y, float brightness, float alpha, float partialTick) {
-        GL11.glPushMatrix();
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glDisable(GL11.GL_LIGHTING);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glEnable(GL11.GL_CULL_FACE);
-        GL11.glTranslatef(x + 8, y + 8, 0);
-        GL11.glScalef(16, -16, 1);
-        render(tessellator, holder, itemStack, DisplayPos.GUI, false, 1, brightness, alpha, partialTick, false);
-        GL11.glEnable(GL11.GL_LIGHTING);
-        GL11.glDisable(GL11.GL_CULL_FACE);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glPopMatrix();
+    public void renderGui(@NotNull TessellatorGeneral tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, int x, int y, int lightmapCoord, float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.globalSetLightEnabled(false);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.modelM4f().translate(x + 8, y + 8, 0);
+        GLRenderer.modelM4f().scale(16, -16, 1);
+        render(tessellator, holder, itemStack, DisplayPos.GUI, false, 1, LightmapHelper.getLightmapCoord(15, 15), partialTick, false);
+        GLRenderer.globalSetLightEnabled(true);
+        GLRenderer.popFrame();
     }
 
-    public void renderItemEntity(@NotNull Tessellator tessellator, @NotNull ItemStack itemStack, boolean items3d, int clusterSize, int ticks, float yaw, float brightness, float alpha, float partialTick) {
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glEnable(GL11.GL_BLEND);
+    public void renderItemEntity(@NotNull TessellatorGeneral tessellator, @NotNull ItemStack itemStack, boolean items3d, int clusterSize, int ticks, float yaw, int lightmap, float partialTick) {
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.enableState(State.BLEND);
         if (items3d) {
-            GL11.glRotated(yaw, 0, 1, 0);
+            GLRenderer.modelM4f().rotateY(Math.toRadians(yaw));
         } else {
-            GL11.glRotatef(180F - EntityRenderDispatcher.instance.viewLerpYaw, 0.0F, 1.0F, 0.0F);
+            GLRenderer.modelM4f().rotateY(Math.toRadians(180F - EntityRendererDispatcher.instance.viewLerpYaw));
         }
-        render(tessellator, null, itemStack, DisplayPos.GROUND, items3d, clusterSize, brightness, alpha, partialTick, false);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        render(tessellator, null, itemStack, DisplayPos.GROUND, items3d, clusterSize, lightmap, partialTick, false);
+        GLRenderer.disableState(State.BLEND);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 
-    public void renderFirstPerson(@NotNull Tessellator tessellator, @NotNull ItemRenderer itemRenderer, @NotNull Player player, @NotNull ItemStack itemStack, float brightness, float alpha, float partialTick) {
-        GL11.glPushMatrix();
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+    public void renderFirstPerson(@NotNull TessellatorGeneral tessellator, @NotNull ItemRenderer itemRenderer, @NotNull Player player, @NotNull ItemStack itemStack, int lightmapCoord, float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.CULL_FACE);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
         final float swingProgress = player.getSwingProgress(partialTick);
         final float animationProgress2 = MathHelper.sin(swingProgress * MathHelper.PI);
         final float animationProgress = MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI);
@@ -66,39 +71,39 @@ public abstract class ItemModel {
             final float yOff = -8.25f/16f -(1.0F - itemRenderer.getEquippedProgress(partialTick)) * 0.6F;
             final float zOff = -0.725f;
 
-            GL11.glScalef(-1, 1, 1);
-            GL11.glTranslatef(-animationProgress * 0.4F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.2F, -animationProgress2 * 0.2F); // Makes swing travel in an arc
-            GL11.glTranslatef(xOff, yOff, zOff);
+            GLRenderer.modelM4f().scale(-1, 1, 1);
+            GLRenderer.modelM4f().translate(-animationProgress * 0.4F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.2F, -animationProgress2 * 0.2F); // Makes swing travel in an arc
+            GLRenderer.modelM4f().translate(xOff, yOff, zOff);
 
             float animationProgress3 = MathHelper.sin(swingProgress * swingProgress * MathHelper.PI);
-            GL11.glRotatef(45, 0, 1, 0);
-            GL11.glRotatef(-animationProgress3 * 20F, 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(-animationProgress * 20F, 0.0F, 0.0F, 1.0F);
-            GL11.glRotatef(-animationProgress * 80F, 1.0F, 0.0F, 0.0F);
-            GL11.glRotatef(-45, 0, 1, 0);
+            GLRenderer.modelM4f().rotateY(Math.toRadians(45));
+            GLRenderer.modelM4f().rotateY(Math.toRadians(-animationProgress3) * 20F);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(-animationProgress) * 20F);
+            GLRenderer.modelM4f().rotateX(Math.toRadians(-animationProgress) * 80F);
+            GLRenderer.modelM4f().rotateY(Math.toRadians(-45));
 
-            GL11.glFrontFace(GL11.GL_CW);
-            render(tessellator,player, itemStack, DisplayPos.FIRST_PERSON_LEFT_HAND, true, 1, brightness, alpha, partialTick, true);
-            GL11.glFrontFace(GL11.GL_CCW);
+            GLRenderer.setFrontFace(FrontFace.CW);
+            render(tessellator,player, itemStack, DisplayPos.FIRST_PERSON_LEFT_HAND, true, 1, lightmapCoord, partialTick, true);
+            GLRenderer.setFrontFace(FrontFace.CCW);
         } else {
             final float xOff = 9/16f;
             final float yOff = -8.25f/16f -(1.0F - itemRenderer.getEquippedProgress(partialTick)) * 0.6F;
             final float zOff = -0.725f;
 
-            GL11.glTranslatef(-animationProgress * 0.4F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.2F, -animationProgress2 * 0.2F); // Makes swing travel in an arc
-            GL11.glTranslatef(xOff, yOff, zOff);
+            GLRenderer.modelM4f().translate(-animationProgress * 0.4F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.2F, -animationProgress2 * 0.2F); // Makes swing travel in an arc
+            GLRenderer.modelM4f().translate(xOff, yOff, zOff);
 
             float animationProgress3 = MathHelper.sin(swingProgress * swingProgress * MathHelper.PI);
-            GL11.glRotatef(45, 0, 1, 0);
-            GL11.glRotatef(-animationProgress3 * 20F, 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(-animationProgress * 20F, 0.0F, 0.0F, 1.0F);
-            GL11.glRotatef(-animationProgress * 80F, 1.0F, 0.0F, 0.0F);
-            GL11.glRotatef(-45, 0, 1, 0);
+            GLRenderer.modelM4f().rotateY(Math.toRadians(45));
+            GLRenderer.modelM4f().rotateY(Math.toRadians(-animationProgress3) * 20F);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(-animationProgress) * 20F);
+            GLRenderer.modelM4f().rotateX(Math.toRadians(-animationProgress) * 80F);
+            GLRenderer.modelM4f().rotateY(Math.toRadians(-45));
 
-            render(tessellator,player, itemStack, DisplayPos.FIRST_PERSON_RIGHT_HAND, true, 1, brightness, alpha, partialTick, false);
+            render(tessellator,player, itemStack, DisplayPos.FIRST_PERSON_RIGHT_HAND, true, 1, lightmapCoord, partialTick, false);
         }
-        GL11.glPopMatrix();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.popFrame();
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 
     public abstract IconCoordinate getIcon(@Nullable Entity entity, ItemStack itemStack);
diff --git a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelBlock.java b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelBlock.java
index 4d6042d6e..a42708629 100644
--- a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelBlock.java
+++ b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelBlock.java
@@ -3,7 +3,12 @@ package net.minecraft.client.render.item.model;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
 import net.minecraft.client.render.block.model.BlockModel;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.block.model.BlockModelStandard;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.Block;
@@ -12,8 +17,7 @@ import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.item.block.ItemBlock;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 import org.useless.dragonfly.DisplayPos;
 
 public class ItemModelBlock extends ItemModelStandard {
@@ -22,38 +26,34 @@ public class ItemModelBlock extends ItemModelStandard {
     public ItemModelBlock(ItemBlock<?> itemBlock){
         super(itemBlock, null);
         this.block = itemBlock.getBlock();
-        this.blockModel = BlockModelDispatcher.getInstance().getDispatch(block);
-        icon = blockModel.getOverlayTexture(0);
+        this.blockModel = BlockModelDispatcher.getInstance().getDispatch(this.block);
+        this.icon = this.blockModel.getOverlayTexture(0);
     }
 
     @Override
     public @NotNull IconCoordinate getIcon(@Nullable Entity entity, ItemStack itemStack) {
-        return this.blockModel.getOverlayTexture(itemStack.getMetadata());
+        IconCoordinate overlay = this.blockModel.getOverlayTexture(itemStack.getMetadata());
+        return overlay != null ? overlay : BlockModelStandard.BLOCK_TEXTURE_UNASSIGNED;
     }
 
     @Override
     public @NotNull DisplayPos getDisplayPos(@NotNull String id) {
-        return blockModel.shouldItemRender3d() ? this.blockModel.getItemDisplayPos(id) : super.getDisplayPos(id); // TODO this is jank fix with proper implementation
+        return this.blockModel.shouldItemRender3d() ? this.blockModel.getItemDisplayPos(id) : super.getDisplayPos(id); // TODO this is jank fix with proper implementation
     }
 
     @Override
-    public void render(@NotNull Tessellator tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, @NotNull String displayPosId, boolean items3d, int clusterSize, float brightness, float alpha, float partialTick, boolean mirrorX) {
-        if (!blockModel.shouldItemRender3d()) {
-            super.render(tessellator, holder, itemStack, displayPosId, items3d, clusterSize, brightness, alpha, partialTick, mirrorX);
+    public void render(@NotNull TessellatorGeneral tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, @NotNull String displayPosId, boolean items3d, int clusterSize, int lightmapCoord, float partialTick, boolean mirrorX) {
+        if (!this.blockModel.shouldItemRender3d()) {
+            super.render(tessellator, holder, itemStack, displayPosId, items3d, clusterSize, lightmapCoord, partialTick, mirrorX);
             return;
         }
         random.setSeed(187L);
         DisplayPos displayPos = getDisplayPos(displayPosId);
-        GL11.glTranslatef(displayPos.tx, displayPos.ty, displayPos.tz);
-        GL11.glRotatef(displayPos.rx, 1, 0, 0);
-        GL11.glRotatef(displayPos.ry, 0, 1, 0);
-        GL11.glRotatef(displayPos.rz, 0, 0, 1);
-        GL11.glScalef(displayPos.sx, displayPos.sy, displayPos.sz);
-        int color = getColor(itemStack);
-        float r = net.minecraft.core.util.helper.Color.redFromInt(color)/255f;
-        float g = net.minecraft.core.util.helper.Color.greenFromInt(color)/255f;
-        float b = net.minecraft.core.util.helper.Color.blueFromInt(color)/255f;
-        GL11.glColor4f(brightness * r, brightness * g, brightness * b, alpha);
+        GLRenderer.modelM4f().translate(displayPos.tx, displayPos.ty, displayPos.tz);
+        GLRenderer.modelM4f().rotateX(Math.toRadians(displayPos.rx));
+        GLRenderer.modelM4f().rotateY(Math.toRadians(displayPos.ry));
+        GLRenderer.modelM4f().rotateZ(Math.toRadians(displayPos.rz));
+        GLRenderer.modelM4f().scale(displayPos.sx, displayPos.sy, displayPos.sz);
         for (int i = 0; i < clusterSize; i++) {
             float rOffX = 0;
             float rOffY = 0;
@@ -63,57 +63,56 @@ public class ItemModelBlock extends ItemModelStandard {
                 rOffY = ((random.nextFloat() * 2.0F - 1.0F) * 0.2F) / displayPos.sy;
                 rOffZ = ((random.nextFloat() * 2.0F - 1.0F) * 0.2F) / displayPos.sz;
             }
-            GL11.glTranslatef(rOffX, rOffY, rOffZ);
-            renderSingle(tessellator, holder, itemStack, items3d, brightness, alpha, partialTick, mirrorX);
-            GL11.glTranslatef(-rOffX, -rOffY, -rOffZ);
+            GLRenderer.modelM4f().translate(rOffX, rOffY, rOffZ);
+            renderSingle(tessellator, holder, itemStack, items3d, lightmapCoord, getColor(itemStack), partialTick, mirrorX);
+            GLRenderer.modelM4f().translate(-rOffX, -rOffY, -rOffZ);
         }
     }
 
     @Override
-    protected void renderSingle(@NotNull Tessellator tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, boolean items3d, float brightness, float alpha, float partialTick, boolean mirrorX) {
-        if (!blockModel.shouldItemRender3d()) {
-            super.renderSingle(tessellator, holder,itemStack, items3d, brightness, alpha, partialTick, mirrorX);
+    protected void renderSingle(@NotNull TessellatorGeneral tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, boolean items3d, int lightmapCoord, int color, float partialTick, boolean mirrorX) {
+        if (!this.blockModel.shouldItemRender3d()) {
+            super.renderSingle(tessellator, holder, itemStack, items3d, lightmapCoord, color, partialTick, mirrorX);
         } else {
-            TextureRegistry.blockAtlas.bind();
-            blockModel.renderStandalone(tessellator, itemStack.getMetadata(), brightness, alpha, null);
+            TextureRegistry.worldAtlas.bind();
+            this.blockModel.renderStandalone(tessellator, itemStack.getMetadata(), lightmapCoord);
         }
     }
 
     @Override
-    public void renderGui(@NotNull Tessellator tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, int x, int y, float brightness, float alpha, float partialTick) {
-        if (!blockModel.shouldItemRender3d()) {
-            super.renderGui(tessellator, holder, itemStack, x, y, brightness, alpha, partialTick);
+    public void renderGui(@NotNull TessellatorGeneral tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, int x, int y, int lightmapCoord, float partialTick) {
+        if (!this.blockModel.shouldItemRender3d()) {
+            super.renderGui(tessellator, holder, itemStack, x, y, lightmapCoord, partialTick);
             return;
         }
-        GL11.glPushMatrix();
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-        GL11.glEnable(GL11.GL_CULL_FACE);
-        GL11.glTranslatef(x + 8, y + 8, 8);
-        GL11.glScalef(16, -16, 16);
-        render(tessellator, holder, itemStack, DisplayPos.GUI, false, 1, brightness, alpha, partialTick, false);
-        GL11.glDisable(GL11.GL_CULL_FACE);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glPopMatrix();
+        GLRenderer.pushFrame();
+        GLRenderer.setShader(Shaders.WORLD);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.modelM4f().translate(x + 8, y + 8, 8);
+        GLRenderer.modelM4f().scale(16f, -16f, 16f);
+        render(tessellator, holder, itemStack, DisplayPos.GUI, false, 1, lightmapCoord, partialTick, false);
+        GLRenderer.popFrame();
     }
 
     @Override
-    public void renderItemEntity(@NotNull Tessellator tessellator, @NotNull ItemStack itemStack, boolean items3d, int clusterSize, int ticks, float yaw, float brightness, float alpha, float partialTick) {
-        if (!blockModel.shouldItemRender3d()) {
-            super.renderItemEntity(tessellator, itemStack, items3d, clusterSize, ticks, yaw, brightness, alpha, partialTick);
+    public void renderItemEntity(@NotNull TessellatorGeneral tessellator, @NotNull ItemStack itemStack, boolean items3d, int clusterSize, int ticks, float yaw, int lightmap, float partialTick) {
+        if (!this.blockModel.shouldItemRender3d()) {
+            super.renderItemEntity(tessellator, itemStack, items3d, clusterSize, ticks, yaw, lightmap, partialTick);
             return;
         }
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glRotated(yaw, 0, 1, 0);
-        render(tessellator, null, itemStack, DisplayPos.GROUND, items3d, clusterSize, brightness, alpha, partialTick, false);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(yaw));
+        render(tessellator, null, itemStack, DisplayPos.GROUND, items3d, clusterSize, lightmap, partialTick, false);
+        GLRenderer.disableState(State.BLEND);
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 
     @Override
     public int getColor(ItemStack stack)
     {
-        return BlockColorDispatcher.getInstance().getDispatch(block).getFallbackColor(stack.getMetadata(), 0);
+        return BlockColorDispatcher.getInstance().getDispatch(this.block).getFallbackColor(stack.getMetadata(), 0);
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelBow.java b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelBow.java
index 665a70ba6..d7e1c3749 100644
--- a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelBow.java
+++ b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelBow.java
@@ -1,7 +1,8 @@
 package net.minecraft.client.render.item.model;
 
 import net.minecraft.client.entity.player.PlayerRemote;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.entity.monster.MobSkeleton;
 import net.minecraft.core.entity.player.Player;
@@ -10,7 +11,7 @@ import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.item.Items;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
+import org.joml.Math;
 
 public class ItemModelBow extends ItemModelStandard {
     public ItemModelBow(Item item, String namespace) {
@@ -18,33 +19,32 @@ public class ItemModelBow extends ItemModelStandard {
     }
 
     @Override
-    protected void renderSingle(@NotNull Tessellator tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, boolean items3d, float brightness, float alpha, float partialTick, boolean mirrorX) {
-        super.renderSingle(tessellator, holder, itemStack, items3d, brightness, alpha, partialTick, mirrorX);
+    protected void renderSingle(@NotNull TessellatorGeneral tessellator, @Nullable Entity holder, @NotNull ItemStack itemStack, boolean items3d, int lightmapCoord, int color, float partialTick, boolean mirrorX) {
+        super.renderSingle(tessellator, holder, itemStack, items3d, lightmapCoord, color, partialTick, mirrorX);
         Item nextArrow = null;
-        if (holder instanceof Player){
-            Player entityplayer = (Player)holder;
-            nextArrow = getNextArrow(entityplayer);
-        } else if (holder instanceof MobSkeleton){
-            if (((MobSkeleton) holder).attackTime < 5){
+        if (holder instanceof Player player) {
+            nextArrow = getNextArrow(player);
+        } else if (holder instanceof MobSkeleton skeleton) {
+            if (skeleton.attackTime < 5) {
                 nextArrow = Items.AMMO_ARROW;
             }
         }
-        if (nextArrow != null){
-            GL11.glPushMatrix();
+        if (nextArrow != null) {
+            GLRenderer.pushFrame();
             if (mirrorX) {
-                GL11.glRotatef(-90, 0, 0, 1);
+                GLRenderer.modelM4f().rotateZ(-Math.PI_OVER_2_f);
             } else {
-                GL11.glRotatef(90, 0, 0, 1);
+                GLRenderer.modelM4f().rotateZ(Math.PI_OVER_2_f);
             }
-            GL11.glTranslatef(0.0001f, 0.0001f, 0);
-            GL11.glScalef(1, 1, 0.999f);
-            renderCoordinate(tessellator, ItemModelDispatcher.getInstance().getDispatch(nextArrow).getIcon(holder, nextArrow.getDefaultStack()), items3d, mirrorX);
-            GL11.glPopMatrix();
+            GLRenderer.modelM4f().translate(0.0001f, 0.0001f, 0);
+            GLRenderer.modelM4f().scale(1, 1, 0.999f);
+            renderCoordinate(tessellator, ItemModelDispatcher.getInstance().getDispatch(nextArrow).getIcon(holder, nextArrow.getDefaultStack()), lightmapCoord, color, items3d, mirrorX);
+            GLRenderer.popFrame();
         }
     }
 
-    public Item getNextArrow(Player player){
-        if (player instanceof PlayerRemote){
+    public Item getNextArrow(Player player) {
+        if (player instanceof PlayerRemote) {
             int id = player.getArrowId();
             if (id < 0 || id >= Item.itemsList.length) return null;
             return Item.itemsList[id];
diff --git a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelMap.java b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelMap.java
index 5317abc54..b522f4f53 100644
--- a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelMap.java
+++ b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelMap.java
@@ -1,13 +1,14 @@
 package net.minecraft.client.render.item.model;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.EntityRenderDispatcher;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import net.minecraft.client.render.ItemRenderer;
 import net.minecraft.client.render.MapItemRenderer;
 import net.minecraft.client.render.PlayerSkinParser;
 import net.minecraft.client.render.entity.EntityRenderer;
 import net.minecraft.client.render.entity.MobRendererPlayer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.entity.Entity;
@@ -20,8 +21,7 @@ import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.saveddata.maps.ItemMapSavedData;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
+import org.joml.Math;
 
 public class ItemModelMap extends ItemModelStandard {
     private final Minecraft mc = Minecraft.getMinecraft();
@@ -30,102 +30,105 @@ public class ItemModelMap extends ItemModelStandard {
     public ItemModelMap(Item item, String namespace) {
         super(item, namespace);
     }
+
     @Override
-    public void renderFirstPerson(@NotNull Tessellator tessellator, @NotNull ItemRenderer itemRenderer, @NotNull Player player, @NotNull ItemStack itemStack, float brightness, float alpha, float partialTick) {
+    public void renderFirstPerson(@NotNull TessellatorGeneral tessellator, @NotNull ItemRenderer itemRenderer, @NotNull Player player, @NotNull ItemStack itemStack, int lightmapCoord, float partialTick) {
         // The map renders very differently from any other item, so has its own custom first person render code
         if (ItemMap.hasInitialized(itemStack)) {
-            GL11.glPushMatrix();
-            GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+            GLRenderer.pushFrame();
+//            GL11.glEnable(GL12.GL_RESCALE_NORMAL);
 
             final float rotationPitch = player.xRotO + (player.xRot - player.xRotO) * partialTick;
             final float swingProgress = player.getSwingProgress(partialTick);
             final float f_z = MathHelper.sin(swingProgress * MathHelper.PI);
             final float f_x = MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI);
-            GL11.glTranslatef(-f_x * 0.4F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.2F, -f_z * 0.2F);
+            GLRenderer.modelM4f().translate(-f_x * 0.4F, MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI * 2.0F) * 0.2F, -f_z * 0.2F);
 
             float f_val = MathHelper.clamp((1.0F - rotationPitch / 45F) + 0.1F, 0, 1);
             f_val = -MathHelper.cos(f_val * MathHelper.PI) * 0.5F + 0.5F;
             final float zOff = 0.8F * -0.9F;
-            GL11.glTranslatef(0.0F, (-(1.0F - itemRenderer.getEquippedProgress(partialTick)) * 1.2F - f_val * 0.5F) + 0.04F, zOff); // Place map at right distance from camera
-            GL11.glRotatef(90F, 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(f_val * -85F, 0.0F, 0.0F, 1.0F);
-            GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+            GLRenderer.modelM4f().translate(0.0F, (-(1.0F - itemRenderer.getEquippedProgress(partialTick)) * 1.2F - f_val * 0.5F) + 0.04F, zOff); // Place map at right distance from camera
+            GLRenderer.modelM4f().rotateY(Math.PI_OVER_2_f);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(f_val * -85F));
+//            GL11.glEnable(GL12.GL_RESCALE_NORMAL);
 
             // Render both player arms
-            mc.textureManager.bindDownloadableTexture(mc.thePlayer.skinURL, mc.thePlayer.getEntityTexture(), mc.thePlayer.slimModel ? PlayerSkinParser.instanceAlex : PlayerSkinParser.instanceSteve);
-            MobRendererPlayer playerRenderer = (MobRendererPlayer) (EntityRenderer<? extends Entity>) EntityRenderDispatcher.instance.getRenderer(mc.thePlayer);
-
-            GL11.glPushMatrix();
-            GL11.glTranslatef(-0F, -0.6F, -1.1F);
-            GL11.glRotatef(180, 0, 1, 0);
-            GL11.glRotatef(-45, 1.0F, 0.0F, 0.0F);
-            GL11.glRotatef(90F - 59F, 0.0F, 0.0F, 1.0F);
-            GL11.glRotatef(65, 0.0F, 1.0F, 0.0F);
-            GL11.glPushMatrix();
-            GL11.glScalef(1/16f, 1/16f, -1/16f);
-            GL11.glTranslatef(0, 16, 0);
-            GL11.glRotatef(180, 1, 0, 0);
-            GL11.glTranslatef(0, -16, 0);
-            GL11.glTranslatef(0, 8, 0);
-            playerRenderer.drawFirstPersonHand(Tessellator.instance, mc.thePlayer, true);
-            GL11.glPopMatrix();
-            GL11.glPopMatrix();
-            GL11.glPushMatrix();
-            GL11.glTranslatef(-0F, -0.6F, 1.1F);
-            GL11.glRotatef(-45, 1.0F, 0.0F, 0.0F);
-            GL11.glRotatef(-90F + 59F, 0.0F, 0.0F, 1.0F);
-            GL11.glRotatef(-65, 0.0F, 1.0F, 0.0F);
-            GL11.glPushMatrix();
-            GL11.glScalef(1/16f, 1/16f, -1/16f);
-            GL11.glTranslatef(0, 16, 0);
-            GL11.glRotatef(180, 1, 0, 0);
-            GL11.glTranslatef(0, -16, 0);
-            GL11.glTranslatef(0, 8, 0);
-            playerRenderer.drawFirstPersonHand(Tessellator.instance, mc.thePlayer, false);
-            GL11.glPopMatrix();
-            GL11.glPopMatrix();
+            this.mc.textureManager.bindDownloadableTexture(this.mc.thePlayer.skinURL, this.mc.thePlayer.getEntityTexture(), this.mc.thePlayer.slimModel ? PlayerSkinParser.instanceAlex : PlayerSkinParser.instanceSteve);
+            MobRendererPlayer playerRenderer = (MobRendererPlayer) (EntityRenderer<? extends Entity>) EntityRendererDispatcher.instance.getRenderer(this.mc.thePlayer);
+
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().translate(-0F, -0.6F, -1.1F);
+            GLRenderer.modelM4f().rotateY(Math.PI_f);
+            GLRenderer.modelM4f().rotateX(-Math.PI_OVER_4_f);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(90F - 59F));
+            GLRenderer.modelM4f().rotateY(Math.toRadians(65));
+
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().scale(1 / 16f, 1 / 16f, -1 / 16f);
+            GLRenderer.modelM4f().translate(0, 16, 0);
+            GLRenderer.modelM4f().rotateX(Math.PI_f);
+            GLRenderer.modelM4f().translate(0, -16, 0);
+            GLRenderer.modelM4f().translate(0, 8, 0);
+            playerRenderer.drawFirstPersonHand(GLRenderer.getTessellator(), this.mc.thePlayer, true);
+            GLRenderer.popFrame();
+            GLRenderer.popFrame();
+
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().translate(-0F, -0.6F, 1.1F);
+            GLRenderer.modelM4f().rotateX(-Math.PI_OVER_4_f);
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(-90F + 59F));
+            GLRenderer.modelM4f().rotateY(Math.toRadians(-65));
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().scale(1 / 16f, 1 / 16f, -1 / 16f);
+            GLRenderer.modelM4f().translate(0, 16, 0);
+            GLRenderer.modelM4f().rotateX(Math.PI_f);
+            GLRenderer.modelM4f().translate(0, -16, 0);
+            GLRenderer.modelM4f().translate(0, 8, 0);
+            playerRenderer.drawFirstPersonHand(GLRenderer.getTessellator(), this.mc.thePlayer, false);
+            GLRenderer.popFrame();
+            GLRenderer.popFrame();
 
 
             final float f_val3 = MathHelper.sin(swingProgress * swingProgress * MathHelper.PI);
             final float f_val4 = MathHelper.sin(MathHelper.sqrt_float(swingProgress) * MathHelper.PI);
-            GL11.glRotatef(-f_val3 * 20F, 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(-f_val4 * 20F, 0.0F, 0.0F, 1.0F);
-            GL11.glRotatef(-f_val4 * 80F, 1.0F, 0.0F, 0.0F);
+            GLRenderer.modelM4f().rotateY(Math.toRadians(-f_val3 * 20F));
+            GLRenderer.modelM4f().rotateZ(Math.toRadians(-f_val4 * 20F));
+            GLRenderer.modelM4f().rotateX(Math.toRadians(-f_val4 * 80F));
 
             final float scale1 = 0.38F;
-            GL11.glScalef(scale1, scale1, scale1);
-            GL11.glRotatef(90F, 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(180F, 0.0F, 0.0F, 1.0F);
-            GL11.glTranslatef(-1F, -1F, 0.0F);
+            GLRenderer.modelM4f().scale(scale1, scale1, scale1);
+            GLRenderer.modelM4f().rotateY(Math.PI_OVER_2_f);
+            GLRenderer.modelM4f().rotateZ(Math.PI_f);
+            GLRenderer.modelM4f().translate(-1F, -1F, 0.0F);
 
             final float scale2 = 0.015625F;
-            GL11.glScalef(scale2, scale2, scale2);
+            GLRenderer.modelM4f().scale(scale2, scale2, scale2);
 
-            GL11.glNormal3f(0.0F, 0.0F, -1F);
+//            GL11.glNormal3f(0.0F, 0.0F, -1F);
 
             // Render paper background of map
-            mc.textureManager.bindTexture(mc.textureManager.loadTexture("/assets/minecraft/textures/misc/mapbg.png"));
+            this.mc.textureManager.bindTexture(this.mc.textureManager.loadTexture("/assets/minecraft/textures/misc/mapbg.png"));
             tessellator.startDrawingQuads();
             final byte expansion = 7; // makes the edges extend around the actual map data by a bit
-            tessellator.addVertexWithUV(-expansion,     128 + expansion, 0.0D, 0.0D, 1.0D);
-            tessellator.addVertexWithUV(128 + expansion,128 + expansion, 0.0D, 1.0D, 1.0D);
-            tessellator.addVertexWithUV(128 + expansion,-expansion,      0.0D, 1.0D, 0.0D);
-            tessellator.addVertexWithUV(-expansion,     -expansion,      0.0D, 0.0D, 0.0D);
+            tessellator.addVertexWithUV(-expansion, 128 + expansion, 0.0D, 0.0D, 1.0D);
+            tessellator.addVertexWithUV(128 + expansion, 128 + expansion, 0.0D, 1.0D, 1.0D);
+            tessellator.addVertexWithUV(128 + expansion, -expansion, 0.0D, 1.0D, 0.0D);
+            tessellator.addVertexWithUV(-expansion, -expansion, 0.0D, 0.0D, 0.0D);
             tessellator.draw();
 
-            ItemMapSavedData mapData = Items.MAP.getOrCreateSavedData(itemStack, mc.currentWorld);
+            ItemMapSavedData mapData = Items.MAP.getOrCreateSavedData(itemStack, this.mc.currentWorld);
             if (mapData != null) {
-                renderMapInstance.renderMap(tessellator, mapData, brightness);
+                this.renderMapInstance.renderMap(tessellator, mapData);
             }
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         } else {
-            super.renderFirstPerson(tessellator, itemRenderer, player, itemStack, brightness, alpha, partialTick);
+            super.renderFirstPerson(tessellator, itemRenderer, player, itemStack, lightmapCoord, partialTick);
         }
     }
 
     @Override
-    public @NotNull IconCoordinate getIcon(@Nullable Entity entity, ItemStack itemStack){
-        if (!ItemMap.hasInitialized(itemStack)){
+    public @NotNull IconCoordinate getIcon(@Nullable Entity entity, ItemStack itemStack) {
+        if (!ItemMap.hasInitialized(itemStack)) {
             return TextureRegistry.getTexture("minecraft:item/map_blank");
         }
         return super.getIcon(entity, itemStack);
diff --git a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelNone.java b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelNone.java
index 2587cc04a..2d01d27c5 100644
--- a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelNone.java
+++ b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelNone.java
@@ -3,7 +3,7 @@ package net.minecraft.client.render.item.model;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.item.ItemStack;
 import org.jetbrains.annotations.NotNull;
@@ -16,12 +16,12 @@ public class ItemModelNone extends ItemModel{
 
 
     @Override
-    public void render(@NotNull final Tessellator tessellator, @Nullable final Entity holder, @NotNull final ItemStack itemStack, @NotNull final String displayPosId, final boolean items3d, final int clusterSize, final float brightness, final float alpha, final float partialTick, final boolean mirrorX) {
+    public void render(@NotNull final TessellatorGeneral tessellator, @Nullable final Entity holder, @NotNull final ItemStack itemStack, @NotNull final String displayPosId, final boolean items3d, final int clusterSize, int lightmapCoord, final float partialTick, final boolean mirrorX) {
 
     }
 
     @Override
-    public void renderItemOverlayIntoGUI(@NotNull final Tessellator tessellator, @NotNull final FontRenderer fontRenderer, @NotNull final TextureManager textureManager, @NotNull final ItemStack itemstack, final int x, final int y, @Nullable final String override, final float alpha) {
+    public void renderItemOverlayIntoGUI(@NotNull final TessellatorGeneral tessellator, @NotNull final FontRenderer fontRenderer, @NotNull final TextureManager textureManager, @NotNull final ItemStack itemstack, final int x, final int y, @Nullable final String override, final float alpha) {
 
     }
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelStandard.java b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelStandard.java
index 377bbd9a6..4caa237e7 100644
--- a/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelStandard.java
+++ b/game/client/src/main/java/net/minecraft/client/render/item/model/ItemModelStandard.java
@@ -1,18 +1,20 @@
 package net.minecraft.client.render.item.model;
 
+import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.item.Item;
 import net.minecraft.core.item.ItemStack;
-import net.minecraft.core.util.collection.NamespaceID;
-import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 
 import java.awt.*;
@@ -21,14 +23,6 @@ import java.util.Map;
 import java.util.Objects;
 import java.util.Random;
 
-import static org.lwjgl.opengl.GL11.GL_BLEND;
-import static org.lwjgl.opengl.GL11.GL_DEPTH_TEST;
-import static org.lwjgl.opengl.GL11.GL_LIGHTING;
-import static org.lwjgl.opengl.GL11.GL_TEXTURE_2D;
-import static org.lwjgl.opengl.GL11.glBlendFunc;
-import static org.lwjgl.opengl.GL11.glDisable;
-import static org.lwjgl.opengl.GL11.glEnable;
-
 public class ItemModelStandard extends ItemModel{
     protected static final Random random = new Random();
 
@@ -62,28 +56,23 @@ public class ItemModelStandard extends ItemModel{
     }
 
     @Override
-    public void render(@NotNull final Tessellator tessellator, @Nullable final Entity holder, @NotNull final ItemStack itemStack, @NotNull final String displayPosId, final boolean items3d, final int clusterSize, final float brightness, final float alpha, final float partialTick, final boolean mirrorX) {
+    public void render(@NotNull final TessellatorGeneral tessellator, @Nullable final Entity holder, @NotNull final ItemStack itemStack, @NotNull final String displayPosId, final boolean items3d, final int clusterSize, int lightmapCoord, final float partialTick, final boolean mirrorX) {
         random.setSeed(187L);
         final DisplayPos displayPos = getDisplayPos(displayPosId);
 
-        GL11.glTranslatef(displayPos.tx, displayPos.ty, displayPos.tz);
-        GL11.glRotatef(displayPos.rx, 1, 0, 0);
-        GL11.glRotatef(displayPos.ry, 0, 1, 0);
-        GL11.glRotatef(displayPos.rz, 0, 0, 1);
-        GL11.glScalef(displayPos.sx, displayPos.sy, displayPos.sz);
-        final int color = getColor(itemStack);
-        final float r = net.minecraft.core.util.helper.Color.redFromInt(color)/255f;
-        final float g = net.minecraft.core.util.helper.Color.greenFromInt(color)/255f;
-        final float b = net.minecraft.core.util.helper.Color.blueFromInt(color)/255f;
-        GL11.glColor4f(brightness * r, brightness * g, brightness * b, alpha);
+        GLRenderer.modelM4f().translate(displayPos.tx, displayPos.ty, displayPos.tz);
+        GLRenderer.modelM4f().rotateX(org.joml.Math.toRadians(displayPos.rx));
+        GLRenderer.modelM4f().rotateY(org.joml.Math.toRadians(displayPos.ry));
+        GLRenderer.modelM4f().rotateZ(org.joml.Math.toRadians(displayPos.rz));
+        GLRenderer.modelM4f().scale(displayPos.sx, displayPos.sy, displayPos.sz);
         if (items3d) {
             for (int i = 0; i < clusterSize; i++) {
                 final float offX = 0;
                 final float offY = 0;
                 final float offZ = 0.1f * i;
-                GL11.glTranslatef(offX, offY, offZ);
-                renderSingle(tessellator, holder, itemStack, true, brightness, alpha, partialTick, mirrorX);
-                GL11.glTranslatef(-offX, -offY, -offZ);
+                GLRenderer.modelM4f().translate(offX, offY, offZ);
+                renderSingle(tessellator, holder, itemStack, true, lightmapCoord, getColor(itemStack), partialTick, mirrorX);
+                GLRenderer.modelM4f().translate(-offX, -offY, -offZ);
             }
         } else {
             for (int i = 0; i < clusterSize; i++) {
@@ -95,18 +84,18 @@ public class ItemModelStandard extends ItemModel{
                     rOffY = ((random.nextFloat() * 2.0F - 1.0F) * 0.2F) / displayPos.sy;
                     rOffZ = ((random.nextFloat() * 2.0F - 1.0F) * 0.2F) / displayPos.sz;
                 }
-                GL11.glTranslatef(rOffX, rOffY, rOffZ);
-                renderSingle(tessellator, holder, itemStack, false, brightness, alpha, partialTick, mirrorX);
-                GL11.glTranslatef(-rOffX, -rOffY, -rOffZ);
+                GLRenderer.modelM4f().translate(rOffX, rOffY, rOffZ);
+                renderSingle(tessellator, holder, itemStack, false, lightmapCoord, getColor(itemStack), partialTick, mirrorX);
+                GLRenderer.modelM4f().translate(-rOffX, -rOffY, -rOffZ);
             }
         }
     }
 
-    protected void renderSingle(@NotNull final Tessellator tessellator, @Nullable final Entity holder, @NotNull final ItemStack itemStack, final boolean items3d, final float brightness, final float alpha, final float partialTick, final boolean mirrorX) {
-        renderCoordinate(tessellator, getIcon(holder, itemStack), items3d, mirrorX);
+    protected void renderSingle(@NotNull final TessellatorGeneral tessellator, @Nullable final Entity holder, @NotNull final ItemStack itemStack, final boolean items3d, int lightmapCoord, int color, final float partialTick, final boolean mirrorX) {
+        renderCoordinate(tessellator, getIcon(holder, itemStack), this.itemfullBright ? LightmapHelper.getLightmapCoord(15, 15) : lightmapCoord, color, items3d, mirrorX);
     }
 
-    protected void renderCoordinate(@NotNull final Tessellator tessellator, @NotNull final IconCoordinate coordinate, final boolean items3d, final boolean mirrorX) {
+    protected void renderCoordinate(@NotNull final TessellatorGeneral tessellator, @NotNull final IconCoordinate coordinate, int lightmap, int color, final boolean items3d, final boolean mirrorX) {
         final double cUMin = mirrorX ? coordinate.getIconUMax() : coordinate.getIconUMin();
         final double cUMax = mirrorX ? coordinate.getIconUMin() : coordinate.getIconUMax();
         final double cVMin = coordinate.getIconVMin();
@@ -119,6 +108,8 @@ public class ItemModelStandard extends ItemModel{
             final int pxW = coordinate.width;
 
             tessellator.startDrawingQuads();
+            tessellator.setLightmapCoord1i(lightmap);
+            tessellator.setColor1i(color);
             // front
             tessellator.setNormal(0, 0, -1);
             tessellator.addVertexWithUV(-0.5,  0.5, -halfThickness, cUMin, cVMin);
@@ -181,6 +172,8 @@ public class ItemModelStandard extends ItemModel{
             tessellator.draw();
         } else {
             tessellator.startDrawingQuads();
+            tessellator.setLightmapCoord1i(lightmap);
+            tessellator.setColor1i(color);
             tessellator.setNormal(0, 1, 0);
             tessellator.addVertexWithUV(-0.5,  0.5, 0, cUMin, cVMin);
             tessellator.addVertexWithUV(-0.5, -0.5, 0, cUMin, cVMax);
@@ -206,46 +199,46 @@ public class ItemModelStandard extends ItemModel{
     }
 
     @Override
-    public void renderItemOverlayIntoGUI(@NotNull final Tessellator tessellator, @NotNull final FontRenderer fontRenderer, @NotNull final TextureManager textureManager, @NotNull final ItemStack itemstack, final int x, final int y, @Nullable final String override, final float alpha) {
-        glEnable(GL_BLEND);
-        glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+    public void renderItemOverlayIntoGUI(@NotNull final TessellatorGeneral tessellator, @NotNull final FontRenderer fontRenderer, @NotNull final TextureManager textureManager, @NotNull final ItemStack itemstack, final int x, final int y, @Nullable final String override, final float alpha) {
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         final int a = (int) (alpha * 255.0f);
         if (itemstack.stackSize != 1 || override != null) {
             final String s = override != null ? override : "" + itemstack.stackSize;
-            GL11.glDisable(GL_LIGHTING);
-            GL11.glDisable(GL_DEPTH_TEST);
-            fontRenderer.render(tessellator, s, (x + 19) - 2 - fontRenderer.stringWidth(s), y + 6 + 3).setShadow().setColor(0xffffff | (a << 24)).call();
-            GL11.glEnable(GL_LIGHTING);
-            GL11.glEnable(GL_DEPTH_TEST);
+//            GL11.glDisable(GL_LIGHTING);
+            GLRenderer.disableState(State.DEPTH_TEST);
+            fontRenderer.render(s, (x + 19) - 2 - fontRenderer.stringWidth(s), y + 6 + 3).setShadow().setColor(0xffffff | (a << 24)).call();
+//            GL11.glEnable(GL_LIGHTING);
+            GLRenderer.enableState(State.DEPTH_TEST);
         }
         if (itemstack.isItemDamaged() || itemstack.getItem().showFullDurability()) {
             final int barWidth = (int) Math.round(13D - (itemstack.getItemDamageForDisplay() * 13D) / itemstack.getMaxDamage());
             final int progress = (int) Math.round(255D - (itemstack.getItemDamageForDisplay() * 255D) / itemstack.getMaxDamage());
-            GL11.glDisable(GL_LIGHTING);
-            GL11.glDisable(GL_DEPTH_TEST);
-            GL11.glDisable(GL_TEXTURE_2D);
+//            GL11.glDisable(GL_LIGHTING);
+            GLRenderer.pushFrame();
+            GLRenderer.disableState(State.DEPTH_TEST);
+            GLRenderer.setShader(Shaders.COLOR);
             final int colorFG = Color.HSBtoRGB(progress / 255F / 3F, 1f, 1f);
             final int colorBG = (0xFF - progress) / 4 << 16 | 0x3f00;
+            tessellator.startDrawingQuads();
             renderColoredQuad(tessellator, x + 2, y + 13, 13, 2, 0, a);
             renderColoredQuad(tessellator, x + 2, y + 13, 12, 1, colorBG, a);
             renderColoredQuad(tessellator, x + 2, y + 13, barWidth, 1, colorFG, a);
-            GL11.glEnable(GL_TEXTURE_2D);
-            GL11.glEnable(GL_LIGHTING);
-            GL11.glEnable(GL_DEPTH_TEST);
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+            tessellator.draw();
+            GLRenderer.popFrame();
+//            GL11.glEnable(GL_LIGHTING);
         }
-        glDisable(GL_BLEND);
+        GLRenderer.popFrame();
     }
 
-    protected void renderColoredQuad(final Tessellator tessellator, final int x, final int y, final int width, final int height, final int colorRGB, final int alpha) {
+    protected void renderColoredQuad(final TessellatorGeneral tessellator, final int x, final int y, final int width, final int height, final int colorRGB, final int alpha) {
         final float z = 0.0F;
-        tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_I(colorRGB, alpha);
+        tessellator.setColor2i(colorRGB, alpha);
         tessellator.addVertex(x,        y,          z);
         tessellator.addVertex(x,        y + height, z);
         tessellator.addVertex(x + width,y + height, z);
         tessellator.addVertex(x + width,y,          z);
-        tessellator.draw();
     }
 
     public @NotNull IconCoordinate getIcon(@Nullable final Entity entity, final ItemStack itemStack){
@@ -257,7 +250,7 @@ public class ItemModelStandard extends ItemModel{
     }
     public int getColorFromMeta(final int meta)
     {
-        return 0xffffff;
+        return 0xffffffff;
     }
 
     public ItemModelStandard setFullBright()
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/Particle.java b/game/client/src/main/java/net/minecraft/client/render/particle/Particle.java
index f8fb8869f..b7e7fb6a4 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/Particle.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/Particle.java
@@ -1,10 +1,9 @@
 package net.minecraft.client.render.particle;
 
 import it.unimi.dsi.fastutil.objects.ObjectArrayList;
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.ParticleEngine;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.core.Global;
 import net.minecraft.core.block.Block;
@@ -74,9 +73,6 @@ public class Particle {
         this.x = x;
         this.y = y;
         this.z = z;
-        this.xo = this.x;
-        this.yo = this.y;
-        this.zo = this.z;
         this.rCol = this.gCol = this.bCol = 1.0F;
         this.xd = xa + (float) (Math.random() * 2D - 1.0D) * 0.4F;
         this.yd = ya + (float) (Math.random() * 2D - 1.0D) * 0.4F;
@@ -91,10 +87,13 @@ public class Particle {
         this.size = (random.nextFloat() * 0.5F + 0.5F) * 2.0F;
         this.lifetime = (int) (4F / (random.nextFloat() * 0.9F + 0.1F));
         this.age = 0;
+    }
 
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+    public void init() {
+        this.xo = this.x;
+        this.yo = this.y;
+        this.zo = this.z;
+        this.cachedLightmapCoord = calcLightmap(1f);
     }
 
     /**
@@ -120,9 +119,7 @@ public class Particle {
     }
 
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
@@ -272,15 +269,10 @@ public class Particle {
      * @param t           The tessellator to use to draw the particle.
      * @param partialTick The time since the last tick.
      */
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         if (this.tex == null) return;
-        float br = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            t.setLightmapCoord(getLightmap(partialTick));
-        } else if (!Global.accessor.isFullbrightEnabled()) {
-            br = getBrightness(partialTick);
-        }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+        t.setLightmapCoord1i(getLightmap(partialTick));
+        t.setColorOpaque3f(this.rCol, this.gCol, this.bCol);
         t.addParticle(
             MathHelper.lerp(this.xo, this.x, partialTick),
             MathHelper.lerp(this.yo, this.y, partialTick),
@@ -290,12 +282,12 @@ public class Particle {
             this.tex.getIconUSize(), this.tex.getIconVSize());
     }
 
-    public void renderLit(@NotNull Tessellator t, float partialTick, double xOff, double yOff, double zOff) {
+    public void renderLit(@NotNull TessellatorGeneral t, float partialTick, double xOff, double yOff, double zOff) {
 
     }
 
     public int getParticleTexture() {
-        return ParticleEngine.PARTICLE_TEXTURE;
+        return ParticleEngine.WORLD_TEXTURE;
     }
 
     public float calcBrightness(float partialTick) {
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleArrowGolden.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleArrowGolden.java
index ac0a91431..014541f3c 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleArrowGolden.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleArrowGolden.java
@@ -1,7 +1,6 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
@@ -32,7 +31,7 @@ public class ParticleArrowGolden extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float l = ((this.age + partialTick) / this.lifetime) * 32F;
         if (l < 0.0F) {
             l = 0.0F;
@@ -46,9 +45,7 @@ public class ParticleArrowGolden extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleAsh.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleAsh.java
index f91133675..20397c62e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleAsh.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleAsh.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.world.World;
 
@@ -17,9 +16,7 @@ public class ParticleAsh extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleBlockBreaking.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleBlockBreaking.java
index 889106529..b919a180e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleBlockBreaking.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleBlockBreaking.java
@@ -1,13 +1,13 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.ParticleEngine;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
 import net.minecraft.client.render.block.model.BlockModel;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.core.Global;
 import net.minecraft.core.block.Block;
+import net.minecraft.core.enums.LightLayer;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.World;
@@ -17,6 +17,7 @@ import org.jetbrains.annotations.NotNull;
 public class ParticleBlockBreaking extends Particle {
     private final Block<?> block;
     private final Side side;
+    private TilePos initPos = new TilePos(Integer.MAX_VALUE, Integer.MAX_VALUE, Integer.MAX_VALUE);
 
     public ParticleBlockBreaking(World world, double x, double y, double z, double xa, double ya, double za, Block<?> block, Side side, int meta) {
         super(world, x, y, z, xa, ya, za);
@@ -29,6 +30,7 @@ public class ParticleBlockBreaking extends Particle {
     }
 
     public ParticleBlockBreaking init(@NotNull TilePos tilePos) {
+        this.initPos = tilePos;
         int meta = this.world.getBlockData(tilePos);
         BlockModel<?> model = BlockModelDispatcher.getInstance().getDispatch(this.block);
         int index = model.particleColorIndex(this.world, tilePos, this.side, meta);
@@ -42,24 +44,73 @@ public class ParticleBlockBreaking extends Particle {
     }
 
     @Override
-    public int getParticleTexture() {
-        return ParticleEngine.TERRAIN_TEXTURE;
-    }
-
-    @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         if (this.tex == null) return;
-        float br = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            t.setLightmapCoord(getLightmap(partialTick));
-        } else if (!Global.accessor.isFullbrightEnabled()) {
-            br = getBrightness(partialTick);
-        }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+        t.setLightmapCoord1i(getLightmap(partialTick));
+        t.setColorOpaque3f(this.rCol, this.gCol, this.bCol);
         t.addParticle(
             MathHelper.lerp(this.xo, this.x, partialTick),
             MathHelper.lerp(this.yo, this.y, partialTick),
             MathHelper.lerp(this.zo, this.z, partialTick), this.size * 0.1f,
             this.tex.getIconUMin() + (this.tex.getIconUSize() * this.uo / 4F), this.tex.getIconVMin() + (this.tex.getIconVSize() * this.uo / 4F), this.tex.getIconUSize() * 0.25f, this.tex.getIconVSize() * 0.25f);
     }
+
+    @Override
+    public int calcLightmap(float partialTick) {
+        if (Global.accessor.isFullbrightEnabled()) return 15 << 20 | 15;
+        TilePos blockPos = new TilePos(
+            MathHelper.lerp(this.xo, this.x, partialTick),
+            MathHelper.lerp(this.yo, this.y, partialTick),
+            MathHelper.lerp(this.zo, this.z, partialTick));
+
+        final int skylight;
+        final int blocklight;
+        if (this.world.getBlockLitInteriorSurface(blockPos) || blockPos.equals(this.initPos)) {
+            TilePos queryPos = new TilePos();
+
+            int bU = this.world.getSavedLightValue(LightLayer.Block, blockPos.up(queryPos));
+            final int bW = this.world.getSavedLightValue(LightLayer.Block, blockPos.west(queryPos));
+            final int bE = this.world.getSavedLightValue(LightLayer.Block, blockPos.east(queryPos));
+            final int bS = this.world.getSavedLightValue(LightLayer.Block, blockPos.south(queryPos));
+            final int bN = this.world.getSavedLightValue(LightLayer.Block, blockPos.north(queryPos));
+            if (bW > bU) {
+                bU = bW;
+            }
+            if (bE > bU) {
+                bU = bE;
+            }
+            if (bS > bU) {
+                bU = bS;
+            }
+            if (bN > bU) {
+                bU = bN;
+            }
+            blocklight = bU;
+
+            int sU = this.world.getSavedLightValue(LightLayer.Sky, blockPos.up(queryPos));
+            final int sW = this.world.getSavedLightValue(LightLayer.Sky, blockPos.west(queryPos));
+            final int sE = this.world.getSavedLightValue(LightLayer.Sky, blockPos.east(queryPos));
+            final int sS = this.world.getSavedLightValue(LightLayer.Sky, blockPos.south(queryPos));
+            final int sN = this.world.getSavedLightValue(LightLayer.Sky, blockPos.north(queryPos));
+            if (sW > sU) {
+                sU = sW;
+            }
+            if (sE > sU) {
+                sU = sE;
+            }
+            if (sS > sU) {
+                sU = sS;
+            }
+            if (sN > sU) {
+                sU = sN;
+            }
+            skylight = sU;
+
+        } else {
+            skylight = this.world.getSavedLightValue(LightLayer.Sky, blockPos);
+            blocklight = this.world.getSavedLightValue(LightLayer.Block, blockPos);
+        }
+
+        return this.world.getLightmapCoord(skylight, blocklight);
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleBubble.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleBubble.java
index 705badb1e..fc9bb4af9 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleBubble.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleBubble.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.block.material.Materials;
 import net.minecraft.core.world.World;
@@ -25,9 +24,7 @@ public class ParticleBubble extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleExplode.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleExplode.java
index 4adb6a68e..27ca2a5bc 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleExplode.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleExplode.java
@@ -1,6 +1,5 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.world.World;
 
@@ -17,9 +16,7 @@ public class ParticleExplode extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFirefly.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFirefly.java
index 694fcc066..4cab8c024 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFirefly.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFirefly.java
@@ -1,9 +1,9 @@
 package net.minecraft.client.render.particle;
 
 import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.animal.MobFireflyCluster;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
@@ -82,7 +82,7 @@ public class ParticleFirefly extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float ibr = getInternalBrightness(partialTick);
         if (ibr < 0.5f) {
             this.rCol = MathHelper.lerp(this.minR, this.midR, ibr * 2);
@@ -101,7 +101,7 @@ public class ParticleFirefly extends Particle {
         super.render(t, partialTick);
     }
 
-    public void renderParticleInGui(Tessellator t, float partialTick) {
+    public void renderParticleInGui(TessellatorGeneral t, float partialTick) {
         float ibr = getInternalBrightness(partialTick);
         if (ibr < 0.5f) {
             this.rCol = MathHelper.lerp(this.minR, this.midR, ibr * 2);
@@ -125,13 +125,8 @@ public class ParticleFirefly extends Particle {
         float x = (float) (this.xo + (this.x - this.xo) * partialTick);
         float y = (float) (this.yo + (this.y - this.yo) * partialTick);
         float z = (float) (this.zo + (this.z - this.zo) * partialTick);
-        float br = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            t.setLightmapCoord(getLightmap(partialTick));
-        } else {
-            br = getBrightness(partialTick);
-        }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+        t.setLightmapCoord1i(getLightmap(partialTick));
+        t.setColorOpaque3f(this.rCol, this.gCol, this.bCol);
         t.addVertexWithUV(x + r, y - r, z / 10, u2, v2);
         t.addVertexWithUV(x + r, y + r, z / 10, u2, v0);
         t.addVertexWithUV(x - r, y + r, z / 10, u0, v0);
@@ -169,9 +164,7 @@ public class ParticleFirefly extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.sinTimer++;
         if (this.sinTimer > 100) {
             this.sinTimer = 0;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFlame.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFlame.java
index 2030b65b8..19b708ded 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFlame.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFlame.java
@@ -1,7 +1,7 @@
 package net.minecraft.client.render.particle;
 
 import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.MathHelper;
@@ -27,7 +27,7 @@ public class ParticleFlame extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float s = ((float) this.age + partialTick) / (float) this.lifetime;
         this.size = this.oSize * (1.0F - s * s * 0.5F);
         super.render(t, partialTick);
@@ -46,9 +46,7 @@ public class ParticleFlame extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFluidDrip.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFluidDrip.java
index cb2fcd017..1a8f9e816 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFluidDrip.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFluidDrip.java
@@ -2,9 +2,8 @@ package net.minecraft.client.render.particle;
 
 import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.ParticleEngine;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
-import net.minecraft.core.Global;
 import net.minecraft.core.enums.LightLayer;
 import net.minecraft.core.util.helper.Color;
 import net.minecraft.core.util.helper.MathHelper;
@@ -33,16 +32,9 @@ public class ParticleFluidDrip extends Particle {
         this.bCol = Color.blueFromInt(color) / 255f;
     }
 
-    @Override
-    public int getParticleTexture() {
-        return ParticleEngine.TERRAIN_TEXTURE;
-    }
-
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
@@ -67,15 +59,10 @@ public class ParticleFluidDrip extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         if (this.tex == null) return;
-        float br = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            t.setLightmapCoord(getLightmap(partialTick));
-        } else if (!Global.accessor.isFullbrightEnabled()) {
-            br = getBrightness(partialTick);
-        }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+        t.setLightmapCoord1i(getLightmap(partialTick));
+        t.setColorOpaque3f(this.rCol, this.gCol, this.bCol);
         t.addParticle(
             MathHelper.lerp(this.xo, this.x, partialTick),
             MathHelper.lerp(this.yo, this.y, partialTick),
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFootstep.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFootstep.java
index e8dced1a6..f37a469dc 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFootstep.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleFootstep.java
@@ -1,13 +1,14 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.ParticleEngine;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 public class ParticleFootstep extends Particle {
     private int life;
@@ -23,15 +24,15 @@ public class ParticleFootstep extends Particle {
     }
 
     @Override
-    public void renderLit(@NotNull Tessellator t, float partialTick, double xOff, double yOff, double zOff) {
-        float time = (life + partialTick) / lifeTime;
+    public void renderLit(@NotNull TessellatorGeneral t, float partialTick, double xOff, double yOff, double zOff) {
+        float time = (this.life + partialTick) / this.lifeTime;
         time *= time;
         float a = 2.0F - time * 2.0F;
         if (a > 1.0F) {
             a = 1.0F;
         }
         a *= 0.2F;
-        GL11.glDisable(GL11.GL_LIGHTING);
+        GLRenderer.globalSetLightEnabled(false);
         float s = 0.125F;
         float x = (float) (this.x - xOff);
         float y = (float) (this.y - yOff);
@@ -39,24 +40,22 @@ public class ParticleFootstep extends Particle {
         float br = this.world.getLightBrightness(MathHelper.floor(this.x), MathHelper.floor(this.y), MathHelper.floor(this.z));
         this.textureManager.bindTexture(this.textureManager.loadTexture("/assets/minecraft/textures/misc/footprint.png"));
 
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         t.startDrawingQuads();
-        t.setColorRGBA_F(br, br, br, a);
+        t.setColor4f(br, br, br, a);
         t.addVertexWithUV(x - s, y, z + s, 0.0D, 1.0D);
         t.addVertexWithUV(x + s, y, z + s, 1.0D, 1.0D);
         t.addVertexWithUV(x + s, y, z - s, 1.0D, 0.0D);
         t.addVertexWithUV(x - s, y, z - s, 0.0D, 0.0D);
         t.draw();
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glEnable(GL11.GL_LIGHTING);
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.globalSetLightEnabled(true);
     }
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.life++;
         if (this.life == this.lifeTime) {
             this.remove();
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleHeart.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleHeart.java
index bd8b76ffd..eb7478e3d 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleHeart.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleHeart.java
@@ -1,7 +1,6 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
@@ -28,7 +27,7 @@ public class ParticleHeart extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float l = ((this.age + partialTick) / this.lifetime) * 32F;
         if (l < 0.0F) {
             l = 0.0F;
@@ -42,9 +41,7 @@ public class ParticleHeart extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleItemBreaking.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleItemBreaking.java
index 9ed67d757..e7bdc13e4 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleItemBreaking.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleItemBreaking.java
@@ -1,10 +1,8 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.ParticleEngine;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
-import net.minecraft.core.Global;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.item.Item;
 import net.minecraft.core.util.helper.MathHelper;
@@ -21,20 +19,10 @@ public class ParticleItemBreaking extends Particle {
     }
 
     @Override
-    public int getParticleTexture() {
-        return ParticleEngine.ITEM_TEXTURE;
-    }
-
-    @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
-        if (tex == null) return;
-        float br = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            t.setLightmapCoord(getLightmap(partialTick));
-        } else if (!Global.accessor.isFullbrightEnabled()) {
-            br = getBrightness(partialTick);
-        }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
+        if (this.tex == null) return;
+        t.setLightmapCoord1i(getLightmap(partialTick));
+        t.setColorOpaque3f(this.rCol, this.gCol, this.bCol);
         t.addParticle(MathHelper.lerp(this.xo, this.x, partialTick),
             MathHelper.lerp(this.yo, this.y, partialTick),
             MathHelper.lerp(this.zo, this.z, partialTick), this.size * 0.1f,
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleLava.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleLava.java
index 07253c603..b8aff2cfe 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleLava.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleLava.java
@@ -1,7 +1,6 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
@@ -29,7 +28,7 @@ public class ParticleLava extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float l = (this.age + partialTick) / this.lifetime;
         this.size = this.oSize * (1.0F - l * l);
         super.render(t, partialTick);
@@ -37,9 +36,7 @@ public class ParticleLava extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleLeaf.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleLeaf.java
index f67c6bfb3..5f8b6b132 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleLeaf.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleLeaf.java
@@ -1,11 +1,9 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.ParticleEngine;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.core.Global;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.BlockLogicLeavesBase;
 import net.minecraft.core.block.Blocks;
@@ -26,7 +24,6 @@ public class ParticleLeaf extends Particle {
         this.zd = 0.0f;
     }
 
-    // TODO readd programatic collisions
     @Override
     public boolean collidesWithBlock(@NotNull Block<?> block, int data) {
         return !Block.hasLogicClass(block, BlockLogicLeavesBase.class);
@@ -44,9 +41,7 @@ public class ParticleLeaf extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         float windDirection = this.world.worldType.getWindManager().getWindDirection(this.world, (float) this.x, (float) this.y, (float) this.z);
         float windIntensity = this.world.worldType.getWindManager().getWindIntensity(this.world, (float) this.x, (float) this.y, (float) this.z) * 0.01f;
 
@@ -71,20 +66,10 @@ public class ParticleLeaf extends Particle {
     }
 
     @Override
-    public int getParticleTexture() {
-        return ParticleEngine.TERRAIN_TEXTURE;
-    }
-
-    @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         if (this.tex == null) return;
-        float br = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            t.setLightmapCoord(getLightmap(partialTick));
-        } else if (!Global.accessor.isFullbrightEnabled()) {
-            br = getBrightness(partialTick);
-        }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+        t.setLightmapCoord1i(getLightmap(partialTick));
+        t.setColorOpaque3f(this.rCol, this.gCol, this.bCol);
         t.addParticle(
             MathHelper.lerp(this.xo, this.x, partialTick),
             MathHelper.lerp(this.yo, this.y, partialTick),
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleNote.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleNote.java
index 20bc1f4ac..dec30e89f 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleNote.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleNote.java
@@ -1,8 +1,7 @@
 package net.minecraft.client.render.particle;
 
 
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
@@ -33,7 +32,7 @@ public class ParticleNote extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float l = ((this.age + partialTick) / this.lifetime) * 32F;
         if (l < 0.0F) {
             l = 0.0F;
@@ -47,9 +46,7 @@ public class ParticleNote extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePickupAnimation.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePickupAnimation.java
index ab701af53..b2aa91c2f 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePickupAnimation.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePickupAnimation.java
@@ -1,14 +1,13 @@
 package net.minecraft.client.render.particle;
 
 import net.minecraft.client.render.ParticleEngine;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.entity.Entity;
-import net.minecraft.client.render.EntityRenderDispatcher;
-import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import net.minecraft.core.world.World;
 import net.minecraft.core.world.pos.TilePos;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
 
 public class ParticlePickupAnimation extends Particle {
     private final Entity item;
@@ -27,7 +26,7 @@ public class ParticlePickupAnimation extends Particle {
     }
 
     @Override
-    public void renderLit(@NotNull Tessellator t, float partialTick, double xOff, double yOff, double zOff) {
+    public void renderLit(@NotNull TessellatorGeneral t, float partialTick, double xOff, double yOff, double zOff) {
         float time = (this.life + partialTick) / this.lifeTime;
         time *= time;
         double xo = this.item.x;
@@ -43,21 +42,14 @@ public class ParticlePickupAnimation extends Particle {
         xx -= xOff;
         yy -= yOff;
         zz -= zOff;
-        float br = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            LightmapHelper.setLightmapCoord(this.item.world.getLightmapCoord(tilePos, 0));
-        } else {
-            br = this.world.getLightBrightness(tilePos);
-        }
-        GL11.glColor4f(br, br, br, 1.0F);
-        EntityRenderDispatcher.instance.renderEntityWithPosYaw(t, this.item, (float) xx, (float) yy, (float) zz, this.item.yRot, partialTick);
+        GLRenderer.setLightmapCoord1i(this.item.world.getLightmapCoord(tilePos, 0));
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+        EntityRendererDispatcher.instance.renderEntityWithPosYaw(t, this.item, (float) xx, (float) yy, (float) zz, this.item.yRot, partialTick);
     }
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.life++;
         if (this.life == this.lifeTime) {
             remove();
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePortal.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePortal.java
index 6f64641d6..6019c3626 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePortal.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePortal.java
@@ -1,7 +1,6 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.util.helper.Colors;
 import net.minecraft.core.util.helper.Color;
@@ -35,7 +34,7 @@ public class ParticlePortal extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float s = (this.age + partialTick) / this.lifetime;
         s = 1.0F - s;
         s *= s;
@@ -55,9 +54,7 @@ public class ParticlePortal extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePuffRGB.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePuffRGB.java
index 8a5c67f02..41d456651 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePuffRGB.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticlePuffRGB.java
@@ -1,7 +1,7 @@
 package net.minecraft.client.render.particle;
 
 import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.enums.LightLayer;
 import net.minecraft.core.util.helper.MathHelper;
@@ -38,7 +38,7 @@ public class ParticlePuffRGB extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float l = ((this.age + partialTick) / this.lifetime) * 32F;
         if (l < 0.0F) {
             l = 0.0F;
@@ -48,22 +48,17 @@ public class ParticlePuffRGB extends Particle {
         }
         this.size = this.oSize * l;
         if (this.tex == null) return;
-        float br = 1f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            int xTile = MathHelper.floor(this.x);
-            int yTile = MathHelper.floor(this.y);
-            int zTile = MathHelper.floor(this.z);
-            int lmc;
-            if (this.brightness >= 0) {
-                lmc = LightmapHelper.getLightmapCoord(this.world.getSavedLightValue(LightLayer.Sky, xTile, yTile, zTile), Math.max(this.world.getSavedLightValue(LightLayer.Block, xTile, yTile, zTile), this.brightness));
-            } else {
-                lmc = getLightmap(partialTick);
-            }
-            t.setLightmapCoord(lmc);
+        int xTile = MathHelper.floor(this.x);
+        int yTile = MathHelper.floor(this.y);
+        int zTile = MathHelper.floor(this.z);
+        int lmc;
+        if (this.brightness >= 0) {
+            lmc = LightmapHelper.getLightmapCoord(this.world.getSavedLightValue(LightLayer.Sky, xTile, yTile, zTile), Math.max(this.world.getSavedLightValue(LightLayer.Block, xTile, yTile, zTile), this.brightness));
         } else {
-            br = Math.max(getBrightness(partialTick), this.brightness / 15f);
+            lmc = getLightmap(partialTick);
         }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+        t.setLightmapCoord1i(lmc);
+        t.setColorOpaque3f(this.rCol, this.gCol, this.bCol);
         t.addParticle(
             MathHelper.lerp(this.xo, this.x, partialTick),
             MathHelper.lerp(this.yo, this.y, partialTick),
@@ -73,9 +68,7 @@ public class ParticlePuffRGB extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleRedstoneDust.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleRedstoneDust.java
index 0760ffecd..97c8ee12e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleRedstoneDust.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleRedstoneDust.java
@@ -1,7 +1,7 @@
 package net.minecraft.client.render.particle;
 
 import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.util.helper.Colors;
 import net.minecraft.core.enums.LightLayer;
@@ -46,7 +46,7 @@ public class ParticleRedstoneDust extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         if (this.tex == null) return;
         float l = ((this.age + partialTick) / this.lifetime) * 32F;
         if (l < 0.0F) {
@@ -56,22 +56,17 @@ public class ParticleRedstoneDust extends Particle {
             l = 1.0F;
         }
         this.size = this.oSize * l;
-        float br = 1f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            int xTile = MathHelper.floor(this.x);
-            int yTile = MathHelper.floor(this.y);
-            int zTile = MathHelper.floor(this.z);
-            int lmc;
-            if (this.brightness >= 0) {
-                lmc = LightmapHelper.getLightmapCoord(this.world.getSavedLightValue(LightLayer.Sky, xTile, yTile, zTile), Math.max(this.world.getSavedLightValue(LightLayer.Block, xTile, yTile, zTile), this.brightness));
-            } else {
-                lmc = getLightmap(partialTick);
-            }
-            t.setLightmapCoord(lmc);
+        int xTile = MathHelper.floor(this.x);
+        int yTile = MathHelper.floor(this.y);
+        int zTile = MathHelper.floor(this.z);
+        int lmc;
+        if (this.brightness >= 0) {
+            lmc = LightmapHelper.getLightmapCoord(this.world.getSavedLightValue(LightLayer.Sky, xTile, yTile, zTile), Math.max(this.world.getSavedLightValue(LightLayer.Block, xTile, yTile, zTile), this.brightness));
         } else {
-            br = Math.max(getBrightness(partialTick), this.brightness / 15f);
+            lmc = getLightmap(partialTick);
         }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+        t.setLightmapCoord1i(lmc);
+        t.setColorOpaque3f(this.rCol, this.gCol, this.bCol);
         t.addParticle(
             MathHelper.lerp(this.xo, this.x, partialTick),
             MathHelper.lerp(this.yo, this.y, partialTick),
@@ -83,9 +78,7 @@ public class ParticleRedstoneDust extends Particle {
 
     @Override
     public void tick() {
-        if (LightmapHelper.isLightmapEnabled()) {
-            this.cachedLightmapCoord = calcLightmap(1f);
-        }
+        this.cachedLightmapCoord = calcLightmap(1f);
         this.xo = this.x;
         this.yo = this.y;
         this.zo = this.z;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSlimeChunk.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSlimeChunk.java
index 6d93410e7..edc08c51d 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSlimeChunk.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSlimeChunk.java
@@ -1,10 +1,8 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.ParticleEngine;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
-import net.minecraft.core.Global;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.core.item.Item;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
@@ -21,20 +19,11 @@ public class ParticleSlimeChunk extends Particle {
     }
 
     @Override
-    public int getParticleTexture() {
-        return ParticleEngine.ITEM_TEXTURE;
-    }
-
-    @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         if (this.tex == null) return;
         float br = 1.0f;
-        if (LightmapHelper.isLightmapEnabled()) {
-            t.setLightmapCoord(getLightmap(partialTick));
-        } else if (!Global.accessor.isFullbrightEnabled()) {
-            br = getBrightness(partialTick);
-        }
-        t.setColorOpaque_F(this.rCol * br, this.gCol * br, this.bCol * br);
+        t.setLightmapCoord1i(getLightmap(partialTick));
+        t.setColorOpaque3f(this.rCol * br, this.gCol * br, this.bCol * br);
         t.addParticle(MathHelper.lerp(this.xo, this.x, partialTick),
             MathHelper.lerp(this.yo, this.y, partialTick),
             MathHelper.lerp(this.zo, this.z, partialTick),
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSmoke.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSmoke.java
index fab34eb00..1c15b7412 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSmoke.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSmoke.java
@@ -1,6 +1,6 @@
 package net.minecraft.client.render.particle;
 
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
@@ -30,7 +30,7 @@ public class ParticleSmoke extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float l = ((this.age + partialTick) / this.lifetime) * 32F;
         if (l < 0.0F) {
             l = 0.0F;
diff --git a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSnowShovel.java b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSnowShovel.java
index ecfb347a6..e89fe76f4 100644
--- a/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSnowShovel.java
+++ b/game/client/src/main/java/net/minecraft/client/render/particle/ParticleSnowShovel.java
@@ -1,7 +1,7 @@
 package net.minecraft.client.render.particle;
 
 
-import net.minecraft.client.render.tessellator.ParticleTessellator;
+import net.minecraft.client.render.tessellator.TessellatorParticle;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
@@ -31,7 +31,7 @@ public class ParticleSnowShovel extends Particle {
     }
 
     @Override
-    public void render(@NotNull ParticleTessellator t, float partialTick) {
+    public void render(@NotNull TessellatorParticle t, float partialTick) {
         float l = ((this.age + partialTick) / this.lifetime) * 32F;
         if(l < 0.0F) {
             l = 0.0F;
diff --git a/game/client/src/main/java/net/minecraft/client/render/renderer/BlendFactor.java b/game/client/src/main/java/net/minecraft/client/render/renderer/BlendFactor.java
new file mode 100644
index 000000000..09a04cc3c
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/renderer/BlendFactor.java
@@ -0,0 +1,31 @@
+package net.minecraft.client.render.renderer;
+
+import org.lwjgl.opengl.GL41;
+
+public enum BlendFactor {
+    ONE(GL41.GL_ONE),
+    ZERO(GL41.GL_ZERO),
+    SRC_COLOR(GL41.GL_SRC_COLOR),
+    ONE_MINUS_SRC_COLOR(GL41.GL_ONE_MINUS_SRC_COLOR),
+    DST_COLOR(GL41.GL_DST_COLOR),
+    ONE_MINUS_DST_COLOR(GL41.GL_ONE_MINUS_DST_COLOR),
+    SRC_ALPHA(GL41.GL_SRC_ALPHA),
+    ONE_MINUS_SRC_ALPHA(GL41.GL_ONE_MINUS_SRC_ALPHA),
+    DST_ALPHA(GL41.GL_DST_ALPHA),
+    ONE_MINUS_DST_ALPHA(GL41.GL_ONE_MINUS_DST_ALPHA),
+    CONSTANT_COLOR(GL41.GL_CONSTANT_COLOR),
+    ONE_MINUS_CONSTANT_COLOR(GL41.GL_ONE_MINUS_CONSTANT_COLOR),
+    CONSTANT_ALPHA(GL41.GL_CONSTANT_ALPHA),
+    ONE_MINUS_CONSTANT_ALPHA(GL41.GL_ONE_MINUS_CONSTANT_ALPHA),
+    SRC_ALPHA_SATURATE(GL41.GL_SRC_ALPHA_SATURATE),
+    SRC1_COLOR(GL41.GL_SRC1_COLOR),
+    ONE_MINUS_SRC1_COLOR(GL41.GL_ONE_MINUS_SRC1_COLOR),
+    SRC1_ALPHA(GL41.GL_SRC1_ALPHA),
+    ONE_MINUS_SRC1_ALPHA(GL41.GL_ONE_MINUS_SRC1_ALPHA);;
+
+    public final int cap;
+
+    BlendFactor(int cap) {
+        this.cap = cap;
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/renderer/CompareFunc.java b/game/client/src/main/java/net/minecraft/client/render/renderer/CompareFunc.java
new file mode 100644
index 000000000..2f8db596c
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/renderer/CompareFunc.java
@@ -0,0 +1,19 @@
+package net.minecraft.client.render.renderer;
+
+import org.lwjgl.opengl.GL41;
+
+public enum CompareFunc {
+    NEVER(GL41.GL_NEVER),
+    LESS(GL41.GL_LESS),
+    EQUAL(GL41.GL_EQUAL),
+    LESS_EQUAL(GL41.GL_LEQUAL),
+    GREATER(GL41.GL_GREATER),
+    NOT_EQUAL(GL41.GL_NOTEQUAL),
+    GREATER_EQUAL(GL41.GL_GEQUAL),
+    ALWAYS(GL41.GL_ALWAYS);
+    public final int cap;
+
+    CompareFunc(int cap) {
+        this.cap = cap;
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/renderer/CullFace.java b/game/client/src/main/java/net/minecraft/client/render/renderer/CullFace.java
new file mode 100644
index 000000000..ab95e5c4c
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/renderer/CullFace.java
@@ -0,0 +1,15 @@
+package net.minecraft.client.render.renderer;
+
+import org.lwjgl.opengl.GL41;
+
+public enum CullFace {
+    FRONT(GL41.GL_FRONT),
+    BACK(GL41.GL_BACK),
+    FRONT_AND_BACK(GL41.GL_FRONT_AND_BACK);
+
+    public final int cap;
+
+    CullFace(int cap) {
+        this.cap = cap;
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/renderer/DrawMode.java b/game/client/src/main/java/net/minecraft/client/render/renderer/DrawMode.java
new file mode 100644
index 000000000..2e4312c7d
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/renderer/DrawMode.java
@@ -0,0 +1,27 @@
+package net.minecraft.client.render.renderer;
+
+import org.lwjgl.opengl.GL41;
+
+public enum DrawMode {
+    POINTS(GL41.GL_POINTS),
+    LINE_STRIP(GL41.GL_LINE_STRIP),
+    LINE_LOOP(GL41.GL_LINE_LOOP),
+    LINES(GL41.GL_LINES),
+    LINE_STRIP_ADJACENCY(GL41.GL_LINE_STRIP_ADJACENCY),
+    LINES_ADJACENCY(GL41.GL_LINES_ADJACENCY),
+    TRIANGLE_STRIP(GL41.GL_TRIANGLE_STRIP),
+    TRIANGLE_FAN(GL41.GL_TRIANGLE_FAN),
+    TRIANGLES(GL41.GL_TRIANGLES),
+    TRIANGLE_STRIP_ADJACENCY(GL41.GL_TRIANGLE_STRIP_ADJACENCY),
+    TRIANGLES_ADJACENCY(GL41.GL_TRIANGLES_ADJACENCY),
+    PATCHES(GL41.GL_PATCHES),
+    @Deprecated QUAD_STRIP(GL41.GL_QUAD_STRIP),
+    @Deprecated QUADS(GL41.GL_QUADS),
+    @Deprecated POLYGON(GL41.GL_POLYGON)
+    ;
+
+    public final int cap;
+    DrawMode(int cap) {
+        this.cap = cap;
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/renderer/FrontFace.java b/game/client/src/main/java/net/minecraft/client/render/renderer/FrontFace.java
new file mode 100644
index 000000000..16c6c2c28
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/renderer/FrontFace.java
@@ -0,0 +1,13 @@
+package net.minecraft.client.render.renderer;
+
+import org.lwjgl.opengl.GL41;
+
+public enum FrontFace {
+    CW(GL41.GL_CW),
+    CCW(GL41.GL_CCW)
+    ;
+    public final int cap;
+    FrontFace(int cap) {
+        this.cap = cap;
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/renderer/GLRenderer.java b/game/client/src/main/java/net/minecraft/client/render/renderer/GLRenderer.java
new file mode 100644
index 000000000..cec7baa36
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/renderer/GLRenderer.java
@@ -0,0 +1,507 @@
+package net.minecraft.client.render.renderer;
+
+import com.mojang.logging.LogUtils;
+import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.FogManager;
+import net.minecraft.client.render.Lighting;
+import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.shader.Shader;
+import net.minecraft.client.render.tessellator.RenderBuffer;
+import net.minecraft.client.render.tessellator.TessellatorShader;
+import net.minecraft.core.util.helper.Color;
+import org.jetbrains.annotations.NotNull;
+import org.joml.Matrix4f;
+import org.joml.Matrix4fStack;
+import org.joml.Vector3dc;
+import org.joml.Vector3fc;
+import org.joml.Vector4dc;
+import org.joml.Vector4f;
+import org.joml.Vector4fc;
+import org.lwjgl.BufferUtils;
+import org.lwjgl.opengl.GL41;
+import org.slf4j.Logger;
+
+import java.nio.FloatBuffer;
+
+public class GLRenderer {
+    private static final Logger LOGGER = LogUtils.getLogger();
+    public static boolean DEBUG = false;
+    public static final int RENDER_FRAMES_STACK_SIZE = 64; // GL guaranteed stack size was 32, so 64 should be more than plenty :)
+
+    private static final @NotNull GLRenderer instance = new GLRenderer();
+
+    // Global configuration
+    private static boolean LIGHT_ENABLED = false;
+    private static final @NotNull Vector4f LIGHT_MODEL_AMBIENT = new Vector4f(0.2f, 0.2f, 0.2f, 1.0f);
+    private static final @NotNull Lighting.LightSource LIGHT_0 = new Lighting.LightSource();
+    private static final @NotNull Lighting.LightSource LIGHT_1 = new Lighting.LightSource();
+    static {
+        LIGHT_0.diffuse.set(1, 1, 1, 1);
+        LIGHT_0.specular.set(1, 1, 1, 1);
+    }
+    private static final @NotNull Matrix4f NORMAL_TRANSFORM_MATRIX = new Matrix4f().identity();
+
+    public static void globalSetLightEnabled(boolean flag) {
+        LIGHT_ENABLED = flag;
+    }
+
+    public static @NotNull Vector4f globalGetLightModelAmbient() {
+        return LIGHT_MODEL_AMBIENT;
+    }
+
+    public static @NotNull Lighting.LightSource globalGetLight0() {
+        return LIGHT_0;
+    }
+
+    public static @NotNull Lighting.LightSource globalGetLight1() {
+        return LIGHT_1;
+    }
+
+    public static @NotNull Matrix4f globalGetNormalTransformMatrix() {
+        return NORMAL_TRANSFORM_MATRIX;
+    }
+
+    // Debug Stack Config
+    private static final StackWalker STACK_WALKER = StackWalker.getInstance(StackWalker.Option.RETAIN_CLASS_REFERENCE);
+    private final StackTraceElement[] pushListenStack = new StackTraceElement[RENDER_FRAMES_STACK_SIZE];
+    private final StackTraceElement[] popListenStack = new StackTraceElement[RENDER_FRAMES_STACK_SIZE];
+
+    // Stacked configuration
+    private final @NotNull Matrix4fStack projectionMatrixStack = new Matrix4fStack(RENDER_FRAMES_STACK_SIZE);
+    private final @NotNull Matrix4fStack viewMatrixStack = new Matrix4fStack(RENDER_FRAMES_STACK_SIZE);
+    private final @NotNull Matrix4fStack modelMatrixStack = new Matrix4fStack(RENDER_FRAMES_STACK_SIZE);
+
+    private final long[] stateConfigStack = new long[RENDER_FRAMES_STACK_SIZE];
+    private long currentStateConfig = State.DITHER.bitMask | State.MULTISAMPLE.bitMask; // Spec says these two are default on https://docs.gl/gl4/glEnable
+
+    private final int[] colorStack = new int[RENDER_FRAMES_STACK_SIZE];
+    private int currentColor = Color.intToIntARGB(255, 255, 255, 255);
+
+    private final Shader[] shaderStack = new Shader[RENDER_FRAMES_STACK_SIZE];
+    private @NotNull Shader currentShader = Shaders.INTERFACE;
+
+    private final FogManager.FogState[] fogStateStack = new FogManager.FogState[RENDER_FRAMES_STACK_SIZE];
+    private @NotNull FogManager.FogState currentFogState = new FogManager.FogState().disable();
+
+    private final CompareFunc[] depthFuncStack = new CompareFunc[RENDER_FRAMES_STACK_SIZE];
+    private @NotNull CompareFunc currentDepthFunc = CompareFunc.LESS;
+
+    private final CullFace[] cullFaceStack = new CullFace[RENDER_FRAMES_STACK_SIZE];
+    private @NotNull CullFace currentCullFace = CullFace.BACK;
+
+    private final BlendFactor[] sFactorStack = new BlendFactor[RENDER_FRAMES_STACK_SIZE];
+    private final BlendFactor[] dFactorStack = new BlendFactor[RENDER_FRAMES_STACK_SIZE];
+    private @NotNull BlendFactor currentSFactor = BlendFactor.ONE;
+    private @NotNull BlendFactor currentDFactor = BlendFactor.ZERO;
+
+    private final FrontFace[] frontFaceStack = new FrontFace[RENDER_FRAMES_STACK_SIZE];
+    private @NotNull FrontFace currentFrontFace = FrontFace.CCW;
+
+    private final byte[] colorMaskStack = new byte[RENDER_FRAMES_STACK_SIZE];
+    private byte currentColorMask = 0b1111; // RGBA
+
+    private final boolean[] depthMaskStack = new boolean[RENDER_FRAMES_STACK_SIZE];
+    private boolean currentDepthMask = true;
+
+    private final float[] lineWidthStack = new float[RENDER_FRAMES_STACK_SIZE];
+    private float currentLineWidth = 1f;
+
+    private final float[] polygonFactorStack = new float[RENDER_FRAMES_STACK_SIZE];
+    private final float[] polygonUnitsStack = new float[RENDER_FRAMES_STACK_SIZE];
+    private float currentPolygonFactor = 0f;
+    private float currentPolygonUnits = 0f;
+
+    private final float[] lightmapBlockStack = new float[RENDER_FRAMES_STACK_SIZE];
+    private final float[] lightmapSkyStack = new float[RENDER_FRAMES_STACK_SIZE];
+    private float currentLightmapBlock = 15.5f/16f;
+    private float currentLightmapSky = 15.5f/16f;
+
+    private int stackIndex = 0;
+
+
+    private final @NotNull Minecraft mc = Minecraft.getMinecraft();
+    private final FloatBuffer mat4fBuf = BufferUtils.createFloatBuffer(16);
+    private final @NotNull TessellatorShader tessellatorShader = new TessellatorShader("GLRender Tessellator", 0x200000);
+
+    public GLRenderer() {
+    }
+
+    public static void init() {
+    }
+
+    private static final FloatBuffer lightBuf = BufferUtils.createFloatBuffer(8);
+    private static final Matrix4f matBuf = new Matrix4f();
+    public static void globalSetUniforms(@NotNull Shader shader) {
+        shader.bind();
+        GL41.glUniformMatrix4fv(shader.getUniform("projection"), false, projectionM4f().get(instance.mat4fBuf));
+        GL41.glUniformMatrix4fv(shader.getUniform("projectionInv"), false, projectionM4f().invert(matBuf).get(instance.mat4fBuf));
+        GL41.glUniformMatrix4fv(shader.getUniform("view"), false, viewM4f().get(instance.mat4fBuf));
+        GL41.glUniformMatrix4fv(shader.getUniform("viewInv"), false, viewM4f().invert(matBuf).get(instance.mat4fBuf));
+        GL41.glUniformMatrix4fv(shader.getUniform("model"), false, modelM4f().get(instance.mat4fBuf));
+
+        GL41.glUniform4f(shader.getUniform("ucolor"), Color.redFromInt(instance.currentColor)/255f, Color.greenFromInt(instance.currentColor)/255f, Color.blueFromInt(instance.currentColor)/255f, Color.alphaFromInt(instance.currentColor)/255f);
+        GL41.glUniform1i(shader.getUniform("uticks"), instance.mc.ticksRan);
+        GL41.glUniform1f(shader.getUniform("upartialTick"), instance.mc.timer.partialTicks);
+
+        GL41.glUniform1f(shader.getUniform("uLineWidth"), instance.currentLineWidth);
+
+        double renderScale = (float) instance.mc.gameSettings.renderScale.value.scale;
+        int scaledWidth = (int) (renderScale * instance.mc.gameWindow.getWidthPixels());
+        int scaledHeight = (int) (renderScale * instance.mc.gameWindow.getHeightPixels());
+
+        GL41.glUniform1f(shader.getUniform("viewWidth"), scaledWidth);
+        GL41.glUniform1f(shader.getUniform("viewHeight"), scaledHeight);
+
+        GL41.glUniform1i(shader.getUniform("texture0"), 0);
+        GL41.glUniform1i(shader.getUniform("texture1"), 1);
+
+        GL41.glUniform4f(shader.getUniform("ufogColor"), instance.currentFogState.fogColor.x, instance.currentFogState.fogColor.y, instance.currentFogState.fogColor.z, instance.currentFogState.fogColor.w);
+        GL41.glUniform1i(shader.getUniform("ufogMode"), instance.currentFogState.fogMode.ordinal());
+        GL41.glUniform1f(shader.getUniform("ufogStart"), instance.currentFogState.fogStart);
+        GL41.glUniform1f(shader.getUniform("ufogEnd"), instance.currentFogState.fogEnd);
+        GL41.glUniform1f(shader.getUniform("ufogDensity"), instance.currentFogState.fogDensity);
+
+        GL41.glUniformMatrix4fv(shader.getUniform("normalTransform"), false, NORMAL_TRANSFORM_MATRIX.get(instance.mat4fBuf));
+        if (LIGHT_ENABLED) {
+            GL41.glUniform4f(shader.getUniform("lightModelAmbient"), LIGHT_MODEL_AMBIENT.x(), LIGHT_MODEL_AMBIENT.y(), LIGHT_MODEL_AMBIENT.z(), LIGHT_MODEL_AMBIENT.w());
+            LIGHT_0.position.get(lightBuf);
+            LIGHT_1.position.get(lightBuf.position(4));
+            GL41.glUniform4fv(shader.getUniform("lightSourcePosition"), lightBuf.position(8).flip());
+            LIGHT_0.diffuse.get(lightBuf);
+            LIGHT_1.diffuse.get(lightBuf.position(4));
+            GL41.glUniform4fv(shader.getUniform("lightSourceDiffuse"), lightBuf.position(8).flip());
+        } else {
+            GL41.glUniform4f(shader.getUniform("lightModelAmbient"), 1f, 1f, 1f, 1f);
+            LIGHT_0.position.get(lightBuf);
+            LIGHT_1.position.get(lightBuf.position(4));
+            GL41.glUniform4fv(shader.getUniform("lightSourcePosition"), lightBuf.position(8).flip());
+            lightBuf.put(0f).put(0f).put(0f).put(0f);
+            lightBuf.put(0f).put(0f).put(0f).put(0f);
+            GL41.glUniform4fv(shader.getUniform("lightSourceDiffuse"), lightBuf.position(8).flip());
+        }
+    }
+
+    public static void render(@NotNull RenderBuffer renderBuffer) {
+        render(renderBuffer.vao(), renderBuffer.vbo(), renderBuffer.offset(), renderBuffer.count(), renderBuffer.drawMode());
+    }
+
+    public static void render(int vao, int vbo, int offset, int count, @NotNull DrawMode drawMode) {
+        GL41.glBindVertexArray(vao);
+        GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, vbo);
+        instance.currentShader.bind();
+
+        globalSetUniforms(instance.currentShader);
+
+        GL41.glDrawArrays(drawMode.cap, offset, count);
+
+        GL41.glUseProgram(0);
+        GL41.glBindVertexArray(0);
+    }
+
+    public static void enableState(@NotNull State state) {
+        instance.currentStateConfig |= state.bitMask;
+        GL41.glEnable(state.cap);
+    }
+
+    public static void disableState(@NotNull State state) {
+        instance.currentStateConfig &= ~state.bitMask;
+        GL41.glDisable(state.cap);
+    }
+
+    public static boolean isStateEnabled(@NotNull State state) {
+        return state.isEnabled(instance.currentStateConfig);
+    }
+
+    public static @NotNull Matrix4f projectionM4f() {
+        return instance.projectionMatrixStack;
+    }
+
+    public static @NotNull Matrix4f viewM4f() {
+        return instance.viewMatrixStack;
+    }
+
+    public static @NotNull Matrix4f modelM4f() {
+        return instance.modelMatrixStack;
+    }
+
+    public static void setShader(@NotNull Shader shader) {
+        instance.currentShader = shader;
+    }
+
+    public static @NotNull Shader getShader() {
+        return instance.currentShader;
+    }
+
+    public static @NotNull FogManager.FogState getFogState() {
+        return instance.currentFogState;
+    }
+
+    public static void setDepthFunc(@NotNull CompareFunc func) {
+        instance.currentDepthFunc = func;
+        GL41.glDepthFunc(func.cap);
+    }
+
+    public static @NotNull CompareFunc getDepthFunc() {
+        return instance.currentDepthFunc;
+    }
+
+    public static void setCullFace(@NotNull CullFace cullFace) {
+        instance.currentCullFace = cullFace;
+        GL41.glCullFace(cullFace.cap);
+    }
+
+    public static void setBlendFunc(@NotNull BlendFactor srcFactor, @NotNull BlendFactor destFactor) {
+        instance.currentSFactor = srcFactor;
+        instance.currentDFactor = destFactor;
+        GL41.glBlendFunc(srcFactor.cap, destFactor.cap);
+    }
+
+    public static @NotNull BlendFactor getBlendSFactor() {
+        return instance.currentSFactor;
+    }
+
+    public static @NotNull BlendFactor getBlendDFactor() {
+        return instance.currentDFactor;
+    }
+
+    public static void setFrontFace(@NotNull FrontFace frontFace) {
+        instance.currentFrontFace = frontFace;
+        GL41.glFrontFace(frontFace.cap);
+    }
+
+    public static @NotNull FrontFace getFrontFace() {
+        return instance.currentFrontFace;
+    }
+
+    public static void setLineWidth(float lineWidth) {
+        instance.currentLineWidth = lineWidth;
+    }
+
+    public static float getLineWidth() {
+        return instance.currentLineWidth;
+    }
+
+    public static void setColorMask(boolean red, boolean green, boolean blue, boolean alpha) {
+        instance.currentColorMask = (byte) ((red ? 0b1000 : 0) | (green ? 0b0100 : 0) | (blue ? 0b0010 : 0) | (alpha ? 0b0001 : 0));
+        GL41.glColorMask(red, green, blue, alpha);
+    }
+
+    public static byte getColorMask() {
+        return instance.currentColorMask;
+    }
+
+    public static void setDepthMask(boolean flag) {
+        instance.currentDepthMask = flag;
+        GL41.glDepthMask(flag);
+    }
+
+    public static boolean getDepthMask() {
+        return instance.currentDepthMask;
+    }
+
+    public static void setPolygonOffset(float factor, float units) {
+        instance.currentPolygonFactor = factor;
+        instance.currentPolygonUnits = units;
+        GL41.glPolygonOffset(factor, units);
+    }
+
+    public static float getPolygonFactor() {
+        return instance.currentPolygonFactor;
+    }
+
+    public static float getPolygonUnits() {
+        return instance.currentPolygonUnits;
+    }
+
+    public static void setLightmapCoord1i(int lightmapCoord) {
+        setLightmapCoord2i(LightmapHelper.getBlockLightFromCoord(lightmapCoord), LightmapHelper.getSkyLightFromCoord(lightmapCoord));
+    }
+
+    public static void setLightmapCoord2i(int blockLight, int skyLight) {
+        setLightmapCoord2f((blockLight + 0.5f) / 16f, (skyLight + 0.5f) / 16f);
+    }
+
+    public static void setLightmapCoord2f(float blockLight, float skyLight) {
+        instance.currentLightmapBlock = blockLight;
+        instance.currentLightmapSky = skyLight;
+    }
+
+    public static float getLightmapBlock() {
+        return instance.currentLightmapBlock;
+    }
+
+    public static float getLightmapSky() {
+        return instance.currentLightmapSky;
+    }
+
+    public static void setColor1i(int argb) {
+        instance.currentColor = argb;
+    }
+
+    public static void setColor4f(float r, float g, float b, float a) {
+        setColor1i(Color.floatToIntARGB(a, r, g, b));
+    }
+
+    public static void setColor4d(double r, double g, double b, double a) {
+        setColor1i(Color.doubleToIntARGB(a, r, g, b));
+    }
+
+    public static void setColor4i(int r, int g, int b, int a) {
+        setColor1i(Color.intToIntARGB(a, r, g, b));
+    }
+
+    public static void setColor3f(float r, float g, float b) {
+        setColor4f(r, g, b, 1f);
+    }
+
+    public static void setColor(@NotNull Color color) {
+        setColor1i(color.value);
+    }
+
+    public static void setColor3fv(@NotNull Vector3fc colorVec) {
+        setColor4f(colorVec.x(), colorVec.y(), colorVec.z(), 1f);
+    }
+
+    public static void setColor4fv(@NotNull Vector4fc colorVec) {
+        setColor4f(colorVec.x(), colorVec.y(), colorVec.z(), colorVec.w());
+    }
+    public static void setColor3dv(@NotNull Vector3dc colorVec) {
+        setColor4d(colorVec.x(), colorVec.y(), colorVec.z(), 1d);
+    }
+
+    public static void setColor4dv(@NotNull Vector4dc colorVec) {
+        setColor4d(colorVec.x(), colorVec.y(), colorVec.z(), colorVec.w());
+    }
+
+    public static void setColor3d(double r, double g, double b) {
+        setColor4d(r, g, b, 1d);
+    }
+
+    public static void setColor3i(int r, int g, int b) {
+        setColor4i(r, g, b, 255);
+    }
+
+    public static int getColor() {
+        return instance.currentColor;
+    }
+
+    public static @NotNull TessellatorShader getTessellator() {
+        return instance.tessellatorShader;
+    }
+
+    public static void pushFrame() {
+        instance.stateConfigStack[instance.stackIndex] = instance.currentStateConfig;
+        instance.colorStack[instance.stackIndex] = instance.currentColor;
+        instance.shaderStack[instance.stackIndex] = instance.currentShader;
+        instance.fogStateStack[instance.stackIndex] =instance.currentFogState.copy();
+        instance.depthFuncStack[instance.stackIndex] = instance.currentDepthFunc;
+        instance.cullFaceStack[instance.stackIndex] = instance.currentCullFace;
+        instance.sFactorStack[instance.stackIndex] = instance.currentSFactor;
+        instance.dFactorStack[instance.stackIndex] = instance.currentDFactor;
+        instance.frontFaceStack[instance.stackIndex] = instance.currentFrontFace;
+        instance.lineWidthStack[instance.stackIndex] = instance.currentLineWidth;
+        instance.colorMaskStack[instance.stackIndex] = instance.currentColorMask;
+        instance.depthMaskStack[instance.stackIndex] = instance.currentDepthMask;
+        instance.polygonFactorStack[instance.stackIndex] = instance.currentPolygonFactor;
+        instance.polygonUnitsStack[instance.stackIndex] = instance.currentPolygonUnits;
+        instance.lightmapBlockStack[instance.stackIndex] = instance.currentLightmapBlock;
+        instance.lightmapSkyStack[instance.stackIndex] = instance.currentLightmapSky;
+
+        if (DEBUG) {
+            StackTraceElement[] eles = Thread.currentThread().getStackTrace();
+            instance.pushListenStack[instance.stackIndex] = eles[2];
+            if (instance.stackIndex >= RENDER_FRAMES_STACK_SIZE -1) {
+                for (int i = 0; i < RENDER_FRAMES_STACK_SIZE; i++) {
+                    StackTraceElement pushE = instance.pushListenStack[i];
+                    if (pushE != null) {
+                        LOGGER.error("Index: {} \t {}.{}({}.java:{})", i, pushE.getClassName(), pushE.getMethodName(), pushE.getClassName().substring(pushE.getClassName().lastIndexOf(".") + 1), pushE.getLineNumber());
+                    }
+                }
+                reset();
+                throw new RuntimeException("Stack Limit Exceeded");
+            }
+        }
+
+        instance.stackIndex++;
+
+        instance.projectionMatrixStack.pushMatrix();
+        instance.viewMatrixStack.pushMatrix();
+        instance.modelMatrixStack.pushMatrix();
+    }
+
+    public static void popFrame() {
+        instance.stackIndex--;
+        if (DEBUG) {
+            StackTraceElement[] eles = Thread.currentThread().getStackTrace();
+            if (instance.stackIndex < 0) {
+                for (int i = 0; i < RENDER_FRAMES_STACK_SIZE; i++) {
+                    StackTraceElement pushE = instance.pushListenStack[i];
+                    StackTraceElement popE = instance.popListenStack[i];
+                    LOGGER.error("Index: {} \t {}.{}({}.java:{})", i, pushE.getClassName(), pushE.getMethodName(), pushE.getClassName().substring(pushE.getClassName().lastIndexOf(".") + 1), pushE.getLineNumber());
+                    LOGGER.error("Index: {} \t {}.{}({}.java:{})", i, popE.getClassName(), popE.getMethodName(), popE.getClassName().substring(popE.getClassName().lastIndexOf(".") + 1), popE.getLineNumber());
+                }
+                reset();
+                throw new RuntimeException("Stack Limit Exceeded");
+            }
+            instance.popListenStack[instance.stackIndex ] = eles[2];
+        }
+
+        instance.projectionMatrixStack.popMatrix();
+        instance.viewMatrixStack.popMatrix();
+        instance.modelMatrixStack.popMatrix();
+
+        long newConfig = instance.stateConfigStack[instance.stackIndex];
+        State.setStateConfig(instance.currentStateConfig, newConfig);
+        instance.currentStateConfig = newConfig;
+
+        instance.currentColor = instance.colorStack[instance.stackIndex];
+        instance.currentShader = instance.shaderStack[instance.stackIndex];
+        instance.currentFogState = instance.fogStateStack[instance.stackIndex];
+
+        if (instance.currentDepthFunc != instance.depthFuncStack[instance.stackIndex]) {
+            instance.currentDepthFunc = instance.depthFuncStack[instance.stackIndex];
+            GL41.glDepthFunc(instance.currentDepthFunc.cap);
+        }
+
+        if (instance.currentCullFace != instance.cullFaceStack[instance.stackIndex]) {
+            instance.currentCullFace = instance.cullFaceStack[instance.stackIndex];
+            GL41.glCullFace(instance.currentCullFace.cap);
+        }
+
+        if (instance.currentSFactor != instance.sFactorStack[instance.stackIndex] || instance.currentDFactor != instance.dFactorStack[instance.stackIndex]) {
+            instance.currentSFactor = instance.sFactorStack[instance.stackIndex];
+            instance.currentDFactor = instance.dFactorStack[instance.stackIndex];
+            GL41.glBlendFunc(instance.currentSFactor.cap, instance.currentDFactor.cap);
+        }
+
+        if (instance.currentFrontFace != instance.frontFaceStack[instance.stackIndex]) {
+            instance.currentFrontFace = instance.frontFaceStack[instance.stackIndex];
+            GL41.glFrontFace(instance.currentFrontFace.cap);
+        }
+
+        instance.currentLineWidth = instance.lineWidthStack[instance.stackIndex];
+
+        if (instance.currentColorMask != instance.colorMaskStack[instance.stackIndex]) {
+            instance.currentColorMask = instance.colorMaskStack[instance.stackIndex];
+            GL41.glColorMask((instance.currentColorMask & 0b1000) != 0, (instance.currentColorMask & 0b0100) != 0, (instance.currentColorMask & 0b0010) != 0, (instance.currentColorMask & 0b0001) != 0);
+        }
+
+        if (instance.currentDepthMask != instance.depthMaskStack[instance.stackIndex]) {
+            instance.currentDepthMask = instance.depthMaskStack[instance.stackIndex];
+            GL41.glDepthMask(instance.currentDepthMask);
+        }
+
+        if (instance.currentPolygonFactor != instance.polygonFactorStack[instance.stackIndex] || instance.currentPolygonUnits != instance.polygonUnitsStack[instance.stackIndex]) {
+            instance.currentPolygonFactor = instance.polygonFactorStack[instance.stackIndex];
+            instance.currentPolygonUnits = instance.polygonUnitsStack[instance.stackIndex];
+            GL41.glPolygonOffset(instance.currentPolygonFactor, instance.currentPolygonUnits);
+        }
+
+        instance.currentLightmapBlock = instance.lightmapBlockStack[instance.stackIndex];
+        instance.currentLightmapSky = instance.lightmapSkyStack[instance.stackIndex];
+    }
+
+    protected static void reset() {
+        instance.stackIndex = 1;
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/renderer/Shaders.java b/game/client/src/main/java/net/minecraft/client/render/renderer/Shaders.java
new file mode 100644
index 000000000..689a8feb2
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/renderer/Shaders.java
@@ -0,0 +1,57 @@
+package net.minecraft.client.render.renderer;
+
+import com.mojang.logging.LogUtils;
+import net.minecraft.client.render.shader.Shader;
+import net.minecraft.client.render.shader.ShaderGeometry;
+import net.minecraft.client.render.shader.ShaderProvider;
+import net.minecraft.client.render.shader.ShaderProviderInternal;
+import org.jetbrains.annotations.NotNull;
+import org.slf4j.Logger;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+public final class Shaders {
+    private static final Logger LOGGER = LogUtils.getLogger();
+    public static final @NotNull List<@NotNull Shader> ALL_SHADERS = new ArrayList<>();
+    public static final @NotNull Map<@NotNull String, @NotNull Shader> SHADER_MAP = new HashMap<>();
+    public static final @NotNull ShaderProvider PROVIDER_INTERNAL = new ShaderProviderInternal("/shaders/");
+
+    public static final @NotNull Shader WORLD = register("world", new Shader());
+    public static final @NotNull Shader INTERFACE = register("interface", new Shader());
+    public static final @NotNull Shader COLOR = register("color", new Shader());
+    public static final @NotNull Shader COLOR_WORLD = register("color_world", new Shader());
+    public static final @NotNull Shader CLOUDS = register("clouds", new Shader());
+    public static final @NotNull ShaderGeometry PARTICLE = register("particle", new ShaderGeometry());
+    public static final @NotNull ShaderGeometry FONT = register("font", new ShaderGeometry());
+    public static final @NotNull ShaderGeometry LINES = register("lines", new ShaderGeometry());
+
+    public static @NotNull <T extends Shader> T register(@NotNull String id, @NotNull T shader) {
+        if (!ALL_SHADERS.contains(shader)) ALL_SHADERS.add(shader);
+        SHADER_MAP.put(id, shader);
+        return shader;
+    }
+
+    public static void init() {
+        for (Map.Entry<String, Shader> entry : SHADER_MAP.entrySet()) {
+            try {
+                entry.getValue().compile(PROVIDER_INTERNAL, entry.getKey());
+            } catch (Exception e) {
+                LOGGER.error("", e);
+            }
+        }
+    }
+
+    public static void reload() {
+        for (Map.Entry<String, Shader> entry : SHADER_MAP.entrySet()) {
+            try {
+                entry.getValue().delete();
+                entry.getValue().compile(PROVIDER_INTERNAL, entry.getKey());
+            } catch (Exception e) {
+                LOGGER.error("", e);
+            }
+        }
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/renderer/State.java b/game/client/src/main/java/net/minecraft/client/render/renderer/State.java
new file mode 100644
index 000000000..1ec24cd49
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/renderer/State.java
@@ -0,0 +1,96 @@
+package net.minecraft.client.render.renderer;
+
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.opengl.GL41;
+
+public enum State {// Keep ordered so that most commonly used toggles have the lowest ordinals, should decrease average set state time
+    BLEND(GL41.GL_BLEND),
+    DEPTH_TEST(GL41.GL_DEPTH_TEST),
+    CULL_FACE(GL41.GL_CULL_FACE),
+    SCISSOR_TEST(GL41.GL_SCISSOR_TEST),
+    POLYGON_OFFSET_FILL(GL41.GL_POLYGON_OFFSET_FILL),
+    POLYGON_OFFSET_LINE(GL41.GL_POLYGON_OFFSET_LINE),
+    POLYGON_OFFSET_POINT(GL41.GL_POLYGON_OFFSET_POINT),
+    POLYGON_SMOOTH(GL41.GL_POLYGON_SMOOTH),
+    STENCIL_TEST(GL41.GL_STENCIL_TEST),
+    CLIP_DISTANCE0(GL41.GL_CLIP_DISTANCE0),
+    CLIP_DISTANCE1(GL41.GL_CLIP_DISTANCE1),
+    CLIP_DISTANCE2(GL41.GL_CLIP_DISTANCE2),
+    CLIP_DISTANCE3(GL41.GL_CLIP_DISTANCE3),
+    CLIP_DISTANCE4(GL41.GL_CLIP_DISTANCE4),
+    CLIP_DISTANCE5(GL41.GL_CLIP_DISTANCE5),
+    CLIP_DISTANCE6(GL41.GL_CLIP_DISTANCE6),
+    CLIP_DISTANCE7(GL41.GL_CLIP_DISTANCE7),
+    COLOR_LOGIC_OP(GL41.GL_COLOR_LOGIC_OP),
+    //        DEBUG_OUTPUT(GL43.GL_DEBUG_OUTPUT),
+    //        DEBUG_OUTPUT_SYNCHRONOUS(GL43.GL_DEBUG_OUTPUT_SYNCHRONOUS),
+    DEPTH_CLAMP(GL41.GL_DEPTH_CLAMP),
+    DITHER(GL41.GL_DITHER),
+    FRAMEBUFFER_SRGB(GL41.GL_FRAMEBUFFER_SRGB),
+    LINE_SMOOTH(GL41.GL_LINE_SMOOTH),
+    MULTISAMPLE(GL41.GL_MULTISAMPLE),
+    PRIMITIVE_RESTART(GL41.GL_PRIMITIVE_RESTART),
+    //        PRIMITIVE_RESTART_FIXED_INDEX(GL43.GL_PRIMITIVE_RESTART_FIXED_INDEX),
+    RASTERIZER_DISCARD(GL41.GL_RASTERIZER_DISCARD),
+    SAMPLE_ALPHA_TO_COVERAGE(GL41.GL_SAMPLE_ALPHA_TO_COVERAGE),
+    SAMPLE_ALPHA_TO_ONE(GL41.GL_SAMPLE_ALPHA_TO_ONE),
+    SAMPLE_COVERAGE(GL41.GL_SAMPLE_COVERAGE),
+    SAMPLE_SHADING(GL41.GL_SAMPLE_SHADING),
+    SAMPLE_MASK(GL41.GL_SAMPLE_MASK),
+    TEXTURE_CUBE_MAP_SEAMLESS(GL41.GL_TEXTURE_CUBE_MAP_SEAMLESS),
+    PROGRAM_POINT_SIZE(GL41.GL_PROGRAM_POINT_SIZE);
+
+    private static final int COUNT = values().length;
+    private static final @NotNull net.minecraft.client.render.renderer.State @NotNull [] TOGGLES = values();
+
+    public final int cap;
+    public final long bitMask;
+
+    State(int cap) {
+        this.cap = cap;
+        this.bitMask = 1L << ordinal();
+    }
+
+    long enable(long config) {
+        return config | this.bitMask;
+    }
+
+    long disable(long config) {
+        return config & ~this.bitMask;
+    }
+
+    boolean isEnabled(long config) {
+        return (config & this.bitMask) != 0;
+    }
+
+    boolean isSystemEnabled() {
+        return GL41.glIsEnabled(this.cap);
+    }
+
+    private static long getSystemStateConfig() {
+        long currentConfig = 0L;
+        for (int i = 0; i < net.minecraft.client.render.renderer.State.COUNT; i++) {
+            net.minecraft.client.render.renderer.State t = net.minecraft.client.render.renderer.State.TOGGLES[i];
+            if (t.isSystemEnabled()) {
+                currentConfig |= t.bitMask;
+            }
+        }
+        return currentConfig;
+    }
+
+    static void setStateConfig(long currentConfig, long newConfig) {
+        if (currentConfig == newConfig) return;
+        long difConfig = currentConfig ^ newConfig; // Differences between configs
+        int max = 64 - Long.numberOfLeadingZeros(difConfig); // Number of bits until reaching the highest difference bit
+        for (int i = 0; i < max; i++) {
+            if ((difConfig >> i & 0b1) != 0) { // If config differs from current
+                net.minecraft.client.render.renderer.State t = net.minecraft.client.render.renderer.State.TOGGLES[i];
+                if (t.isEnabled(newConfig)) {
+                    GL41.glEnable(t.cap);
+                } else {
+                    GL41.glDisable(t.cap);
+                }
+            }
+        }
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/shader/PhotoModeRenderer.java b/game/client/src/main/java/net/minecraft/client/render/shader/PhotoModeRenderer.java
index 1521e22b7..121307b0c 100644
--- a/game/client/src/main/java/net/minecraft/client/render/shader/PhotoModeRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/shader/PhotoModeRenderer.java
@@ -5,41 +5,40 @@ import net.minecraft.client.gui.ScreenPhotoMode;
 
 public class PhotoModeRenderer extends ShadersRenderer {
 
-	public static final String[] shaders = new String[] { null, "blur", "silhouette", "vignette", "tiltshift", "outline", "outline2", "eerie", "sepia", "inverted", "distantblur" };
-
-	public final ScreenPhotoMode screen;
-
-	private int selectedShader = 0;
-
-	public PhotoModeRenderer(Minecraft minecraft, ScreenPhotoMode screen) {
-		super(minecraft);
-
-		this.screen = screen;
-		
-		if(!Shaders.enableShaders) throw new RuntimeException("Shaders disabled!");
-	}
-
-	@Override
-	public ShaderProvider getShader() {
-		if(selectedShader > 0) {
-			return new ShaderProviderInternal("/shaders/photo/" + getActiveShader() + "/");
-		} else {
-			return internal;
-		}
-	}
-	
-	public void next() {
-		selectedShader = (selectedShader + 1) % shaders.length;
-		reload();
-	}
-
-	public void first() {
-		selectedShader = 0;
-		reload();
-	}
-
-	public String getActiveShader() {
-		return shaders[selectedShader];
-	}
+    public static final String[] shaders = new String[]{null, "blur", "silhouette", "vignette", "tiltshift", "outline", "outline2", "eerie", "sepia", "inverted", "distantblur"};
+
+    public final ScreenPhotoMode screen;
+
+    private int selectedShader = 0;
+
+    public PhotoModeRenderer(Minecraft minecraft, ScreenPhotoMode screen) {
+        super(minecraft);
+
+        this.screen = screen;
+
+    }
+
+    @Override
+    public ShaderProvider getShader() {
+        if (this.selectedShader > 0) {
+            return new ShaderProviderInternal("/shaders/photo/" + getActiveShader() + "/");
+        } else {
+            return this.internal;
+        }
+    }
+
+    public void next() {
+        this.selectedShader = (this.selectedShader + 1) % shaders.length;
+        reload();
+    }
+
+    public void first() {
+        this.selectedShader = 0;
+        reload();
+    }
+
+    public String getActiveShader() {
+        return shaders[this.selectedShader];
+    }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/shader/Shader.java b/game/client/src/main/java/net/minecraft/client/render/shader/Shader.java
index e259f194f..d16c55ea5 100644
--- a/game/client/src/main/java/net/minecraft/client/render/shader/Shader.java
+++ b/game/client/src/main/java/net/minecraft/client/render/shader/Shader.java
@@ -8,6 +8,7 @@ import java.util.Map;
 import com.mojang.logging.LogUtils;
 import it.unimi.dsi.fastutil.objects.Object2IntArrayMap;
 import it.unimi.dsi.fastutil.objects.Object2IntMap;
+import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap;
 import net.minecraft.client.render.OpenGLHelper;
 import org.jetbrains.annotations.NotNull;
 import org.slf4j.Logger;
@@ -22,7 +23,7 @@ public class Shader {
     public boolean supported = true;
     protected boolean enabled = false;
 
-    protected final Object2IntMap<String> uniformLocations = new Object2IntArrayMap<>();
+    protected final Object2IntMap<String> uniformLocations = new Object2IntOpenHashMap<>();
 
     public @NotNull Shader compile(@NotNull ShaderProvider folder, @NotNull String name) {
         if (!supported) return this;
@@ -91,8 +92,8 @@ public class Shader {
     }
 
     public int getUniform(String uniform) {
-        int location = this.uniformLocations.getOrDefault(uniform, -1);
-        if (location == -1) {
+        int location = this.uniformLocations.getOrDefault(uniform, -2);
+        if (location == -2) {
             location = glGetUniformLocation(this.program, uniform);
             this.uniformLocations.put(uniform, location);
         }
diff --git a/game/client/src/main/java/net/minecraft/client/render/shader/ShaderHelper.java b/game/client/src/main/java/net/minecraft/client/render/shader/ShaderHelper.java
new file mode 100644
index 000000000..17d9258b2
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/shader/ShaderHelper.java
@@ -0,0 +1,126 @@
+
+package net.minecraft.client.render.shader;
+
+import net.minecraft.client.Minecraft;
+import net.minecraft.client.gui.ScreenPhotoMode;
+import net.minecraft.client.render.camera.CameraUtil;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.RenderBuffer;
+import net.minecraft.core.block.Blocks;
+import net.minecraft.core.block.material.Material;
+import net.minecraft.core.block.material.Materials;
+import net.minecraft.core.enums.HumanArmorShape;
+import net.minecraft.core.item.ItemStack;
+import org.lwjgl.opengl.GL41;
+
+public final class ShaderHelper {
+    private static RenderBuffer fullScreenRect = null;
+
+    private static final long startTime = System.currentTimeMillis();
+    private static float frameTimeCounter = 0.0f;
+
+    private ShaderHelper() {
+
+    }
+
+    public static void drawFullscreenRect() {
+        if (fullScreenRect == null) {
+            int vao = GL41.glGenVertexArrays();
+            int vbo = GL41.glGenBuffers();
+
+            float[] quadVertices = new float[]{
+                -1.0f,   1.0f, 0.0f, 1.0f,
+                -1.0f,  -1.0f, 0.0f, 0.0f,
+                 1.0f,  1.0f,  1.0f, 1.0f,
+                 1.0f,  -1.0f, 1.0f, 0.0f,
+            };
+
+            GL41.glBindVertexArray(vao);
+            GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, vbo);
+
+            GL41.glBufferData(GL41.GL_ARRAY_BUFFER, quadVertices, GL41.GL_STATIC_DRAW);
+
+            GL41.glVertexAttribPointer(0, 2, GL41.GL_FLOAT, false, Float.BYTES * 4, 0);
+            GL41.glVertexAttribPointer(1, 2, GL41.GL_FLOAT, false, Float.BYTES * 4, Float.BYTES * 2);
+
+            GL41.glEnableVertexAttribArray(0);
+            GL41.glEnableVertexAttribArray(1);
+
+            GL41.glBindVertexArray(0);
+            fullScreenRect = new RenderBuffer(vao, vbo, 0, 6, DrawMode.TRIANGLES);
+        }
+
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.disableState(State.CULL_FACE);
+        GLRenderer.disableState(State.SCISSOR_TEST);
+
+        GL41.glBindVertexArray(fullScreenRect.vao());
+        GL41.glDrawArrays(GL41.GL_TRIANGLE_STRIP, 0, 4);
+        GL41.glBindVertexArray(0);
+    }
+
+    public static void setUniforms(Minecraft minecraft, Shader shader, float partialTicks) {
+        long now = System.currentTimeMillis();
+        int passedTime = (int) (now - startTime);
+        frameTimeCounter = passedTime / 1000.0f;
+
+        if (!shader.isEnabled()) return;
+
+        shader.bind();
+        shader.uniformFloat("width", minecraft.gameWindow.getWidthPixels());
+        shader.uniformFloat("height", minecraft.gameWindow.getHeightPixels());
+        shader.uniformFloat("frameTimeCounter", frameTimeCounter);
+        shader.uniformFloat("gamma", minecraft.gameSettings.gamma.value);
+        shader.uniformFloat("fxaa", minecraft.gameSettings.fxaa.value);
+        shader.uniformFloat("heatHaze", minecraft.gameSettings.heatHaze.value ? minecraft.ppm.lerped.heatHaze : 0.0f);
+        shader.uniformInt("bloom", minecraft.gameSettings.bloom.value);
+        shader.uniformInt("dimension", minecraft.currentWorld != null && minecraft.currentWorld.dimension != null ? minecraft.currentWorld.dimension.id : 0);
+        shader.uniformInt("cbCorrectionMode", minecraft.gameSettings.colorblindnessFix.value.ordinal());
+
+        ItemStack helmet = minecraft.thePlayer == null ? null : minecraft.thePlayer.getItemInArmorSlot(HumanArmorShape.HEAD);
+        shader.uniformInt("shaderEffect", helmet != null && helmet.itemID == Blocks.PUMPKIN_REDSTONE.id() ? 1 : 0);
+
+        int isEyeInLiquid = 0;
+        float celestialAngle = 0.0f;
+        if (minecraft.thePlayer != null && minecraft.currentWorld != null && minecraft.activeCamera != null) {
+            if (CameraUtil.isUnderLiquid(minecraft.activeCamera, minecraft.currentWorld, Materials.LAVA, partialTicks)) {
+                isEyeInLiquid = 2;
+            } else if (CameraUtil.isUnderLiquid(minecraft.activeCamera, minecraft.currentWorld, Materials.WATER, partialTicks)) {
+                isEyeInLiquid = 1;
+            }
+            celestialAngle = minecraft.currentWorld.getCelestialAngle(partialTicks);
+        }
+        shader.uniformInt("isEyeInLiquid", isEyeInLiquid);
+        shader.uniformFloat("celestialAngle", celestialAngle);
+
+        if (minecraft.ppm.enabled) {
+            shader.uniformFloat("brightness", minecraft.ppm.lerped.brightness);
+            shader.uniformFloat("contrast", minecraft.ppm.lerped.contrast);
+            shader.uniformFloat("exposure", minecraft.ppm.lerped.exposure);
+            shader.uniformFloat("saturation", minecraft.ppm.lerped.saturation);
+            shader.uniformFloat("rMod", minecraft.ppm.lerped.rMod);
+            shader.uniformFloat("gMod", minecraft.ppm.lerped.gMod);
+            shader.uniformFloat("bMod", minecraft.ppm.lerped.bMod);
+        } else {
+            shader.uniformFloat("brightness", 0.0f);
+            shader.uniformFloat("contrast", 0.0f);
+            shader.uniformFloat("exposure", 0.0f);
+            shader.uniformFloat("saturation", 0.0f);
+            shader.uniformFloat("rMod", 1.0f);
+            shader.uniformFloat("gMod", 1.0f);
+            shader.uniformFloat("bMod", 1.0f);
+        }
+        shader.uniformFloat("photoMode", minecraft.currentScreen instanceof ScreenPhotoMode);
+        shader.uniformFloat("guiOpened", minecraft.currentScreen != null);
+
+        if (minecraft.currentScreen instanceof ScreenPhotoMode screenPhotoMode) {
+            shader.uniformFloat("intensity", screenPhotoMode.intensityValue);
+        } else {
+            shader.uniformFloat("intensity", 1.0f);
+        }
+    }
+
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/shader/ShaderProviderInternal.java b/game/client/src/main/java/net/minecraft/client/render/shader/ShaderProviderInternal.java
index da6097a29..afb41fe6b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/shader/ShaderProviderInternal.java
+++ b/game/client/src/main/java/net/minecraft/client/render/shader/ShaderProviderInternal.java
@@ -4,6 +4,7 @@ import java.io.InputStream;
 
 import com.b100.utils.StringUtils;
 import com.mojang.logging.LogUtils;
+import net.minecraft.client.Minecraft;
 import org.slf4j.Logger;
 
 public class ShaderProviderInternal implements ShaderProvider {
@@ -16,9 +17,9 @@ public class ShaderProviderInternal implements ShaderProvider {
 	
 	@Override
 	public String getShaderSource(String name) {
-		String path = dir + name;
+		String path = this.dir + name;
 
-        try (InputStream stream = ShaderProviderInternal.class.getResourceAsStream(dir + name)) {
+        try (InputStream stream = Minecraft.getMinecraft().texturePackList.getResourceAsStream(this.dir + name)) {
             if (stream != null) {
                 return StringUtils.readInputString(stream);
             } else {
@@ -26,7 +27,7 @@ public class ShaderProviderInternal implements ShaderProvider {
                 return null;
             }
         } catch (Exception e) {
-            LOGGER.error("Exception reading shader resource '{}{}'!", dir, name, e);
+            LOGGER.error("Exception reading shader resource '{}{}'!", this.dir, name, e);
             return null;
         }
 	}
diff --git a/game/client/src/main/java/net/minecraft/client/render/shader/Shaders.java b/game/client/src/main/java/net/minecraft/client/render/shader/Shaders.java
deleted file mode 100644
index 7d1f69138..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/shader/Shaders.java
+++ /dev/null
@@ -1,123 +0,0 @@
-
-package net.minecraft.client.render.shader;
-
-import static org.lwjgl.opengl.GL11.*;
-
-import net.minecraft.client.Minecraft;
-import net.minecraft.client.gui.ScreenPhotoMode;
-import net.minecraft.client.render.camera.CameraUtil;
-import net.minecraft.core.block.Blocks;
-import net.minecraft.core.block.material.Materials;
-import net.minecraft.core.enums.HumanArmorShape;
-import net.minecraft.core.item.ItemStack;
-
-public abstract class Shaders {
-	
-    private static int fullscreenRectList;	
-    
-    public static boolean enableShaders = false;
-	
-	private static final long startTime = System.currentTimeMillis();
-	private static float frameTimeCounter = 0.0f;
-    
-	public static void drawFullscreenRect() {
-    	glDisable(GL_BLEND);
-    	glDisable(GL_FOG);
-    	glDisable(GL_DEPTH_TEST);
-    	glDisable(GL_CULL_FACE);
-    	glDisable(GL_LIGHTING);
-    	glDisable(GL_SCISSOR_TEST);
-    	glDisable(GL_ALPHA_TEST);
-    	glColor4d(1.0, 1.0, 1.0, 1.0);
-    	glEnable(GL_TEXTURE_2D);
-    	
-    	glMatrixMode(GL_PROJECTION);
-    	glLoadIdentity();
-    	glMatrixMode(GL_MODELVIEW);
-    	glLoadIdentity();
-    	glMatrixMode(GL_PROJECTION);
-    	
-    	if(fullscreenRectList == 0) {
-    		fullscreenRectList = glGenLists(1);
-    		glNewList(fullscreenRectList, GL_COMPILE);
-    		
-        	glBegin(GL_QUADS);
-        	glTexCoord2d(0, 0);
-        	glVertex2d(-1, -1);
-        	glTexCoord2d(0, 1);
-        	glVertex2d(-1, 1);
-        	glTexCoord2d(1, 1);
-        	glVertex2d(1, 1);
-        	glTexCoord2d(1, 0);
-        	glVertex2d(1, -1);
-        	glEnd();
-        	
-        	glEndList();
-    	}
-    	
-    	glCallList(fullscreenRectList);
-	}
-	
-	public static void setUniforms(Minecraft minecraft, Shader shader, float partialTicks) {
-		long now = System.currentTimeMillis();
-		int passedTime = (int) (now - startTime);
-		frameTimeCounter = passedTime / 1000.0f;
-		
-		if(!shader.isEnabled()) return;
-		
-		shader.bind();
-		shader.uniformFloat("width", minecraft.gameWindow.getWidthPixels());
-		shader.uniformFloat("height", minecraft.gameWindow.getHeightPixels());
-		shader.uniformFloat("frameTimeCounter", frameTimeCounter);
-		shader.uniformFloat("gamma", minecraft.gameSettings.gamma.value);
-		shader.uniformFloat("fxaa", minecraft.gameSettings.fxaa.value);
-		shader.uniformFloat("heatHaze", minecraft.gameSettings.heatHaze.value ? minecraft.ppm.lerped.heatHaze : 0.0f);
-		shader.uniformInt("bloom", minecraft.gameSettings.bloom.value);
-		shader.uniformInt("dimension", minecraft.currentWorld != null && minecraft.currentWorld.dimension != null ? minecraft.currentWorld.dimension.id : 0);
-		shader.uniformInt("cbCorrectionMode", minecraft.gameSettings.colorblindnessFix.value.ordinal());
-
-		ItemStack helmet = minecraft.thePlayer == null ? null : minecraft.thePlayer.getItemInArmorSlot(HumanArmorShape.HEAD);
-		shader.uniformInt("shaderEffect", helmet != null && helmet.itemID == Blocks.PUMPKIN_REDSTONE.id() ? 1 : 0);
-
-		int isEyeInLiquid = 0;
-		float celestialAngle = 0.0f;
-		if(minecraft.thePlayer != null && minecraft.currentWorld != null && minecraft.activeCamera != null) {
-			if(CameraUtil.isUnderLiquid(minecraft.activeCamera, minecraft.currentWorld, Materials.LAVA, partialTicks)) {
-				isEyeInLiquid = 2;
-			}else if(CameraUtil.isUnderLiquid(minecraft.activeCamera, minecraft.currentWorld, Materials.WATER, partialTicks)) {
-				isEyeInLiquid = 1;
-			}
-			celestialAngle = minecraft.currentWorld.getCelestialAngle(partialTicks);
-		}
-		shader.uniformInt("isEyeInLiquid", isEyeInLiquid);
-		shader.uniformFloat("celestialAngle", celestialAngle);
-		
-		if (minecraft.ppm.enabled) {
-			shader.uniformFloat("brightness", minecraft.ppm.lerped.brightness);
-			shader.uniformFloat("contrast", minecraft.ppm.lerped.contrast);
-			shader.uniformFloat("exposure", minecraft.ppm.lerped.exposure);
-			shader.uniformFloat("saturation", minecraft.ppm.lerped.saturation);
-			shader.uniformFloat("rMod", minecraft.ppm.lerped.rMod);
-			shader.uniformFloat("gMod", minecraft.ppm.lerped.gMod);
-			shader.uniformFloat("bMod", minecraft.ppm.lerped.bMod);
-		} else {
-			shader.uniformFloat("brightness", 0.0f);
-			shader.uniformFloat("contrast", 0.0f);
-			shader.uniformFloat("exposure", 0.0f);
-			shader.uniformFloat("saturation", 0.0f);
-			shader.uniformFloat("rMod", 1.0f);
-			shader.uniformFloat("gMod", 1.0f);
-			shader.uniformFloat("bMod", 1.0f);
-		}
-		shader.uniformFloat("photoMode", minecraft.currentScreen instanceof ScreenPhotoMode);
-		shader.uniformFloat("guiOpened", minecraft.currentScreen != null);
-		
-		if(minecraft.currentScreen instanceof ScreenPhotoMode) {
-			ScreenPhotoMode screenPhotoMode = (ScreenPhotoMode) minecraft.currentScreen;
-			shader.uniformFloat("intensity", screenPhotoMode.intensityValue);
-		}else {
-			shader.uniformFloat("intensity", 1.0f);
-		}
-	}
-
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/shader/ShadersRenderer.java b/game/client/src/main/java/net/minecraft/client/render/shader/ShadersRenderer.java
index 0bb681523..397d2cc2a 100644
--- a/game/client/src/main/java/net/minecraft/client/render/shader/ShadersRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/shader/ShadersRenderer.java
@@ -1,77 +1,46 @@
 package net.minecraft.client.render.shader;
 
-import static org.lwjgl.opengl.ARBFramebufferObject.*;
-import static org.lwjgl.opengl.ARBMultitexture.*;
-import static org.lwjgl.opengl.GL20.*;
-
 import java.io.File;
-import java.nio.ByteBuffer;
-import java.nio.FloatBuffer;
 
 import com.mojang.logging.LogUtils;
-import net.minecraft.client.gui.ScreenPhotoMode;
 import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.tessellator.ParticleTessellator;
-import net.minecraft.client.render.tessellator.ShaderParticleTessellator;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.Shaders;
 import net.minecraft.core.block.material.Materials;
-import org.jetbrains.annotations.NotNull;
-import org.joml.Matrix4f;
-import org.lwjgl.opengl.GL30;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.Framebuffer;
+import net.minecraft.client.render.FrameBuffer;
 import net.minecraft.client.render.OpenGLHelper;
 import net.minecraft.client.render.Renderer;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.client.render.camera.CameraUtil;
-import org.lwjgl.system.MemoryUtil;
+import org.lwjgl.opengl.GL41;
 import org.slf4j.Logger;
 
 public class ShadersRenderer implements Renderer {
     private static final Logger LOGGER = LogUtils.getLogger();
     public Minecraft mc;
 
-    protected final int vao;
-    protected final Framebuffer worldFramebuffer = new Framebuffer();
-    protected final Texture worldFramebufferTex = new Texture();
+    protected final FrameBuffer worldFramebuffer = new FrameBuffer();
+    protected final Texture worldFramebufferColor = new Texture();
     protected final Texture worldFramebufferDepth = new Texture();
+    protected int worldRenderBufferObject = 0;
 
-    protected final Framebuffer gameFramebuffer = new Framebuffer();
-    protected final Texture gameFramebufferTex = new Texture();
-    protected final Texture gameFramebufferDepth = new Texture();
+    protected final FrameBuffer gameFramebuffer = new FrameBuffer();
+    protected final Texture gameFramebufferColor = new Texture();
+    protected int gameRenderBufferObject = 0;
 
     protected final Shader postShader = new Shader();
     protected final Shader finalShader = new Shader();
-    protected final Shader cloudsShader = new Shader();
-    protected final ShaderGeometry particleShader = new ShaderGeometry();
-
     protected ShaderProvider internal = new ShaderProviderInternal("/shaders/");
 
-    public ShaderParticleTessellator shaderParticleTessellator = new ShaderParticleTessellator(200000);
-
     public int fbWidth;
     public int fbHeight;
 
     public int renderWidth;
     public int renderHeight;
 
-    protected FloatBuffer matrixBuffer = MemoryUtil.memAllocFloat(16);
-    protected Matrix4f matrix = new Matrix4f();
-
     public ShadersRenderer(Minecraft minecraft) {
         this.mc = minecraft;
-
-        if (!Shaders.enableShaders) throw new RuntimeException("Shaders disabled!");
-        if (OpenGLHelper.gl32) {
-            this.vao = GL30.glGenVertexArrays();
-            this.particleShader.supported = true;
-            LOGGER.info("GL32 supported, enabling particle geometry shaders");
-        } else {
-            this.vao = 0;
-            this.particleShader.supported = false;
-            LOGGER.info("GL32 not supported, disabling particle geometry shaders");
-        }
     }
 
     @Override
@@ -83,11 +52,11 @@ public class ShadersRenderer implements Renderer {
         if (this.finalShader.isEnabled()) {
             this.gameFramebuffer.bind();
         } else {
-            glBindFramebuffer(GL_FRAMEBUFFER, 0);
+            GL41.glBindFramebuffer(GL41.GL_FRAMEBUFFER, 0);
         }
 
-        glUseProgram(0);
-        glViewport(0, 0, this.fbWidth, this.fbHeight);
+        GL41.glUseProgram(0);
+        GL41.glViewport(0, 0, this.fbWidth, this.fbHeight);
 
         OpenGLHelper.checkError("begin render game");
     }
@@ -96,19 +65,19 @@ public class ShadersRenderer implements Renderer {
     public void endRenderGame(float partialTicks) {
         OpenGLHelper.checkError("pre end render game");
 
-        glViewport(0, 0, this.fbWidth, this.fbHeight);
-        glBindFramebuffer(GL_FRAMEBUFFER, 0);
+        GL41.glViewport(0, 0, this.fbWidth, this.fbHeight);
+        GL41.glBindFramebuffer(GL41.GL_FRAMEBUFFER, 0);
 
         if (this.finalShader.isEnabled()) {
             this.finalShader.bind();
 
-            glActiveTextureARB(GL_TEXTURE0_ARB);
-            this.gameFramebufferTex.bind();
+            GL41.glActiveTexture(GL41.GL_TEXTURE0);
+            this.gameFramebufferColor.bind();
             this.finalShader.uniformInt("colortex0", 0);
 
-            Shaders.setUniforms(this.mc, this.finalShader, partialTicks);
-            Shaders.drawFullscreenRect();
-            glUseProgram(0);
+            ShaderHelper.setUniforms(this.mc, this.finalShader, partialTicks);
+            ShaderHelper.drawFullscreenRect();
+            GL41.glUseProgram(0);
         }
 
         OpenGLHelper.checkError("end render game");
@@ -120,40 +89,62 @@ public class ShadersRenderer implements Renderer {
 
         setupFramebuffer();
         this.worldFramebuffer.bind();
-        glViewport(0, 0, this.renderWidth, this.renderHeight);
+        GL41.glViewport(0, 0, this.renderWidth, this.renderHeight);
 
-        glUseProgram(0);
+        GL41.glUseProgram(0);
 
         OpenGLHelper.checkError("begin render world");
     }
 
     @Override
-    public void beginRenderClouds(float partialTicks) {
-        if (this.mc.gameSettings.clouds.value && this.mc.gameSettings.fancyGraphics.value == 1 && this.cloudsShader.isEnabled()) {
-            OpenGLHelper.checkError("pre setup clouds");
+    public void endRenderWorld(float partialTicks) {
+        OpenGLHelper.checkError("pre end render world");
 
-            // Alpha test is implemented in the shader because regular alpha test removes some pixels at the edge
-            glDisable(GL_ALPHA_TEST);
+        if (this.finalShader.isEnabled()) {
+            this.gameFramebuffer.bind();
+        } else {
+            GL41.glBindFramebuffer(GL41.GL_FRAMEBUFFER, 0);
+        }
 
-            this.cloudsShader.bind();
+        if (this.postShader.isEnabled()) {
+            this.postShader.bind();
 
-            // Read projection matrix, invert it, and send it to the shader
-            this.matrixBuffer.clear();
-            glGetFloatv(GL_PROJECTION_MATRIX, this.matrixBuffer);
+            GL41.glActiveTexture(GL41.GL_TEXTURE0);
+            this.worldFramebufferColor.bind();
+            this.postShader.uniformInt("colortex0", 0);
+            GL41.glActiveTexture(GL41.GL_TEXTURE1);
+            this.worldFramebufferDepth.bind();
+            this.postShader.uniformInt("depthtex0", 1);
+            GL41.glActiveTexture(GL41.GL_TEXTURE0);
 
-            this.matrixBuffer.position(0);
-            this.matrix.set(this.matrixBuffer);
+            this.mc.ppm.enabled = true;
+            ShaderHelper.setUniforms(this.mc, this.postShader, partialTicks);
+            this.mc.ppm.enabled = false;
+        } else {
+            GL41.glUseProgram(0);
+            this.worldFramebufferColor.bind();
+        }
 
-            this.matrix.invert();
+        GL41.glViewport(0, 0, this.fbWidth, this.fbHeight);
+        ShaderHelper.drawFullscreenRect();
 
+        LightmapHelper.instance.enableLightmapRendering();
 
-            this.matrixBuffer.clear();
-            this.matrix.get(this.matrixBuffer);
+        GL41.glUseProgram(0);
+//        GL41.glEnable(GL41.GL_ALPHA_TEST);
+
+        OpenGLHelper.checkError("end render world");
+    }
 
-            this.matrixBuffer.position(0);
-            this.matrixBuffer.limit(16);
-            glUniformMatrix4fv(this.cloudsShader.getUniform("gbufferProjectionInverse"), false, this.matrixBuffer);
+    @Override
+    public void beginRenderClouds(float partialTicks) {
+        if (this.mc.gameSettings.clouds.value && this.mc.gameSettings.fancyGraphics.value == 1 && Shaders.CLOUDS.isEnabled()) {
+            OpenGLHelper.checkError("pre setup clouds");
+
+            // Alpha test is implemented in the shader because regular alpha test removes some pixels at the edge
+//            glDisable(GL_ALPHA_TEST);
 
+            Shaders.CLOUDS.bind();
             int isEyeInLiquid;
             if (CameraUtil.isUnderLiquid(this.mc.activeCamera, this.mc.currentWorld, Materials.LAVA, partialTicks)) {
                 isEyeInLiquid = 2;
@@ -162,108 +153,25 @@ public class ShadersRenderer implements Renderer {
             } else {
                 isEyeInLiquid = 0;
             }
-            glUniform1i(this.cloudsShader.getUniform("isEyeInLiquid"), isEyeInLiquid);
-
-            glUniform1f(this.cloudsShader.getUniform("viewWidth"), this.renderWidth);
-            glUniform1f(this.cloudsShader.getUniform("viewHeight"), this.renderHeight);
+            GL41.glUniform1i(Shaders.CLOUDS.getUniform("isEyeInLiquid"), isEyeInLiquid);
+            GL41.glUseProgram(0);
 
             OpenGLHelper.checkError("setup clouds");
         }
     }
 
     @Override
-    public void beginRenderParticles(float partialTick) {
-        if (this.particleShader.isEnabled()) {
-            OpenGLHelper.checkError("pre enable render particles");
-            GL30.glBindVertexArray(this.vao);
-            this.particleShader.bind();
-
-            this.matrix.identity();
-            glUniformMatrix4fv(this.particleShader.getUniform("model"), false, this.matrix.get(this.matrixBuffer));
-
-            this.mc.worldRenderer.getViewMatrix(this.matrix, partialTick);
-            glUniformMatrix4fv(this.particleShader.getUniform("view"), false, this.matrix.get(this.matrixBuffer));
-
-            if (this.mc.currentScreen instanceof ScreenPhotoMode) {
-                this.matrix.identity();
-            } else {
-                this.mc.worldRenderer.orientCamera(this.matrix.identity(), partialTick).invert();
-            }
-            glUniformMatrix4fv(this.particleShader.getUniform("viewInv"), false, this.matrix.get(this.matrixBuffer));
-
-            this.mc.worldRenderer.getProjectionMatrix(this.matrix, partialTick);
-            glUniformMatrix4fv(this.particleShader.getUniform("projection"), false, this.matrix.get(this.matrixBuffer));
-
-            glUniform1i(this.particleShader.getUniform("texture0"), 0);
-            glUniform1i(this.particleShader.getUniform("texture1"), 1);
-
-            glActiveTexture(GL_TEXTURE1);
-            if (LightmapHelper.isLightmapEnabled()) {
-                glBindTexture(GL_TEXTURE_2D, LightmapHelper.instance.lightmapTexture);
-            } else {
-                this.mc.textureManager.loadTexture("/assets/minecraft/textures/environment/lightmap/disabled.png");
-            }
-            glActiveTexture(GL_TEXTURE0);
+    public void endRenderClouds(float partialTicks) {
 
-            OpenGLHelper.checkError("post enable render particles");
-        }
     }
 
     @Override
-    public @NotNull ParticleTessellator getParticleTessellator() {
-        return this.particleShader.isEnabled() ? this.shaderParticleTessellator : Tessellator.instance;
-    }
-
-    @Override
-    public void endRenderParticles(float partialTicks) {
-        if (this.particleShader.isEnabled()) {
-            glUseProgram(0);
-            GL30.glBindVertexArray(0);
-        }
-    }
+    public void beginRenderParticles(float partialTick) {
 
-    @Override
-    public void endRenderClouds(float partialTicks) {
-        glUseProgram(0);
-        glEnable(GL_ALPHA_TEST);
     }
 
     @Override
-    public void endRenderWorld(float partialTicks) {
-        OpenGLHelper.checkError("pre end render world");
-
-        if (this.finalShader.isEnabled()) {
-            this.gameFramebuffer.bind();
-        } else {
-            glBindFramebuffer(GL_FRAMEBUFFER, 0);
-        }
-
-        if (this.postShader.isEnabled()) {
-            this.postShader.bind();
-
-            glActiveTextureARB(GL_TEXTURE0_ARB);
-            this.worldFramebufferTex.bind();
-            this.postShader.uniformInt("colortex0", 0);
-            glActiveTextureARB(GL_TEXTURE1_ARB);
-            this.worldFramebufferDepth.bind();
-            this.postShader.uniformInt("depthtex0", 1);
-            glActiveTextureARB(GL_TEXTURE0_ARB);
-
-            this.mc.ppm.enabled = true;
-            Shaders.setUniforms(this.mc, this.postShader, partialTicks);
-            this.mc.ppm.enabled = false;
-        } else {
-            glUseProgram(0);
-            this.worldFramebufferTex.bind();
-        }
-
-        glViewport(0, 0, this.fbWidth, this.fbHeight);
-        Shaders.drawFullscreenRect();
-
-        glUseProgram(0);
-        glEnable(GL_ALPHA_TEST);
-
-        OpenGLHelper.checkError("end render world");
+    public void endRenderParticles(float partialTicks) {
     }
 
     public void setupFramebuffer() {
@@ -274,11 +182,12 @@ public class ShadersRenderer implements Renderer {
 
         if (this.fbWidth != this.mc.gameWindow.getWidthPixels() || this.fbHeight != this.mc.gameWindow.getHeightPixels() || this.renderWidth != scaledWidth || this.renderHeight != scaledHeight || !this.gameFramebuffer.isGenerated() || !this.worldFramebuffer.isGenerated()) {
             this.worldFramebuffer.generate();
-            this.worldFramebufferTex.generate();
+            this.worldFramebufferColor.generate();
             this.worldFramebufferDepth.generate();
+            this.worldRenderBufferObject = GL41.glGenRenderbuffers();
             this.gameFramebuffer.generate();
-            this.gameFramebufferTex.generate();
-            this.gameFramebufferDepth.generate();
+            this.gameFramebufferColor.generate();
+            this.gameRenderBufferObject = GL41.glGenRenderbuffers();
 
             this.fbWidth = this.mc.gameWindow.getWidthPixels();
             this.fbHeight = this.mc.gameWindow.getHeightPixels();
@@ -287,72 +196,65 @@ public class ShadersRenderer implements Renderer {
             this.renderHeight = scaledHeight;
 
             boolean filtering = this.mc.gameSettings.renderScale.value.useLinearFiltering;
-            int filterMode = filtering ? GL_LINEAR : GL_NEAREST;
+            int filterMode = filtering ? GL41.GL_LINEAR : GL41.GL_NEAREST;
 
             LOGGER.info("Display: {} x {}, Render: {} x {}", this.fbWidth, this.fbHeight, this.renderWidth, this.renderHeight);
 
             this.worldFramebuffer.bind();
-
-            this.worldFramebufferTex.bind();
-            glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, this.renderWidth, this.renderHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, (ByteBuffer) null);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filterMode);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, filterMode);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
-            glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, this.worldFramebufferTex.id(), 0);
+            this.worldFramebufferColor.bind();
+            GL41.glTexImage2D(GL41.GL_TEXTURE_2D, 0, GL41.GL_RGBA, this.renderWidth, this.renderHeight, 0, GL41.GL_RGBA, GL41.GL_UNSIGNED_BYTE, 0);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MIN_FILTER, filterMode);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MAG_FILTER, filterMode);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_S, GL41.GL_CLAMP_TO_EDGE);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_T, GL41.GL_CLAMP_TO_EDGE);
+            GL41.glFramebufferTexture2D(GL41.GL_FRAMEBUFFER, GL41.GL_COLOR_ATTACHMENT0, GL41.GL_TEXTURE_2D, this.worldFramebufferColor.id(), 0);
 
             this.worldFramebufferDepth.bind();
-            glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, this.renderWidth, this.renderHeight, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_BYTE, (ByteBuffer) null);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filterMode);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, filterMode);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
-            glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, this.worldFramebufferDepth.id(), 0);
+            GL41.glTexImage2D(GL41.GL_TEXTURE_2D, 0, GL41.GL_DEPTH_COMPONENT, this.renderWidth, this.renderHeight, 0, GL41.GL_DEPTH_COMPONENT, GL41.GL_FLOAT, 0);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MIN_FILTER, filterMode);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MAG_FILTER, filterMode);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_S, GL41.GL_CLAMP_TO_EDGE);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_T, GL41.GL_CLAMP_TO_EDGE);
 
-            this.gameFramebuffer.bind();
+            GL41.glFramebufferTexture2D(GL41.GL_FRAMEBUFFER, GL41.GL_DEPTH_ATTACHMENT, GL41.GL_TEXTURE_2D, this.worldFramebufferDepth.id(), 0);
+
+//            GL41.glBindRenderbuffer(GL41.GL_RENDERBUFFER, this.worldRenderBufferObject);
+//            GL41.glRenderbufferStorage(GL41.GL_RENDERBUFFER, GL41.GL_DEPTH24_STENCIL8, this.renderWidth, this.renderHeight);
+//            GL41.glFramebufferRenderbuffer(GL41.GL_FRAMEBUFFER, GL41.GL_DEPTH_STENCIL_ATTACHMENT, GL41.GL_RENDERBUFFER, this.worldRenderBufferObject);
 
-            this.gameFramebufferTex.bind();
-            glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, this.fbWidth, this.fbHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, (ByteBuffer) null);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
-            glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, this.gameFramebufferTex.id(), 0);
-
-            this.gameFramebufferDepth.bind();
-            glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, this.fbWidth, this.fbHeight, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_BYTE, (ByteBuffer) null);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
-            glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, this.gameFramebufferDepth.id(), 0);
-
-            glBindFramebuffer(GL_FRAMEBUFFER, 0);
+            this.gameFramebuffer.bind();
+            this.gameFramebufferColor.bind();
+            GL41.glTexImage2D(GL41.GL_TEXTURE_2D, 0, GL41.GL_RGBA, this.fbWidth, this.fbHeight, 0, GL41.GL_RGBA, GL41.GL_UNSIGNED_BYTE, 0);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MIN_FILTER, filterMode);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_MAG_FILTER, filterMode);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_S, GL41.GL_CLAMP_TO_EDGE);
+            GL41.glTexParameteri(GL41.GL_TEXTURE_2D, GL41.GL_TEXTURE_WRAP_T, GL41.GL_CLAMP_TO_EDGE);
+            GL41.glFramebufferTexture2D(GL41.GL_FRAMEBUFFER, GL41.GL_COLOR_ATTACHMENT0, GL41.GL_TEXTURE_2D, this.gameFramebufferColor.id(), 0);
+
+            GL41.glBindRenderbuffer(GL41.GL_RENDERBUFFER, this.gameRenderBufferObject);
+            GL41.glRenderbufferStorage(GL41.GL_RENDERBUFFER, GL41.GL_DEPTH24_STENCIL8, this.fbWidth, this.fbHeight);
+            GL41.glFramebufferRenderbuffer(GL41.GL_FRAMEBUFFER, GL41.GL_DEPTH_STENCIL_ATTACHMENT, GL41.GL_RENDERBUFFER, this.gameRenderBufferObject);
+
+            GL41.glBindFramebuffer(GL41.GL_FRAMEBUFFER, 0);
         }
     }
 
     public void reload() {
         LOGGER.info("Reloading Shaders...");
 
-        glUseProgram(0);
-        glBindFramebuffer(GL_FRAMEBUFFER, 0);
+        GL41.glUseProgram(0);
+        GL41.glBindFramebuffer(GL41.GL_FRAMEBUFFER, 0);
 
         OpenGLHelper.checkError("pre shader reload");
 
-        this.matrixBuffer = MemoryUtil.memAllocFloat(16);
-
         this.postShader.delete();
         this.finalShader.delete();
-        this.cloudsShader.delete();
-        this.particleShader.delete();
 
         ShaderProvider shaderProvider = getShader();
 
         if (shaderProvider != null) {
-            this.finalShader.compile(shaderProvider, "base");
-            this.postShader.compile(shaderProvider, "post");
-            this.cloudsShader.compile(shaderProvider, "clouds");
-            this.particleShader.compile(shaderProvider, "particle");
+            this.finalShader.compile(shaderProvider, "post/base");
+            this.postShader.compile(shaderProvider, "post/post");
         }
 
         OpenGLHelper.checkError("shader reload");
@@ -361,14 +263,13 @@ public class ShadersRenderer implements Renderer {
     @Override
     public void delete() {
         this.gameFramebuffer.delete();
-        this.gameFramebufferDepth.delete();
-        this.gameFramebufferTex.delete();
+        GL41.glDeleteRenderbuffers(this.gameRenderBufferObject);
+        this.gameFramebufferColor.delete();
 
         this.worldFramebuffer.delete();
+        GL41.glDeleteRenderbuffers(this.worldRenderBufferObject);
+        this.worldFramebufferColor.delete();
         this.worldFramebufferDepth.delete();
-        this.worldFramebufferTex.delete();
-
-        MemoryUtil.memFree(this.matrixBuffer);
     }
 
     @Override
@@ -385,8 +286,8 @@ public class ShadersRenderer implements Renderer {
         }
     }
 
-    public Texture getWorldFramebufferTex() {
-        return this.worldFramebufferTex;
+    public Texture getWorldFramebufferColor() {
+        return this.worldFramebufferColor;
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRenderer.java b/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRenderer.java
index 1741688fe..492e99b17 100644
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRenderer.java
@@ -3,19 +3,17 @@ package net.minecraft.client.render.terrain;
 import java.util.ArrayList;
 import java.util.List;
 
+import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.core.block.entity.TileEntity;
 import net.minecraft.core.world.WorldSource;
 import net.minecraft.core.world.pos.TilePos;
 import org.jetbrains.annotations.NotNull;
 import org.joml.primitives.AABBd;
-import org.joml.primitives.AABBf;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.render.block.model.BlockModel;
 import net.minecraft.client.render.camera.ICamera;
 import net.minecraft.client.render.culling.CameraFrustum;
-import net.minecraft.client.render.entity.EntityRendererItem;
-import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
@@ -25,7 +23,6 @@ public abstract class ChunkRenderer {
     public static int updates = 0;
 
     public World world;
-    protected final int lists;
     public int posX;
     public int posY;
     public int posZ;
@@ -45,27 +42,22 @@ public abstract class ChunkRenderer {
     public int zm;
     public float radius;
     public boolean dirty;
-    public AABBf bb;
+    public AABBd bb;
     public int id;
-    public boolean occlusionVisible;
-    public boolean occlusionQuerying;
-    public int occlusionId;
     public boolean skyLit;
     protected boolean compiled;
     public @NotNull List<@NotNull TileEntity> renderableBlockEntities;
     protected final @NotNull List<@NotNull TileEntity> globalRenderableBlockEntities;
 
-    public ChunkRenderer(@NotNull World world, @NotNull List<@NotNull TileEntity> globalRenderableTileEntities, int x, int y, int z, int size, int lists) {
+    public ChunkRenderer(@NotNull World world, @NotNull List<@NotNull TileEntity> globalRenderableTileEntities, int x, int y, int z, int size) {
         this.visible = false;
         this.empty = new boolean[MAX_RENDER_PASSES];
-        this.occlusionVisible = true;
         this.compiled = false;
         this.renderableBlockEntities = new ArrayList<>();
         this.world = world;
         this.globalRenderableBlockEntities = globalRenderableTileEntities;
         this.sizeX = this.sizeY = this.sizeZ = size;
         this.radius = MathHelper.sqrt_float(this.sizeX * this.sizeX + this.sizeY * this.sizeY + this.sizeZ * this.sizeZ) / 2.0F;
-        this.lists = lists;
         this.posX = -999;
         setPos(x, y, z);
         this.dirty = false;
@@ -87,18 +79,18 @@ public abstract class ChunkRenderer {
             this.yRender = y - this.yRenderOffs;
             this.zRender = z - this.zRenderOffs;
             float f = 6F;
-            this.bb = new AABBf(x - f, y - f,  z - f, (x + this.sizeX) + f, (y + this.sizeY) + f, (z + this.sizeZ) + f);
-            GL11.glNewList(this.lists + MAX_RENDER_PASSES, GL11.GL_COMPILE);
-            EntityRendererItem.renderFlatAABB(new AABBd( this.xRenderOffs - f, this.yRenderOffs - f, this.zRenderOffs - f, (this.xRenderOffs + this.sizeX) + f, (this.yRenderOffs + this.sizeY) + f, (this.zRenderOffs + this.sizeZ) + f));
-            GL11.glEndList();
+            this.bb = new AABBd(x - f, y - f,  z - f, (x + this.sizeX) + f, (y + this.sizeY) + f, (z + this.sizeZ) + f);
             setDirty();
         }
     }
 
     public abstract boolean rebuild(boolean priority);
 
-    public boolean renderBlock(@NotNull Tessellator tessellator, @NotNull WorldSource worldSource, @NotNull BlockModel<?> model, @NotNull TilePos tilePos) {
+    public boolean renderBlock(@NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, @NotNull BlockModel<?> model, @NotNull TilePos tilePos) {
         boolean rendered = false;
+        tessellator.setLightmapCoord1i(LightmapHelper.getLightmapCoord(15, 15));
+        tessellator.setColor4i(255, 255, 255, 255);
+        tessellator.setTextureUV(0.0, 0.0);
         rendered |= model.render(tessellator, worldSource, tilePos);
         if (model.hasOverbright()) {
             rendered |= model.renderOverbright(tessellator, worldSource, tilePos);
@@ -106,10 +98,6 @@ public abstract class ChunkRenderer {
         return rendered;
     }
 
-    protected void translateToPos() {
-        GL11.glTranslatef(this.xRenderOffs, this.yRenderOffs, this.zRenderOffs);
-    }
-
     public float distanceToEntitySquared(Entity entity) {
         float dx = (float) (entity.x - (double) this.xm);
         float dy = (float) (entity.y - (double) this.ym);
@@ -138,23 +126,8 @@ public abstract class ChunkRenderer {
         this.world = null;
     }
 
-    public int getList(int layer) {
-        if (!this.visible) {
-            return -1;
-        }
-        if (!this.empty[layer]) {
-            return this.lists + layer;
-        } else {
-            return -1;
-        }
-    }
-
     public void cull(CameraFrustum frustum, float partialTick) {
-        this.visible = true/*frustum.isVisible(bb, partialTick)*/;
-    }
-
-    public void renderBB() {
-        GL11.glCallList(this.lists + MAX_RENDER_PASSES);
+        this.visible = frustum.isVisible(this.bb, partialTick);
     }
 
     public boolean isEmpty() {
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRendererLegacy.java b/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRendererLegacy.java
deleted file mode 100644
index dbd698ea8..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRendererLegacy.java
+++ /dev/null
@@ -1,137 +0,0 @@
-package net.minecraft.client.render.terrain;
-
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-
-import net.minecraft.client.render.block.model.BlockModelDispatcher;
-import net.minecraft.core.block.Blocks;
-import net.minecraft.core.block.entity.TileEntity;
-import net.minecraft.core.world.pos.TilePos;
-import org.lwjgl.opengl.GL11;
-
-import net.minecraft.client.render.TileEntityRenderDispatcher;
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.block.model.BlockModel;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.core.world.World;
-import net.minecraft.core.world.chunk.Chunk;
-import net.minecraft.core.world.chunk.ChunkCache;
-
-public class ChunkRendererLegacy extends ChunkRenderer {
-
-    public ChunkRendererLegacy(World world, List<TileEntity> globalRenderableTileEntities, int x, int y, int z, int size, int lists) {
-        super(world, globalRenderableTileEntities, x, y, z, size, lists);
-    }
-
-    @Override
-    public boolean rebuild(boolean priority) {
-        if (!this.dirty) {
-            return false;
-        }
-        final int minX = this.posX;
-        final int minY = this.posY;
-        final int minZ = this.posZ;
-        final int maxX = this.posX + this.sizeX;
-        final int maxY = this.posY + this.sizeY;
-        final int maxZ = this.posZ + this.sizeZ;
-
-        final int cacheRadius = 1;
-        final ChunkCache chunkcache = new ChunkCache(this.world, new TilePos(minX - cacheRadius, minY - cacheRadius, minZ - cacheRadius), new TilePos(maxX + cacheRadius, maxY + cacheRadius, maxZ + cacheRadius), priority);
-        if (!chunkcache.allLoaded()) return false;
-
-        for (int i = 0; i < MAX_RENDER_PASSES; i++) {
-            this.empty[i] = true;
-        }
-
-        Chunk.isLit = false;
-        final Set<TileEntity> lastSpecialTileEntities = new HashSet<>(this.renderableBlockEntities);
-        this.renderableBlockEntities.clear();
-        updates++;
-
-        int renderPass = 0;
-        Tessellator tessellator = Tessellator.instance;
-        do {
-            if (renderPass >= MAX_RENDER_PASSES) {
-                break;
-            }
-
-            boolean needsMoreRenderPasses = false;
-            boolean hasRenderedBlock = false;
-            boolean hasStartedDrawing = false;
-
-            TilePos pos = new TilePos(0, 0, 0);
-            for (pos.y = minY; pos.y < maxY; pos.y++) {
-                for (pos.z = minZ; pos.z < maxZ; pos.z++) {
-                    for (pos.x = minX; pos.x < maxX; pos.x++) {
-                        final int blockId = chunkcache.getBlockId(pos);
-                        if (blockId <= 0) {
-                            continue;
-                        }
-                        if (!hasStartedDrawing) {
-                            hasStartedDrawing = true;
-                            GL11.glNewList(this.lists + renderPass, GL11.GL_COMPILE);
-                            GL11.glPushMatrix();
-                            translateToPos();
-                            final float scale = 1.000001F;
-                            GL11.glTranslatef((float) (-this.sizeZ) / 2.0F, (float) (-this.sizeY) / 2.0F, (float) (-this.sizeZ) / 2.0F);
-                            GL11.glScalef(scale, scale, scale);
-                            GL11.glTranslatef((float) this.sizeZ / 2.0F, (float) this.sizeY / 2.0F, (float) this.sizeZ / 2.0F);
-                            tessellator.startDrawingQuads();
-                            tessellator.setTranslation(-this.posX, -this.posY, -this.posZ);
-
-                            if (LightmapHelper.isLightmapEnabled()) {
-                                // Make sure it's active
-                                tessellator.setLightmapCoord(LightmapHelper.getLightmapCoord(15, 15));
-                            }
-                        }
-                        if (renderPass == 0 && Blocks.isEntityTile[blockId]) {
-                            final TileEntity tileentity = chunkcache.getTileEntity(pos);
-                            if (tileentity != null && TileEntityRenderDispatcher.instance.hasRenderer(tileentity)) {
-                                this.renderableBlockEntities.add(tileentity);
-                            }
-                        }
-                        final BlockModel<?> model = BlockModelDispatcher.getInstance().getDispatch(Blocks.blocksList[blockId]);
-                        final int blockRenderPass = model.renderLayer();
-                        if (blockRenderPass != renderPass) {
-                            needsMoreRenderPasses = true;
-                        } else {
-                            if (LightmapHelper.isLightmapEnabled()) {
-                                // Can probably be removed once all block models support the lightmap
-                                tessellator.setLightmapCoord(LightmapHelper.getLightmapCoord(15, 0));
-                            }
-
-                            hasRenderedBlock |= renderBlock(tessellator, this.world, model, pos);
-                        }
-                    }
-                }
-            }
-            if (hasStartedDrawing) {
-                tessellator.draw();
-                GL11.glPopMatrix();
-                GL11.glEndList();
-                tessellator.setTranslation(0.0D, 0.0D, 0.0D);
-            } else {
-                hasRenderedBlock = false;
-            }
-
-            if (hasRenderedBlock) {
-                this.empty[renderPass] = false;
-            }
-            if (!needsMoreRenderPasses) {
-                break;
-            }
-
-            renderPass++;
-        } while (true);
-        HashSet<TileEntity> newSpecialTileEntities = new HashSet<>(this.renderableBlockEntities);
-        newSpecialTileEntities.removeAll(lastSpecialTileEntities);
-        this.globalRenderableBlockEntities.addAll(newSpecialTileEntities);
-        this.renderableBlockEntities.forEach(lastSpecialTileEntities::remove);
-        this.globalRenderableBlockEntities.removeAll(lastSpecialTileEntities);
-        this.skyLit = Chunk.isLit;
-        this.compiled = true;
-        return true;
-    }
-
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRendererMultiDraw.java b/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRendererMultiDraw.java
index 583e9b488..1af75351e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRendererMultiDraw.java
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/ChunkRendererMultiDraw.java
@@ -5,31 +5,26 @@ import java.util.List;
 import java.util.Set;
 
 import net.minecraft.client.render.TileEntityRenderDispatcher;
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.block.model.BlockModel;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
 import net.minecraft.client.render.culling.CameraFrustum;
 import net.minecraft.client.render.terrain.VertexBuffer.Entry;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.client.render.tessellator.TessellatorStandard;
+import net.minecraft.client.render.tessellator.TessellatorTerrainImpl;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.block.entity.TileEntity;
 import net.minecraft.core.world.World;
 import net.minecraft.core.world.chunk.Chunk;
 import net.minecraft.core.world.chunk.ChunkCache;
 import net.minecraft.core.world.pos.TilePos;
+import org.jetbrains.annotations.NotNull;
 
 public class ChunkRendererMultiDraw extends ChunkRenderer {
-
+    private static final @NotNull TessellatorTerrainImpl tessellatorTerrain = new TessellatorTerrainImpl(0x200000);
     public final TerrainRendererMultiDraw terrainRenderer;
     public final Entry[] renderListEntries;
 
-    public ChunkRendererMultiDraw(TerrainRendererMultiDraw terrainRenderer, World world, List<TileEntity> globalRenderableTileEntities, int x, int y, int z, int size, int lists) {
-        super(world, globalRenderableTileEntities, x, y, z, size, lists);
-
-        if (terrainRenderer == null) {
-            throw new NullPointerException("TerrainRenderer is null!");
-        }
+    public ChunkRendererMultiDraw(@NotNull TerrainRendererMultiDraw terrainRenderer, @NotNull World world, @NotNull List<@NotNull TileEntity> globalRenderableTileEntities, int x, int y, int z, int size) {
+        super(world, globalRenderableTileEntities, x, y, z, size);
 
         this.terrainRenderer = terrainRenderer;
         this.renderListEntries = new Entry[terrainRenderer.MAX_RENDER_PASSES];
@@ -62,7 +57,7 @@ public class ChunkRendererMultiDraw extends ChunkRenderer {
 
         updates++;
 
-        TessellatorStandard tessellator = Tessellator.instance;
+        TessellatorTerrainImpl tessellator = tessellatorTerrain;
         for (int renderPass = 0; renderPass < renderPassCount; renderPass++) {
             boolean needsMoreRenderPasses = false;
             boolean hasRenderedBlock = false;
@@ -83,13 +78,6 @@ public class ChunkRendererMultiDraw extends ChunkRenderer {
 
                             RenderRegion region = this.terrainRenderer.getRenderRegionAtBlockPos(this.posX, this.posZ);
                             tessellator.setTranslation(-(region.posX << this.terrainRenderer.REGION_SIZE), 0.0, -(region.posZ << this.terrainRenderer.REGION_SIZE));
-
-                            if (LightmapHelper.isLightmapEnabled()) {
-                                // Make sure it's active
-                                tessellator.setLightmapCoord(LightmapHelper.getLightmapCoord(15, 15));
-                            }
-                            tessellator.setColorRGBA(255, 255, 255, 255);
-                            tessellator.setTextureUV(0.0, 0.0);
                         }
                         if (renderPass == 0 && Blocks.isEntityTile[blockId]) {
                             final TileEntity tileentity = chunkCache.getTileEntity(pos);
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/RenderList.java b/game/client/src/main/java/net/minecraft/client/render/terrain/RenderList.java
index 95afc0524..a76e31e04 100644
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/RenderList.java
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/RenderList.java
@@ -15,149 +15,149 @@ import net.minecraft.core.util.helper.Buffer;
 
 /**
  * 		Can render a lot of objects with a single call
- * <br> All objects need to have the same {@link VertexConfig}
+ * <br> All objects need to have the same {@link VertexConfigStandard}
  * <br> Entries can be toggled visible or invisible quickly
  */
 public class RenderList {
-	private static final CategorizedLogger LOGGER = LogUtils.getLogger();
-	
-	public final VertexBuffer vertexBuffer;
-	
-	private VertexConfig vertexConfig;
-	private boolean vertexConfigLocked = false;
-	
-	private IntBuffer posBuffer;
-	private IntBuffer sizeBuffer;
-	
-	private List<Entry> entryList = new ArrayList<>();
-	private Set<Entry> visibleEntries = new HashSet<>();
-	
-	private boolean visibleEntriesUpdated = true;
-	
-	public RenderList(VertexBuffer vertexBuffer, int capacity) {
-		this.vertexBuffer = vertexBuffer;
-		this.posBuffer = Buffer.createBuffer(capacity * 4).asIntBuffer();
-		this.sizeBuffer = Buffer.createBuffer(capacity * 4).asIntBuffer();
-	}
-	
-	public void draw() {
-		if(entryList.size() == 0) {
+    private static final CategorizedLogger LOGGER = LogUtils.getLogger();
+
+    public final VertexBuffer vertexBuffer;
+
+    private VertexConfig<?> vertexConfig;
+    private boolean vertexConfigLocked = false;
+
+    private IntBuffer posBuffer;
+    private IntBuffer sizeBuffer;
+
+    private final List<Entry> entryList = new ArrayList<>();
+    private final Set<Entry> visibleEntries = new HashSet<>();
+
+    private boolean visibleEntriesUpdated = true;
+
+    public RenderList(VertexBuffer vertexBuffer, int capacity) {
+        this.vertexBuffer = vertexBuffer;
+        this.posBuffer = Buffer.createBuffer(capacity * 4).asIntBuffer();
+        this.sizeBuffer = Buffer.createBuffer(capacity * 4).asIntBuffer();
+    }
+
+    public void draw() {
+        if (this.entryList.isEmpty()) {
 //			System.out.println("No Entries!");
-			return;
-		}
-		
-		if(visibleEntriesUpdated) {
-			int vertexSize = vertexConfig.getVertexSize();
-			
-			posBuffer = expandIfNecessary(posBuffer, visibleEntries.size());
-			sizeBuffer = expandIfNecessary(sizeBuffer, visibleEntries.size());
-			
-			posBuffer.clear();
-			sizeBuffer.clear();
-			
-			for(Entry entry : visibleEntries) {
-				posBuffer.put(entry.position / vertexSize);
-				sizeBuffer.put(entry.size / vertexSize);
-			}
-			
-			posBuffer.flip();
-			sizeBuffer.flip();
-			
-			visibleEntriesUpdated = false;
-		}
-		
-		if(visibleEntries.size() == 0) {
+            return;
+        }
+
+        if (this.visibleEntriesUpdated) {
+            int vertexSize = this.vertexConfig.getVertexSize();
+
+            this.posBuffer = expandIfNecessary(this.posBuffer, this.visibleEntries.size());
+            this.sizeBuffer = expandIfNecessary(this.sizeBuffer, this.visibleEntries.size());
+
+            this.posBuffer.clear();
+            this.sizeBuffer.clear();
+
+            for (Entry entry : this.visibleEntries) {
+                this.posBuffer.put(entry.position / vertexSize);
+                this.sizeBuffer.put(entry.size / vertexSize);
+            }
+
+            this.posBuffer.flip();
+            this.sizeBuffer.flip();
+
+            this.visibleEntriesUpdated = false;
+        }
+
+        if (this.visibleEntries.isEmpty()) {
 //			System.out.println("No Visible Entries!");
-			return;
-		}
-		
+            return;
+        }
+
 //		System.out.println("Rendering " + visibleEntries.size() + " entries");
-		glMultiDrawArrays(vertexConfig.drawMode, posBuffer, sizeBuffer);
-	}
-	
-	public Entry add(VertexData vertexData, boolean visible) {
-		if(vertexData.vertexCount <= 0) {
-			return null;
-		}
-		
-		if(entryList.size() == 0 && !vertexConfigLocked) {
-			this.vertexConfig = vertexData.config.copy();
-		}else {
-			VertexConfig.compareThrow(vertexConfig, vertexData.config);
-		}
-		
-		Entry entry = vertexBuffer.addVertexData(vertexData);
-		entryList.add(entry);
-		
-		if(visible) {
-			visibleEntries.add(entry);
-			visibleEntriesUpdated = true;
-		}
-		
-		return entry;
-	}
-	
-	public void setVisible(Entry entry, boolean visible) {
-		if(entry == null) {
-			throw new NullPointerException();
-		}
-		if(visible) {
-			if(visibleEntries.add(entry)) {
-				visibleEntriesUpdated = true;
-			}
-		}else {
-			if(visibleEntries.remove(entry)) {
-				visibleEntriesUpdated = true;
-			}
-		}
-	}
-	
-	public void lockVertexConfig(VertexConfig vertexConfig) {
-		if(vertexConfig == null) {
-			throw new NullPointerException("VertexConfig cannot be null!");
-		}
-		if(entryList.size() > 0 && !this.vertexConfig.equals(vertexConfig)) {
-			VertexConfig.compareThrow(this.vertexConfig, vertexConfig);
-		}
-		this.vertexConfig = vertexConfig.copy();
-		this.vertexConfigLocked = true;
-	}
-	
-	public boolean remove(Entry entry) {
-		if(entryList.remove(entry)) {
-			vertexBuffer.removeEntry(entry);
-			visibleEntries.remove(entry);
-			visibleEntriesUpdated = true;
-			return true;
-		}
-		return false;
-	}
-	
-	public int size() {
-		return entryList.size();
-	}
-	
-	public int visibleEntryCount() {
-		return visibleEntries.size();
-	}
-	
-	public VertexConfig getVertexConfig() {
-		return vertexConfig;
-	}
-	
-	public boolean isVertexConfigLocked() {
-		return vertexConfigLocked;
-	}
-	
-	public static IntBuffer expandIfNecessary(IntBuffer buffer, int requiredCapacity) {
-		if(buffer.capacity() < requiredCapacity) {
-			int newCapacity = Math.max(buffer.capacity() * 2, requiredCapacity);
-			
-			LOGGER.warn("Expanding RenderList IntBuffer from " + buffer.capacity() + " to " + newCapacity + " ints...");
-			
-			return Buffer.createBuffer(newCapacity << 2).asIntBuffer();
-		}
-		return buffer;
-	}
+        glMultiDrawArrays(this.vertexConfig.drawmode().cap, this.posBuffer, this.sizeBuffer);
+    }
+
+    public Entry add(VertexData vertexData, boolean visible) {
+        if (vertexData.vertexCount <= 0) {
+            return null;
+        }
+
+        if (this.entryList.isEmpty() && !this.vertexConfigLocked) {
+            this.vertexConfig = vertexData.config.copy();
+        } else {
+            VertexConfigStandard.compareThrow(this.vertexConfig, vertexData.config);
+        }
+
+        Entry entry = this.vertexBuffer.addVertexData(vertexData);
+        this.entryList.add(entry);
+
+        if (visible) {
+            this.visibleEntries.add(entry);
+            this.visibleEntriesUpdated = true;
+        }
+
+        return entry;
+    }
+
+    public void setVisible(Entry entry, boolean visible) {
+        if (entry == null) {
+            throw new NullPointerException();
+        }
+        if (visible) {
+            if (this.visibleEntries.add(entry)) {
+                this.visibleEntriesUpdated = true;
+            }
+        } else {
+            if (this.visibleEntries.remove(entry)) {
+                this.visibleEntriesUpdated = true;
+            }
+        }
+    }
+
+    public void lockVertexConfig(VertexConfigStandard vertexConfig) {
+        if (vertexConfig == null) {
+            throw new NullPointerException("VertexConfig cannot be null!");
+        }
+        if (!this.entryList.isEmpty() && !this.vertexConfig.equals(vertexConfig)) {
+            VertexConfigStandard.compareThrow(this.vertexConfig, vertexConfig);
+        }
+        this.vertexConfig = vertexConfig.copy();
+        this.vertexConfigLocked = true;
+    }
+
+    public boolean remove(Entry entry) {
+        if (this.entryList.remove(entry)) {
+            this.vertexBuffer.removeEntry(entry);
+            this.visibleEntries.remove(entry);
+            this.visibleEntriesUpdated = true;
+            return true;
+        }
+        return false;
+    }
+
+    public int size() {
+        return this.entryList.size();
+    }
+
+    public int visibleEntryCount() {
+        return this.visibleEntries.size();
+    }
+
+    public VertexConfig<?> getVertexConfig() {
+        return this.vertexConfig;
+    }
+
+    public boolean isVertexConfigLocked() {
+        return this.vertexConfigLocked;
+    }
+
+    public static IntBuffer expandIfNecessary(IntBuffer buffer, int requiredCapacity) {
+        if (buffer.capacity() < requiredCapacity) {
+            int newCapacity = Math.max(buffer.capacity() * 2, requiredCapacity);
+
+            LOGGER.warn("Expanding RenderList IntBuffer from {} to {} ints...", buffer.capacity(), newCapacity);
+
+            return Buffer.createBuffer(newCapacity << 2).asIntBuffer();
+        }
+        return buffer;
+    }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRenderer.java b/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRenderer.java
index 78b6c85ee..bfafe0bfb 100644
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRenderer.java
@@ -18,6 +18,6 @@ public abstract class TerrainRenderer {
 	
 	public abstract void renderTranslucentTerrain(float partialTicks);
 	
-	public abstract ChunkRenderer createChunkRenderer(World world, List<TileEntity> globalRenderableTileEntities, int x, int y, int z, int size, int lists);
+	public abstract ChunkRenderer createChunkRenderer(World world, List<TileEntity> globalRenderableTileEntities, int x, int y, int z, int size);
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRendererLegacy.java b/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRendererLegacy.java
deleted file mode 100644
index 933f981f3..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRendererLegacy.java
+++ /dev/null
@@ -1,44 +0,0 @@
-package net.minecraft.client.render.terrain;
-
-import static org.lwjgl.opengl.GL11.*;
-
-import java.util.List;
-
-import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.RenderGlobal;
-import net.minecraft.core.block.entity.TileEntity;
-import net.minecraft.core.world.World;
-
-public class TerrainRendererLegacy extends TerrainRenderer {
-
-	public TerrainRendererLegacy(Minecraft minecraft) {
-		super(minecraft);
-	}
-
-	@Override
-	public void renderSolidTerrain(float partialTicks) {
-        mc.renderGlobal.render(mc.activeCamera, 0, partialTicks);
-	}
-
-	@Override
-	public void renderTranslucentTerrain(float partialTicks) {
-		RenderGlobal renderGlobal = mc.renderGlobal;
-		if(mc.gameSettings.fancyGraphics.value == 0) {
-			renderGlobal.render(mc.activeCamera, 1, partialTicks);
-			return;
-		}
-		
-		glColorMask(false, false, false, false);
-		int renderCount = renderGlobal.render(mc.activeCamera, 1, partialTicks);
-		glColorMask(true, true, true, true);
-		
-		if(renderCount > 0) {
-			renderGlobal.renderSameAsLast(1, partialTicks);
-		}
-	}
-
-	@Override
-	public ChunkRenderer createChunkRenderer(World world, List<TileEntity> globalRenderableTileEntities, int x, int y, int z, int size, int lists) {
-		return new ChunkRendererLegacy(world, globalRenderableTileEntities, x, y, z, size, lists);
-	}
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRendererMultiDraw.java b/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRendererMultiDraw.java
index 2a1a6470d..e1df10235 100644
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRendererMultiDraw.java
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/TerrainRendererMultiDraw.java
@@ -1,268 +1,245 @@
 package net.minecraft.client.render.terrain;
 
-import static org.lwjgl.opengl.GL11.*;
-
+import java.util.Arrays;
 import java.util.List;
 
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
 import net.minecraft.core.block.entity.TileEntity;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.camera.ICamera;
 import net.minecraft.client.render.terrain.VertexBuffer.Entry;
-import net.minecraft.client.render.tessellator.TessellatorStandard;
+import net.minecraft.client.render.tessellator.TessellatorTerrainImpl;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
 
 public class TerrainRendererMultiDraw extends TerrainRenderer {
 
-	public final int VERTEX_BUFFER_INITIAL_CAPACITY = 67108864;
-	
-	public final int RENDER_LIST_INITIAL_CAPACITY = 2048;
-	
-	/**
-	 * Exponential Region Size
-	 * Lower Region Size: More Draw Calls, reduced FPS
-	 * Higher Region Size: More Visual Artifacts
-	 */
-	public final int REGION_SIZE = 9;
-	
-	public final int MAX_RENDER_PASSES = 2;
-	
-	/**
-	 * For debugging purposes
-	 */
-	public final boolean DISABLE_REGION_OFFSET = false;
-	
-	public VertexBuffer vertexBuffer;
-	public RegionBuffer regionBuffer;
-	
-	private VertexConfig terrainVertexConfig;
-	
-	int[] drawCalls = new int[MAX_RENDER_PASSES];
-	
-	private double renderPosX;
-	private double renderPosY;
-	private double renderPosZ;
-
-	private double prevSortX;
-	private double prevSortY;
-	private double prevSortZ;
-	
-	public TerrainRendererMultiDraw(Minecraft minecraft) {
-		super(minecraft);
-		
-		vertexBuffer = new VertexBuffer(VERTEX_BUFFER_INITIAL_CAPACITY);
-		regionBuffer = new RegionBuffer(REGION_SIZE);
-	}
-	
-	@Override
-	public void renderSolidTerrain(float partialTicks) {
-		for(int i=0; i < drawCalls.length; i++) {
-			drawCalls[i] = 0;
-		}
-
-		ICamera camera = mc.activeCamera;
-		renderPosX = camera.getX(partialTicks);
-		renderPosY = camera.getY(partialTicks);
-		renderPosZ = camera.getZ(partialTicks);
-
-		double dX = renderPosX - prevSortX;
-		double dY = renderPosY - prevSortY;
-		double dZ = renderPosZ - prevSortZ;
-
-		if(dX * dX + dY * dY + dZ * dZ > 16.0) {
-			prevSortX = renderPosX;
-			prevSortY = renderPosY;
-			prevSortZ = renderPosZ;
-			
-			int x = MathHelper.floor(renderPosX);
-			int y = MathHelper.floor(renderPosY);
-			int z = MathHelper.floor(renderPosZ);
-			
-			mc.renderGlobal.resortChunks(x, y, z);
-		}
-		
-		if(terrainVertexConfig == null) {
-			return;
-		}
-
-		terrainVertexConfig.enableVBO(vertexBuffer.getVbo());
-		
-		List<RenderRegion> regions = regionBuffer.getAllRegions();
-		for(int i=0; i < regions.size(); i++) {
-			RenderRegion region = regions.get(i);
-			// TODO Clear empty regions, but not like this
+    public final int VERTEX_BUFFER_INITIAL_CAPACITY = 67108864;
+
+    public final int RENDER_LIST_INITIAL_CAPACITY = 4096;
+
+    /**
+     * Exponential Region Size
+     * Lower Region Size: More Draw Calls, reduced FPS
+     * Higher Region Size: More Visual Artifacts
+     */
+    public final int REGION_SIZE = 9;
+
+    public final int MAX_RENDER_PASSES = 2;
+
+    public VertexBuffer vertexBuffer;
+    public RegionBuffer regionBuffer;
+
+    private VertexConfig<?> terrainVertexConfig;
+
+    int[] drawCalls = new int[this.MAX_RENDER_PASSES];
+
+    private double renderPosX;
+    private double renderPosY;
+    private double renderPosZ;
+
+    private double prevSortX;
+    private double prevSortY;
+    private double prevSortZ;
+
+    public TerrainRendererMultiDraw(Minecraft minecraft) {
+        super(minecraft);
+
+        this.vertexBuffer = new VertexBuffer(this.VERTEX_BUFFER_INITIAL_CAPACITY);
+        this.regionBuffer = new RegionBuffer(this.REGION_SIZE);
+    }
+
+    @Override
+    public void renderSolidTerrain(float partialTicks) {
+        Arrays.fill(this.drawCalls, 0);
+
+        ICamera camera = this.mc.activeCamera;
+        this.renderPosX = camera.getX(partialTicks);
+        this.renderPosY = camera.getY(partialTicks);
+        this.renderPosZ = camera.getZ(partialTicks);
+
+        double dX = this.renderPosX - this.prevSortX;
+        double dY = this.renderPosY - this.prevSortY;
+        double dZ = this.renderPosZ - this.prevSortZ;
+
+        if (dX * dX + dY * dY + dZ * dZ > 64) {
+            this.prevSortX = this.renderPosX;
+            this.prevSortY = this.renderPosY;
+            this.prevSortZ = this.renderPosZ;
+
+            int x = MathHelper.floor(this.renderPosX);
+            int y = MathHelper.floor(this.renderPosY);
+            int z = MathHelper.floor(this.renderPosZ);
+
+            this.mc.renderGlobal.resortChunks(x, y, z);
+        }
+
+        if (this.terrainVertexConfig == null) {
+            return;
+        }
+
+        this.terrainVertexConfig.enable(this.vertexBuffer.getVao(), this.vertexBuffer.getVbo());
+
+        List<RenderRegion> regions = this.regionBuffer.getAllRegions();
+        for (int i = 0; i < regions.size(); i++) {
+            RenderRegion region = regions.get(i);
+            // TODO Clear empty regions, but not like this
 //			if(!region.hasRenderData()) {
 //				regionBuffer.remove(region);
 //				i--;
 //				continue;
 //			}
 
-			RenderList renderList = region.renderLists[0];
-			if(renderList != null && renderList.size() > 0) {
-				if(!DISABLE_REGION_OFFSET) {
-					glPushMatrix();
-					glTranslated((region.posX << REGION_SIZE) - renderPosX, -renderPosY, (region.posZ << REGION_SIZE) - renderPosZ);
-				} else {
-					glPushMatrix();
-					glTranslated( - renderPosX, -renderPosY, -renderPosZ);
-				}
-				
-				renderList.draw();
-				drawCalls[0]++;
-				
-				if(!DISABLE_REGION_OFFSET) {
-					glPopMatrix();
-				} else {
-					glPopMatrix();
-				}
-			}
-		}
-		
-		terrainVertexConfig.disable();
-	}
-	
-	public void renderAllLists(int renderPass) {
-		List<RenderRegion> regions = regionBuffer.getAllRegions();
-		for(int i=0; i < regions.size(); i++) {
-			RenderRegion region = regions.get(i);
-			RenderList renderList = region.renderLists[renderPass];
-			if(renderList != null && renderList.size() > 0) {
-				if(!DISABLE_REGION_OFFSET) {
-					glPushMatrix();
-					glTranslated((region.posX << REGION_SIZE) - renderPosX, -renderPosY, (region.posZ << REGION_SIZE) - renderPosZ);
-				} else {
-					glPushMatrix();
-					glTranslated( - renderPosX, -renderPosY, -renderPosZ);
-				}
-				
-				renderList.draw();
-				drawCalls[renderPass]++;
-				
-				if(!DISABLE_REGION_OFFSET) {
-					glPopMatrix();
-				} else {
-					glPopMatrix();
-				}
-			}
-		}
-	}
-
-	@Override
-	public void renderTranslucentTerrain(float partialTicks) {
-		if(terrainVertexConfig == null) {
-			return;
-		}
-
-		terrainVertexConfig.enableVBO(vertexBuffer.getVbo());
-		
-		boolean fancy = mc.gameSettings.fancyGraphics.value != 0;
-		
-		if(fancy) {
-			GL11.glColorMask(false, false, false, false);
-		}
-		
-		renderAllLists(1);
-		
-		if(fancy) {
-			GL11.glColorMask(true, true, true, true);
-			if(drawCalls[1] > 0) {
-				renderAllLists(1);
-			}
-		}
-		
-		terrainVertexConfig.disable();
-	}
-	
-	public void chunkRendered(ChunkRendererMultiDraw chunkRenderer, TessellatorStandard tessellator, final int renderPass) {
-		tessellator.drawing = false;
-		VertexConfig config = tessellator.data.config;
-		
-		if(terrainVertexConfig == null) {
-			this.terrainVertexConfig = config.copy();
-		}else {
-			if(!this.terrainVertexConfig.equals(tessellator.data.config)) {
-				List<RenderRegion> allRegions = regionBuffer.getAllRegions();
-				for(int i=0; i < allRegions.size(); i++) {
-					RenderRegion region = allRegions.get(i);
-					if(region.hasRenderData()) {
-						VertexConfig.compareThrow(tessellator.data.config, terrainVertexConfig);
-					}
-					regionBuffer.remove(region);
-					i--;
-				}
-				
-				this.terrainVertexConfig = config.copy();
-			}
-		}
-		
-		RenderList renderList = getOrCreateRenderList(chunkRenderer, renderPass);
-		Entry entry = renderList.add(tessellator.data, chunkRenderer.visible);
-		chunkRenderer.renderListEntries[renderPass] = entry;
-	}
-	
-	public void chunkVisibilityChanged(ChunkRendererMultiDraw chunkRenderer) {
-		RenderRegion region = getRenderRegionAtBlockPos(chunkRenderer.posX, chunkRenderer.posZ);
-		
-		for(int renderPass=0; renderPass < MAX_RENDER_PASSES; renderPass++) {
-			Entry entry = chunkRenderer.renderListEntries[renderPass];
-			if(entry == null) {
-				continue;
-			}
-			RenderList renderList = region.renderLists[renderPass];
-			if(renderList == null) {
-				throw new NullPointerException("Region " + region + " does not have a render list for render pass " + renderPass + "!");
-			}
-			renderList.setVisible(entry, chunkRenderer.visible);
-		}
-	}
-	
-	public void chunkDeleted(ChunkRendererMultiDraw chunkRenderer) {
-		RenderRegion region = getRenderRegionAtBlockPos(chunkRenderer.posX, chunkRenderer.posZ);
-		for(int renderPass=0; renderPass < MAX_RENDER_PASSES; renderPass++) {
-			Entry entry = chunkRenderer.renderListEntries[renderPass];
-			if(entry == null) {
-				continue;
-			}
-			RenderList renderList = region.renderLists[renderPass];
-			if(renderList == null) {
-				throw new NullPointerException("Region " + region + " does not have a render list for render pass " + renderPass + "!");
-			}
-			renderList.remove(entry);
-			chunkRenderer.renderListEntries[renderPass] = null;
-		}
-	}
-	
-	public RenderList getOrCreateRenderList(ChunkRendererMultiDraw chunkRenderer, final int renderPass) {
-		return getOrCreateRenderList(chunkRenderer.posX, chunkRenderer.posZ, renderPass);
-	}
-	
-	public RenderList getOrCreateRenderList(int posX, int posZ, final int renderPass) {
-		RenderRegion region = regionBuffer.getRegionAtBlockPos(posX, posZ);
-		RenderList renderList = region.renderLists[renderPass];
-		if(renderList == null) {
-			renderList = new RenderList(vertexBuffer, RENDER_LIST_INITIAL_CAPACITY);
-			region.renderLists[renderPass] = renderList;
-		}
-		return renderList;
-	}
-
-	@Override
-	public ChunkRenderer createChunkRenderer(World world, List<TileEntity> globalRenderableTileEntities, int x, int y, int z, int size, int lists) {
-		return new ChunkRendererMultiDraw(this, world, globalRenderableTileEntities, x, y, z, size, lists);
-	}
-	
-	public RenderRegion getRenderRegionAtBlockPos(int blockX, int blockZ) {
-		return regionBuffer.getRegionAtBlockPos(blockX, blockZ);
-	}
-	
-	public int getTotalDrawCalls() {
-		int totalDrawCalls = 0;
-		for(int i=0; i < drawCalls.length; i++) {
-			totalDrawCalls += drawCalls[i];
-		}
-		return totalDrawCalls;
-	}
-	
+            RenderList renderList = region.renderLists[0];
+            if (renderList != null && renderList.size() > 0) {
+                GLRenderer.pushFrame();
+                GLRenderer.modelM4f().translate((float) ((region.posX << this.REGION_SIZE) - this.renderPosX), (float) -this.renderPosY, (float) ((region.posZ << this.REGION_SIZE) - this.renderPosZ));
+                GLRenderer.globalSetUniforms(Shaders.WORLD);
+
+                renderList.draw();
+                this.drawCalls[0]++;
+
+                GLRenderer.popFrame();
+            }
+        }
+
+        this.terrainVertexConfig.disable();
+    }
+
+    public void renderAllLists(int renderPass) {
+        List<RenderRegion> regions = this.regionBuffer.getAllRegions();
+        for (int i = 0; i < regions.size(); i++) {
+            RenderRegion region = regions.get(i);
+            RenderList renderList = region.renderLists[renderPass];
+            if (renderList != null && renderList.size() > 0) {
+                GLRenderer.pushFrame();
+                GLRenderer.modelM4f().translate((float) ((region.posX << this.REGION_SIZE) - this.renderPosX), (float) -this.renderPosY, (float) ((region.posZ << this.REGION_SIZE) - this.renderPosZ));
+                GLRenderer.globalSetUniforms(Shaders.WORLD);
+
+                renderList.draw();
+                this.drawCalls[renderPass]++;
+
+                GLRenderer.popFrame();
+            }
+        }
+    }
+
+    @Override
+    public void renderTranslucentTerrain(float partialTicks) {
+        if (this.terrainVertexConfig == null) {
+            return;
+        }
+
+        this.terrainVertexConfig.enable(this.vertexBuffer.getVao(), this.vertexBuffer.getVbo());
+
+        boolean fancy = this.mc.gameSettings.fancyGraphics.value != 0;
+
+        if (fancy) {
+            GLRenderer.setColorMask(false, false, false, false);
+        }
+
+        renderAllLists(1);
+
+        if (fancy) {
+            GLRenderer.setColorMask(true, true, true, true);
+            if (this.drawCalls[1] > 0) {
+                renderAllLists(1);
+            }
+        }
+
+        this.terrainVertexConfig.disable();
+    }
+
+    public void chunkRendered(ChunkRendererMultiDraw chunkRenderer, TessellatorTerrainImpl tessellator, final int renderPass) {
+        tessellator.drawing = false;
+        VertexConfig<?> config = tessellator.data.config;
+
+        if (this.terrainVertexConfig == null) {
+            this.terrainVertexConfig = config.copy();
+        } else {
+            if (!this.terrainVertexConfig.equals(tessellator.data.config)) {
+                List<RenderRegion> allRegions = this.regionBuffer.getAllRegions();
+                for (int i = 0; i < allRegions.size(); i++) {
+                    RenderRegion region = allRegions.get(i);
+                    if (region.hasRenderData()) {
+                        VertexConfigStandard.compareThrow(tessellator.data.config, this.terrainVertexConfig);
+                    }
+                    this.regionBuffer.remove(region);
+                    i--;
+                }
+
+                this.terrainVertexConfig = config.copy();
+            }
+        }
+
+        RenderList renderList = getOrCreateRenderList(chunkRenderer, renderPass);
+        Entry entry = renderList.add(tessellator.data, chunkRenderer.visible);
+        chunkRenderer.renderListEntries[renderPass] = entry;
+    }
+
+    public void chunkVisibilityChanged(ChunkRendererMultiDraw chunkRenderer) {
+        RenderRegion region = getRenderRegionAtBlockPos(chunkRenderer.posX, chunkRenderer.posZ);
+
+        for (int renderPass = 0; renderPass < this.MAX_RENDER_PASSES; renderPass++) {
+            Entry entry = chunkRenderer.renderListEntries[renderPass];
+            if (entry == null) {
+                continue;
+            }
+            RenderList renderList = region.renderLists[renderPass];
+            if (renderList == null) {
+                throw new NullPointerException("Region " + region + " does not have a render list for render pass " + renderPass + "!");
+            }
+            renderList.setVisible(entry, chunkRenderer.visible);
+        }
+    }
+
+    public void chunkDeleted(ChunkRendererMultiDraw chunkRenderer) {
+        RenderRegion region = getRenderRegionAtBlockPos(chunkRenderer.posX, chunkRenderer.posZ);
+        for (int renderPass = 0; renderPass < this.MAX_RENDER_PASSES; renderPass++) {
+            Entry entry = chunkRenderer.renderListEntries[renderPass];
+            if (entry == null) {
+                continue;
+            }
+            RenderList renderList = region.renderLists[renderPass];
+            if (renderList == null) {
+                throw new NullPointerException("Region " + region + " does not have a render list for render pass " + renderPass + "!");
+            }
+            renderList.remove(entry);
+            chunkRenderer.renderListEntries[renderPass] = null;
+        }
+    }
+
+    public RenderList getOrCreateRenderList(ChunkRendererMultiDraw chunkRenderer, final int renderPass) {
+        return getOrCreateRenderList(chunkRenderer.posX, chunkRenderer.posZ, renderPass);
+    }
+
+    public RenderList getOrCreateRenderList(int posX, int posZ, final int renderPass) {
+        RenderRegion region = this.regionBuffer.getRegionAtBlockPos(posX, posZ);
+        RenderList renderList = region.renderLists[renderPass];
+        if (renderList == null) {
+            renderList = new RenderList(this.vertexBuffer, this.RENDER_LIST_INITIAL_CAPACITY);
+            region.renderLists[renderPass] = renderList;
+        }
+        return renderList;
+    }
+
+    @Override
+    public ChunkRenderer createChunkRenderer(World world, List<TileEntity> globalRenderableTileEntities, int x, int y, int z, int size) {
+        return new ChunkRendererMultiDraw(this, world, globalRenderableTileEntities, x, y, z, size);
+    }
+
+    public RenderRegion getRenderRegionAtBlockPos(int blockX, int blockZ) {
+        return this.regionBuffer.getRegionAtBlockPos(blockX, blockZ);
+    }
+
+    public int getTotalDrawCalls() {
+        int totalDrawCalls = 0;
+        for (int i = 0; i < this.drawCalls.length; i++) {
+            totalDrawCalls += this.drawCalls[i];
+        }
+        return totalDrawCalls;
+    }
+
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/VertexBuffer.java b/game/client/src/main/java/net/minecraft/client/render/terrain/VertexBuffer.java
index 6b2ed0a73..f75ee716b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/VertexBuffer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/VertexBuffer.java
@@ -2,8 +2,6 @@ package net.minecraft.client.render.terrain;
 
 import static org.lwjgl.opengl.GL15.*;
 
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
 import java.util.ArrayList;
 import java.util.List;
 
@@ -12,6 +10,7 @@ import com.mojang.logging.LogUtils;
 import org.lwjgl.opengl.GL31;
 
 import net.minecraft.client.render.OpenGLHelper;
+import org.lwjgl.opengl.GL41;
 
 /**
  * 		A large buffer that contains vertex data
@@ -21,6 +20,7 @@ import net.minecraft.client.render.OpenGLHelper;
 public class VertexBuffer {
 	public static final CategorizedLogger LOGGER = LogUtils.getLogger();
 	private int vbo;
+	private final int vao;
 	private long capacity;
 	
 	public List<Entry> entries = new ArrayList<>();
@@ -29,10 +29,11 @@ public class VertexBuffer {
 	
 	public VertexBuffer(long initialCapacity) {
 		this.capacity = initialCapacity;
-		
-		vbo = glGenBuffers();
-		glBindBuffer(GL_ARRAY_BUFFER, vbo);
-		glBufferData(GL_ARRAY_BUFFER, capacity, GL_STATIC_DRAW);
+
+        this.vbo = glGenBuffers();
+        this.vao = GL41.glGenVertexArrays();
+		glBindBuffer(GL_ARRAY_BUFFER, this.vbo);
+		glBufferData(GL_ARRAY_BUFFER, this.capacity, GL_STATIC_DRAW);
 		glBindBuffer(GL_ARRAY_BUFFER, 0);
 	}
 	
@@ -42,7 +43,7 @@ public class VertexBuffer {
 		}
 		
 		// If the buffer is empty, just put it at the start
-		if(entries.size() == 0) {
+		if(this.entries.isEmpty()) {
 			return insertAtIndex(vertexData, 0);
 		}
 		
@@ -50,8 +51,8 @@ public class VertexBuffer {
 		
 		// If there is a single element in the buffer, check if there is enough space in front of it
 		// If not put it behind the other element
-		if(entries.size() == 1) {
-			Entry entry = entries.get(0);
+		if(this.entries.size() == 1) {
+			Entry entry = this.entries.get(0);
 			if(entry.position > bytes) {
 				return insertAtIndex(vertexData, 0);
 			}else {
@@ -60,9 +61,9 @@ public class VertexBuffer {
 		}
 		
 		// Check between every single element for a large enough gap
-		for(int i = 0; i < entries.size() - 1; i++) {
-			Entry entry = entries.get(i);
-			Entry nextEntry = entries.get(i + 1);
+		for(int i = 0; i < this.entries.size() - 1; i++) {
+			Entry entry = this.entries.get(i);
+			Entry nextEntry = this.entries.get(i + 1);
 			
 			int availableSpace = nextEntry.position - (entry.position + entry.size);
 			if(availableSpace > bytes) {
@@ -71,7 +72,7 @@ public class VertexBuffer {
 		}
 		
 		// Put it all the way at the end
-		return insertAtIndex(vertexData, entries.size());
+		return insertAtIndex(vertexData, this.entries.size());
 	}
 	
 	private Entry insertAtIndex(VertexData vertexData, int listIndex) {
@@ -79,24 +80,24 @@ public class VertexBuffer {
 		int bytes = vertexData.buffer.position();
 		
 		if(listIndex > 0) {
-			Entry prev = entries.get(listIndex - 1);
+			Entry prev = this.entries.get(listIndex - 1);
 			pos = prev.position + prev.size;
 		}
 		
-		if(pos + bytes >= capacity) {
+		if(pos + bytes >= this.capacity) {
 			expandVBO();
 		}
 		
 		Entry entry = new Entry(pos, bytes);
 		
 		if(listIndex > 0) {
-			Entry previousEntry = entries.get(listIndex - 1);
+			Entry previousEntry = this.entries.get(listIndex - 1);
 			if(previousEntry.position + previousEntry.size > pos) {
 				throw new RuntimeException("Entry collision: " + entry + " and " + previousEntry);
 			}
 		}
-		if(listIndex < entries.size() - 1) {
-			Entry nextEntry = entries.get(listIndex + 1);
+		if(listIndex < this.entries.size() - 1) {
+			Entry nextEntry = this.entries.get(listIndex + 1);
 			if(nextEntry.position <= pos + bytes) {
 				throw new RuntimeException("Entry collision: " + entry + " and " + nextEntry);
 			}
@@ -104,11 +105,11 @@ public class VertexBuffer {
 		
 		vertexData.buffer.flip();
 		
-		glBindBuffer(GL_ARRAY_BUFFER, vbo);
+		glBindBuffer(GL_ARRAY_BUFFER, this.vbo);
 		glBufferSubData(GL_ARRAY_BUFFER, pos, vertexData.buffer);
 		glBindBuffer(GL_ARRAY_BUFFER, 0);
-		
-		entries.add(listIndex, entry);
+
+        this.entries.add(listIndex, entry);
 		
 		return entry;
 	}
@@ -116,7 +117,7 @@ public class VertexBuffer {
 	private void expandVBO() {
 		final long prevCapacity = this.capacity;
 		long newCapacity = this.capacity * 2L;
-		if(newCapacity < capacity) {
+		if(newCapacity < this.capacity) {
 			// future proof
 			throw new RuntimeException();
 		}
@@ -130,52 +131,35 @@ public class VertexBuffer {
 		glBufferData(GL_ARRAY_BUFFER, newCapacity, GL_STATIC_DRAW);
 		
 		OpenGLHelper.checkError("create expand buffer");
-		
-		if(OpenGLHelper.gl31) {
-			glBindBuffer(GL31.GL_COPY_READ_BUFFER, this.vbo);
-			glBindBuffer(GL31.GL_COPY_WRITE_BUFFER, newBuffer);
-			
-			GL31.glCopyBufferSubData(GL31.GL_COPY_READ_BUFFER, GL31.GL_COPY_WRITE_BUFFER, 0, 0, this.capacity);
-			
-			glBindBuffer(GL31.GL_COPY_READ_BUFFER, 0);
-			glBindBuffer(GL31.GL_COPY_WRITE_BUFFER, 0);	
-		}else {
-			// confirmed to work on trash hardware
-			
-			int iPrevCapacity = (int) prevCapacity;
-			int iNewCapacity = (int) newCapacity;
 
-			if(iPrevCapacity < 0) throw new RuntimeException("Previous capacity < 0");
-			if(iNewCapacity < 0) throw new RuntimeException("New capacity < 0");
-			if(iNewCapacity < iPrevCapacity) throw new RuntimeException("New capacity < previous capacity: " + iNewCapacity + " < " + iPrevCapacity);
-			
-			ByteBuffer oldData = ByteBuffer.allocateDirect(iPrevCapacity).order(ByteOrder.nativeOrder());
-			
-			glBindBuffer(GL_ARRAY_BUFFER, this.vbo);
-			glGetBufferSubData(GL_ARRAY_BUFFER, 0L, oldData);
-			
-			oldData.position(0);
-			
-			glBindBuffer(GL_ARRAY_BUFFER, newBuffer);
-			glBufferSubData(GL_ARRAY_BUFFER, 0L, oldData);
-		}
-		
-		OpenGLHelper.checkError("copy buffer");
+        glBindBuffer(GL31.GL_COPY_READ_BUFFER, this.vbo);
+        glBindBuffer(GL31.GL_COPY_WRITE_BUFFER, newBuffer);
+
+        GL31.glCopyBufferSubData(GL31.GL_COPY_READ_BUFFER, GL31.GL_COPY_WRITE_BUFFER, 0, 0, this.capacity);
+
+        glBindBuffer(GL31.GL_COPY_READ_BUFFER, 0);
+        glBindBuffer(GL31.GL_COPY_WRITE_BUFFER, 0);
+
+        OpenGLHelper.checkError("copy buffer");
 		
 		this.capacity = newCapacity;
 		this.vbo = newBuffer;
 	}
 	
 	public boolean removeEntry(Entry entry) {
-		return entries.remove(entry);
+		return this.entries.remove(entry);
 	}
 	
 	public int getVbo() {
-		return vbo;
+		return this.vbo;
+	}
+
+	public int getVao() {
+		return this.vao;
 	}
 	
 	public int entryCount() {
-		return entries.size();
+		return this.entries.size();
 	}
 	
 	/**
@@ -186,7 +170,7 @@ public class VertexBuffer {
 		public final int position;
 		public final int size;
 		
-		private final int hashCode = entryHashCounter++;
+		private final int hashCode = VertexBuffer.this.entryHashCounter++;
 		
 		public Entry(int position, int size) {
 			this.position = position;
@@ -195,12 +179,12 @@ public class VertexBuffer {
 		
 		@Override
 		public String toString() {
-			return "VertexBufferEntry[position: " + position + ", size: " + size + "]";
+			return "VertexBufferEntry[position: " + this.position + ", size: " + this.size + "]";
 		}
 		
 		@Override
 		public int hashCode() {
-			return hashCode;
+			return this.hashCode;
 		}
 		
 	}
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/VertexConfig.java b/game/client/src/main/java/net/minecraft/client/render/terrain/VertexConfig.java
index 296e48a1d..da09d570e 100644
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/VertexConfig.java
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/VertexConfig.java
@@ -1,242 +1,12 @@
 package net.minecraft.client.render.terrain;
 
-import static org.lwjgl.opengl.GL20.*;
-
-import java.nio.ByteBuffer;
-import java.util.ArrayList;
-import java.util.List;
-
-import com.b100.json.element.JsonObject;
-
-public class VertexConfig {
-	
-	public int drawMode;
-	public boolean enableColor = false;
-	public boolean enableTexture = false;
-	public boolean enableNormal = false;
-	public boolean enableLightmap = false;
-	public final List<VertexAttribute> attributes = new ArrayList<>();
-	
-	public void enableDirect(ByteBuffer buffer) {
-		int vertexSize = getVertexSize();
-		int offset = 0;
-		
-		buffer.position(offset);
-		glEnableClientState(GL_VERTEX_ARRAY);
-		glVertexPointer(3, GL_FLOAT, vertexSize, buffer);
-		offset += 12;
-		
-		if(enableColor) {
-			buffer.position(offset);
-			glColorPointer(4, GL_UNSIGNED_BYTE, vertexSize, buffer);
-			glEnableClientState(GL_COLOR_ARRAY);
-			offset += 4;
-		}else {
-			glDisableClientState(GL_COLOR_ARRAY);
-		}
-		
-		if(enableTexture) {
-			buffer.position(offset);
-			glTexCoordPointer(2, GL_FLOAT, vertexSize, buffer);
-			glEnableClientState(GL_TEXTURE_COORD_ARRAY);
-			offset += 8;
-		}else {
-			glDisableClientState(GL_TEXTURE_COORD_ARRAY);
-		}
-		
-		if(enableNormal) {
-			buffer.position(offset);
-			glNormalPointer(GL_BYTE, vertexSize, buffer);
-			glEnableClientState(GL_NORMAL_ARRAY);
-			offset += 3;
-		}else {
-			glDisableClientState(GL_NORMAL_ARRAY);
-		}
-		
-		glClientActiveTexture(GL_TEXTURE1);
-		if(enableLightmap) {
-			buffer.position(offset);
-			glTexCoordPointer(2, GL_SHORT, vertexSize, buffer);
-			glEnableClientState(GL_TEXTURE_COORD_ARRAY);
-			offset += 4;
-		}else {
-			glDisableClientState(GL_TEXTURE_COORD_ARRAY);
-		}
-		glClientActiveTexture(GL_TEXTURE0);
-		
-		for(int i=0; i < attributes.size(); i++) {
-			VertexAttribute attrib = attributes.get(i);
-			
-			buffer.position(offset);
-			glEnableVertexAttribArray(attrib.id);
-			glVertexAttribPointer(attrib.id, attrib.getSize(), attrib.type, false, vertexSize, buffer);
-			offset += attrib.getTypeSize();
-		}
-	}
-	
-	public void enableVBO(int vbo) {
-		glBindBuffer(GL_ARRAY_BUFFER, vbo);
-		
-		int vertexSize = getVertexSize();
-		int offset = 0;
-		
-		glEnableClientState(GL_VERTEX_ARRAY);
-		glVertexPointer(3, GL_FLOAT, vertexSize, offset);
-		offset += 12;
-		
-		if(enableColor) {
-			glColorPointer(4, GL_UNSIGNED_BYTE, vertexSize, offset);
-			glEnableClientState(GL_COLOR_ARRAY);
-			offset += 4;
-		}else {
-			glDisableClientState(GL_COLOR_ARRAY);
-		}
-		
-		if(enableTexture) {
-			glTexCoordPointer(2, GL_FLOAT, vertexSize, offset);
-			glEnableClientState(GL_TEXTURE_COORD_ARRAY);
-			offset += 8;
-		}else {
-			glDisableClientState(GL_TEXTURE_COORD_ARRAY);
-		}
-		
-		if(enableNormal) {
-			glNormalPointer(GL_BYTE, vertexSize, offset);
-			glEnableClientState(GL_NORMAL_ARRAY);
-			offset += 3;
-		}else {
-			glDisableClientState(GL_NORMAL_ARRAY);
-		}
-		
-		if(enableLightmap) {
-			glClientActiveTexture(GL_TEXTURE1);
-			glTexCoordPointer(2, GL_SHORT, vertexSize, offset);
-			glEnableClientState(GL_TEXTURE_COORD_ARRAY);
-			offset += 4;
-			glClientActiveTexture(GL_TEXTURE0);
-		}
-		
-		for(int i=0; i < attributes.size(); i++) {
-			VertexAttribute attrib = attributes.get(i);
-			
-			glEnableVertexAttribArray(attrib.id);
-			glVertexAttribPointer(attrib.id, attrib.getSize(), attrib.type, false, vertexSize, offset);
-			offset += attrib.getTypeSize();
-		}
-	}
-	
-	public void disable() {
-		if(enableLightmap) {
-			glClientActiveTexture(GL_TEXTURE1);
-			glDisableClientState(GL_TEXTURE_COORD_ARRAY);
-			glClientActiveTexture(GL_TEXTURE0);
-		}
-		
-		glBindBuffer(GL_ARRAY_BUFFER, 0);
-		for(int i=0; i < attributes.size(); i++) {
-			VertexAttribute attrib = attributes.get(i);
-			glDisableVertexAttribArray(attrib.id);
-		}
-	}
-	
-	public int getVertexSize() {
-		int size = 12;
-		
-		if(enableColor) size += 4;
-		if(enableTexture) size += 8;
-		if(enableNormal) size += 3;
-		if(enableLightmap) size += 4;
-		
-		for(int i=0; i < attributes.size(); i++) {
-			size += attributes.get(i).getTypeSize();
-		}
-		
-		return size;
-	}
-	
-	public VertexConfig copy() {
-		VertexConfig copy = new VertexConfig();
-		copy.drawMode = drawMode;
-		copy.enableColor = enableColor;
-		copy.enableTexture = enableTexture;
-		copy.enableNormal = enableNormal;
-		copy.enableLightmap = enableLightmap;
-		copy.attributes.addAll(attributes);
-		return copy;
-	}
-	
-	@Override
-	public boolean equals(Object obj) {
-		if(obj instanceof VertexConfig) {
-			return compare(this, (VertexConfig) obj) == 0;
-		}
-		return false;
-	}
-	
-	/**
-	 * Only used for debugging
-	 */
-	public JsonObject toJson() {
-		JsonObject object = new JsonObject();
-		object.set("drawMode", drawMode);
-		object.set("enableColor", enableColor);
-		object.set("enableTexcoord", enableTexture);
-		object.set("enableNormal", enableNormal);
-		object.set("enableLightmap", enableLightmap);
-		if(attributes.size() > 0) {
-			JsonObject attribsJson = new JsonObject();
-			
-			attribsJson.set("size", attributes.size());
-			
-			for(int i=0; i < attributes.size(); i++) {
-				VertexAttribute attribute = attributes.get(i);
-				JsonObject attribObject = new JsonObject();
-				
-				attribObject.set("id", attribute.id);
-				attribObject.set("type", attribute.type);
-				
-				attribsJson.set(attribute.name, attribObject);
-			}
-			
-			object.set("attribs", attribsJson);
-		}
-		return object;
-	}
-	
-	public static int compare(VertexConfig c1, VertexConfig c2) {
-		if(c1.drawMode != c2.drawMode) return 1;
-		if(c1.enableColor != c2.enableColor) return 2;
-		if(c1.enableTexture != c2.enableTexture) return 3;
-		if(c1.enableNormal != c2.enableNormal) return 4;
-		if(c1.enableLightmap != c2.enableLightmap) return 4;
-		
-		if(c1.attributes.size() != c2.attributes.size()) {
-			return 5;
-		}
-		
-		for(int i=0; i < c1.attributes.size(); i++) {
-			VertexAttribute attrib1 = c1.attributes.get(i);
-			VertexAttribute attrib2 = c2.attributes.get(i);
-			int compare = VertexAttribute.compare(attrib1, attrib2); 
-			if(compare != 0) {
-				return (6 + i) * 1000 + compare;
-			}
-		}
-		
-		return 0;
-	}
-	
-	public static void compareThrow(VertexConfig config1, VertexConfig config2) {
-		int compare = compare(config1, config2);
-		if(compare != 0) {
-			System.err.println("VertexConfig Mismatch:\n" + config1 + "\n!=\n" + config2);
-			throw new RuntimeException("VertexConfig mismatch " + compare + "!");
-		}	
-	}
-	
-	@Override
-	public String toString() {
-		return toJson().toString();
-	}
-
+import net.minecraft.client.render.renderer.DrawMode;
+import org.jetbrains.annotations.NotNull;
+
+public interface VertexConfig<T extends VertexConfig<T>> {
+    @NotNull DrawMode drawmode();
+    void enable(int vao, int vbo);
+    void disable();
+    int getVertexSize();
+    @NotNull T copy();
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/VertexConfigStandard.java b/game/client/src/main/java/net/minecraft/client/render/terrain/VertexConfigStandard.java
new file mode 100644
index 000000000..2b514974c
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/VertexConfigStandard.java
@@ -0,0 +1,189 @@
+package net.minecraft.client.render.terrain;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import com.b100.json.element.JsonObject;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.Tessellator;
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.opengl.GL41;
+
+public class VertexConfigStandard implements VertexConfig<VertexConfigStandard> {
+	
+	public @NotNull DrawMode drawMode = Tessellator.QUAD_EMULATION ? DrawMode.TRIANGLES : DrawMode.QUADS;
+	public boolean enableColor = false;
+	public boolean enableTexture = false;
+	public boolean enableNormal = false;
+	public boolean enableLightmap = false;
+	public final List<VertexAttribute> attributes = new ArrayList<>();
+
+	@Override
+	public @NotNull DrawMode drawmode() {
+		return this.drawMode;
+	}
+
+	public void enable(int vao, int vbo) {
+		GL41.glBindVertexArray(vao);
+		GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, vbo);
+		
+		int vertexSize = getVertexSize();
+		int offset = 0;
+		GL41.glVertexAttribPointer(0, 3, GL41.GL_FLOAT, false, vertexSize, offset); offset += 3 * Float.BYTES;    // Pos
+		GL41.glEnableVertexAttribArray(0);
+		if (this.enableColor) {
+			GL41.glVertexAttribPointer(1, 4, GL41.GL_UNSIGNED_BYTE, true, vertexSize, offset); offset += 4;    // Color
+			GL41.glEnableVertexAttribArray(1);
+		} else {
+			GL41.glVertexAttrib4f(1, 1f, 1f, 1f, 1f);
+		}
+		if (this.enableTexture) {
+			GL41.glVertexAttribPointer(2, 2, GL41.GL_FLOAT, false, vertexSize, offset); offset += 2 * Float.BYTES;    // UV
+			GL41.glEnableVertexAttribArray(2);
+		}
+		if (this.enableLightmap) {
+			GL41.glVertexAttribPointer(3, 2, GL41.GL_UNSIGNED_BYTE, true, vertexSize, offset); offset += 2;    // Lightmap
+			GL41.glEnableVertexAttribArray(3);
+		} else {
+			GL41.glVertexAttrib2f(3, GLRenderer.getLightmapBlock(), GLRenderer.getLightmapSky());
+		}
+		if (this.enableNormal) {
+			GL41.glVertexAttribPointer(4, 3, GL41.GL_BYTE, true, vertexSize, offset); offset += 3;    // Normal
+			GL41.glEnableVertexAttribArray(4);
+		} else {
+			GL41.glVertexAttrib3f(4, 0, -1, 0);
+		}
+		
+		for(int i = 0; i < this.attributes.size(); i++) {
+			VertexAttribute attrib = this.attributes.get(i);
+			
+			GL41.glEnableVertexAttribArray(attrib.id);
+			GL41.glVertexAttribPointer(attrib.id, attrib.getSize(), attrib.type, false, vertexSize, offset);
+			offset += attrib.getTypeSize();
+		}
+	}
+	
+	public void disable() {
+		GL41.glDisableVertexAttribArray(0);
+		GL41.glDisableVertexAttribArray(1);
+		GL41.glDisableVertexAttribArray(2);
+		GL41.glDisableVertexAttribArray(3);
+		GL41.glDisableVertexAttribArray(4);
+
+		for(int i = 0; i < this.attributes.size(); i++) {
+			VertexAttribute attrib = this.attributes.get(i);
+			GL41.glDisableVertexAttribArray(attrib.id);
+		}
+		GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, 0);
+		GL41.glBindVertexArray(0);
+	}
+	
+	public int getVertexSize() {
+		int size = Float.BYTES * 3;
+		
+		if(this.enableColor) {
+			size += 4;
+		}
+		if(this.enableTexture) {
+			size += Float.BYTES * 2;
+		}
+		if(this.enableNormal) {
+			size += 3;
+		}
+		if(this.enableLightmap) {
+			size += 2;
+		}
+		
+		for(int i = 0; i < this.attributes.size(); i++) {
+			size += this.attributes.get(i).getTypeSize();
+		}
+		
+		return size;
+	}
+	
+	public @NotNull VertexConfigStandard copy() {
+		VertexConfigStandard copy = new VertexConfigStandard();
+		copy.drawMode = this.drawMode;
+		copy.enableColor = this.enableColor;
+		copy.enableTexture = this.enableTexture;
+		copy.enableNormal = this.enableNormal;
+		copy.enableLightmap = this.enableLightmap;
+		copy.attributes.addAll(this.attributes);
+		return copy;
+	}
+	
+	@Override
+	public boolean equals(Object obj) {
+		if(obj instanceof VertexConfigStandard) {
+			return compare(this, (VertexConfigStandard) obj) == 0;
+		}
+		return false;
+	}
+	
+	/**
+	 * Only used for debugging
+	 */
+	public JsonObject toJson() {
+		JsonObject object = new JsonObject();
+		object.set("drawMode", this.drawMode.name());
+		object.set("enableColor", this.enableColor);
+		object.set("enableTexcoord", this.enableTexture);
+		object.set("enableNormal", this.enableNormal);
+		object.set("enableLightmap", this.enableLightmap);
+		if(!this.attributes.isEmpty()) {
+			JsonObject attribsJson = new JsonObject();
+			
+			attribsJson.set("size", this.attributes.size());
+			
+			for(int i = 0; i < this.attributes.size(); i++) {
+				VertexAttribute attribute = this.attributes.get(i);
+				JsonObject attribObject = new JsonObject();
+				
+				attribObject.set("id", attribute.id);
+				attribObject.set("type", attribute.type);
+				
+				attribsJson.set(attribute.name, attribObject);
+			}
+			
+			object.set("attribs", attribsJson);
+		}
+		return object;
+	}
+
+	public static int compare(VertexConfigStandard c1, VertexConfigStandard c2) {
+		if(c1.drawMode != c2.drawMode) return 1;
+		if(c1.enableColor != c2.enableColor) return 2;
+		if(c1.enableTexture != c2.enableTexture) return 3;
+		if(c1.enableNormal != c2.enableNormal) return 4;
+		if(c1.enableLightmap != c2.enableLightmap) return 4;
+
+		if(c1.attributes.size() != c2.attributes.size()) {
+			return 5;
+		}
+
+		for(int i=0; i < c1.attributes.size(); i++) {
+			VertexAttribute attrib1 = c1.attributes.get(i);
+			VertexAttribute attrib2 = c2.attributes.get(i);
+			int compare = VertexAttribute.compare(attrib1, attrib2);
+			if(compare != 0) {
+				return (6 + i) * 1000 + compare;
+			}
+		}
+
+		return 0;
+	}
+
+	public static void compareThrow(VertexConfig<?> config1, VertexConfig<?> config2) {
+		if(!config1.equals(config2)) {
+			System.err.println("VertexConfig Mismatch:\n" + config1 + "\n!=\n" + config2);
+			throw new RuntimeException("VertexConfig mismatch " + config1 + " " + config2 + "!");
+		}
+	}
+
+	@Override
+	public String toString() {
+		return toJson().toString();
+	}
+
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/terrain/VertexData.java b/game/client/src/main/java/net/minecraft/client/render/terrain/VertexData.java
index 124c03505..523b0f409 100644
--- a/game/client/src/main/java/net/minecraft/client/render/terrain/VertexData.java
+++ b/game/client/src/main/java/net/minecraft/client/render/terrain/VertexData.java
@@ -1,36 +1,18 @@
 package net.minecraft.client.render.terrain;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.nio.ByteBuffer;
 
 import net.minecraft.core.util.helper.Buffer;
 
 public class VertexData {
-	
-	public ByteBuffer buffer;
-	
-	public VertexConfig config = new VertexConfig();
-	
-	public int vertexCount;
-	
-	public VertexData(int size) {
-		buffer = Buffer.createBuffer(size);
-	}
-	
-	public void drawAll() {
-		draw(0, vertexCount);
-	}
-	
-	public void draw(int first, int count) {
-		if(count == 0) {
-			return;
-		}
-		
-		buffer.limit(config.getVertexSize() * vertexCount);
-		config.enableDirect(buffer);
-		glDrawArrays(config.drawMode, first, count);
-		config.disable();
-	}
 
+    public ByteBuffer buffer;
+
+    public VertexConfig<?> config = new VertexConfigStandard();
+
+    public int vertexCount;
+
+    public VertexData(int size) {
+        this.buffer = Buffer.createBuffer(size);
+    }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/RenderBuffer.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/RenderBuffer.java
new file mode 100644
index 000000000..4bfff5c5a
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/RenderBuffer.java
@@ -0,0 +1,14 @@
+package net.minecraft.client.render.tessellator;
+
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.terrain.VertexConfig;
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.opengl.GL41;
+
+public record RenderBuffer(int vao, int vbo, int offset, int count, @NotNull DrawMode drawMode) {
+
+    public void delete() {
+        GL41.glDeleteBuffers(vbo());
+        GL41.glDeleteVertexArrays(vao());
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/ShaderParticleTessellator.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/ShaderParticleTessellator.java
deleted file mode 100644
index 66df7d808..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/tessellator/ShaderParticleTessellator.java
+++ /dev/null
@@ -1,232 +0,0 @@
-package net.minecraft.client.render.tessellator;
-
-import com.mojang.logging.LogUtils;
-import net.minecraft.client.render.LightmapHelper;
-import net.minecraft.client.render.camera.ICamera;
-import net.minecraft.core.util.helper.Buffer;
-import net.minecraft.core.util.helper.MathHelper;
-import org.jetbrains.annotations.NotNull;
-import org.slf4j.Logger;
-
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-
-import static org.lwjgl.opengl.GL11.GL_FLOAT;
-import static org.lwjgl.opengl.GL11.GL_POINTS;
-import static org.lwjgl.opengl.GL11.GL_UNSIGNED_BYTE;
-import static org.lwjgl.opengl.GL11.glDrawArrays;
-import static org.lwjgl.opengl.GL15.GL_ARRAY_BUFFER;
-import static org.lwjgl.opengl.GL15.GL_STATIC_DRAW;
-import static org.lwjgl.opengl.GL15.GL_STREAM_DRAW;
-import static org.lwjgl.opengl.GL15.glBindBuffer;
-import static org.lwjgl.opengl.GL15.glBufferData;
-import static org.lwjgl.opengl.GL15.glGenBuffers;
-import static org.lwjgl.opengl.GL20.glDisableVertexAttribArray;
-import static org.lwjgl.opengl.GL20.glEnableVertexAttribArray;
-import static org.lwjgl.opengl.GL20.glVertexAttrib2f;
-import static org.lwjgl.opengl.GL20.glVertexAttrib4f;
-import static org.lwjgl.opengl.GL20.glVertexAttribPointer;
-
-public class ShaderParticleTessellator implements ParticleTessellator {
-    private static final Logger LOGGER = LogUtils.getLogger();
-    private boolean drawing = false;
-    private ByteBuffer buffer;
-
-    private int count = 0;
-    private final int vbo;
-
-    private boolean enableColor;
-    private boolean enableLightmap;
-
-    private int color;
-    private int lightmapCoord;
-
-    private double offsetX;
-    private double offsetY;
-    private double offsetZ;
-
-    public ShaderParticleTessellator(int size) {
-        this.buffer = Buffer.createBuffer(size);
-        this.vbo = glGenBuffers();
-    }
-
-    public void startDrawingParticles() {
-        if(this.drawing) {
-            throw new IllegalStateException("Already drawing!");
-        }
-        this.drawing = true;
-        this.count = 0;
-        this.buffer.clear();
-    }
-
-    public void setLightmapCoord(int lightmapCoord) {
-        checkIsDrawing();
-        if(!this.enableLightmap) {
-            if(this.count > 0) {
-                throw new IllegalStateException("Lightmap is disabled!");
-            }
-            this.enableLightmap = true;
-        }
-
-        this.lightmapCoord = lightmapCoord;
-    }
-
-    public void addParticle(double x, double y, double z, float scale, double u, double v, double uSize, double vSize) {
-        checkIsDrawing();
-        if(this.buffer.capacity() < this.buffer.position() + 64) {
-            int newSize = this.buffer.capacity() * 2;
-
-            LOGGER.info("Expanding Particle Tessellator Buffer ({} -> {})", this.buffer.capacity(), newSize);
-
-            ByteBuffer newBuffer = ByteBuffer.allocateDirect(newSize).order(ByteOrder.nativeOrder());
-            this.buffer.flip();
-            newBuffer.put(this.buffer);
-            this.buffer = newBuffer;
-        }
-
-        this.buffer.putFloat((float) (x + this.offsetX)).putFloat((float)(y + this.offsetY)).putFloat((float)(z + this.offsetZ)).putFloat(scale);
-        if (this.enableColor) {
-            this.buffer.putInt(this.color);
-        }
-        this.buffer.putFloat((float) u).putFloat((float) v);
-        this.buffer.putFloat((float) uSize).putFloat((float) vSize);
-
-        if (this.enableLightmap) {
-            this.buffer.put((byte) (LightmapHelper.getBlockLightFromCoord(this.lightmapCoord) * 16 + 8)).put((byte) (LightmapHelper.getSkyLightFromCoord(this.lightmapCoord) * 16 + 8));
-        }
-
-        this.count++;
-    }
-
-    public void drawParticles() {
-        checkIsDrawing();
-        this.drawing = false;
-
-        if (this.count == 0) return;
-
-        int vertexSize = 8 * Float.BYTES;
-        if (this.enableColor) {
-            vertexSize += 4;
-        }
-        if (this.enableLightmap) {
-            vertexSize += 2;
-        }
-        int offset = 0;
-
-        glBindBuffer(GL_ARRAY_BUFFER, this.vbo);
-
-        glVertexAttribPointer(0, 3, GL_FLOAT, false, vertexSize, offset); offset += 3 * Float.BYTES;    // Pos
-        glVertexAttribPointer(1, 1, GL_FLOAT, false, vertexSize, offset); offset += Float.BYTES;        // Scale
-        if (this.enableColor) { // Color
-            glVertexAttribPointer(2, 4, GL_UNSIGNED_BYTE, true, vertexSize, offset);
-            offset += 4;
-        } else {
-            glVertexAttrib4f(2, 1f, 1f, 1f, 1f);
-        }
-        glVertexAttribPointer(3, 2, GL_FLOAT, false, vertexSize, offset); offset += 2 * Float.BYTES;    // UV
-        glVertexAttribPointer(4, 2, GL_FLOAT, false, vertexSize, offset); offset += 2 * Float.BYTES;    // UVSizes
-        if (this.enableLightmap) { // Lightmap
-            glVertexAttribPointer(5, 2, GL_UNSIGNED_BYTE, true, vertexSize, offset);
-            offset += 2;
-        } else {
-            glVertexAttrib2f(5, 15.5f/16f, 15.5f/16f); // Fullbright of lightmap
-        }
-
-        glEnableVertexAttribArray(0);
-        glEnableVertexAttribArray(1);
-        if (this.enableColor) {
-            glEnableVertexAttribArray(2);
-        }
-        glEnableVertexAttribArray(3);
-        glEnableVertexAttribArray(4);
-        if (this.enableLightmap) {
-            glEnableVertexAttribArray(5);
-        }
-
-        glBufferData(GL_ARRAY_BUFFER, this.buffer.flip(), GL_STREAM_DRAW);
-        glDrawArrays(GL_POINTS, 0, this.count);
-
-        glBindBuffer(GL_ARRAY_BUFFER, 0);
-
-        glDisableVertexAttribArray(0);
-        glDisableVertexAttribArray(1);
-        glDisableVertexAttribArray(2);
-        glDisableVertexAttribArray(3);
-        glDisableVertexAttribArray(4);
-        glDisableVertexAttribArray(5);
-
-        this.enableColor = false;
-        this.enableLightmap = false;
-    }
-
-    public void checkIsDrawing() {
-        if(!this.drawing) {
-            throw new IllegalStateException("Not drawing!");
-        }
-    }
-
-    public void setTranslation(double x, double y, double z) {
-        this.offsetX = x;
-        this.offsetY = y;
-        this.offsetZ = z;
-    }
-    public void offsetTranslation(double x, double y, double z) {
-        this.offsetX += x;
-        this.offsetY += y;
-        this.offsetZ += z;
-    }
-
-    @Override
-    public void setColorOpaque(int r, int g, int b) {
-        this.setColorRGBA(r, g, b, 255);
-    }
-
-    @Override
-    public void setColorOpaque_F(float r, float g, float b) {
-        this.setColorOpaque((int) (r * 255.0F), (int) (g * 255.0F), (int) (b * 255.0F));
-    }
-
-    @Override
-    public void setColorOpaque_I(int rgb) {
-        int r = rgb >> 16 & 255;
-        int g = rgb >> 8 & 255;
-        int b = rgb & 255;
-        this.setColorOpaque(r, g, b);
-    }
-
-    @Override
-    public void setColorRGBA_F(float r, float g, float b, float a) {
-        this.setColorRGBA((int) (r * 255.0F), (int) (g * 255.0F), (int) (b * 255.0F), (int) (a * 255.0F));
-    }
-
-    @Override
-    public void setColorRGBA_I(int rgb, int a) {
-        int r = rgb >> 16 & 255;
-        int g = rgb >> 8 & 255;
-        int b = rgb & 255;
-        this.setColorRGBA(r, g, b, a);
-    }
-
-    @Override
-    public void setupParticleValues(@NotNull ICamera camera, float partialTick) {
-        // Do nothing shader handles everything already
-    }
-
-    @Override
-    public void setColorRGBA(int r, int g, int b, int a) {
-        checkIsDrawing();
-        if(!this.enableColor) {
-            if(this.count > 0) {
-                throw new IllegalStateException("Color is disabled!");
-            }
-            this.enableColor = true;
-        }
-
-        r = MathHelper.clamp(r, 0, 255);
-        g = MathHelper.clamp(g, 0, 255);
-        b = MathHelper.clamp(b, 0, 255);
-        a = MathHelper.clamp(a, 0, 255);
-
-        this.color = a << 24 | b << 16 | g << 8 | r;
-    }
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/Tessellator.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/Tessellator.java
index 63638f71b..da2d5ca78 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tessellator/Tessellator.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/Tessellator.java
@@ -1,28 +1,30 @@
 package net.minecraft.client.render.tessellator;
 
+import net.minecraft.client.Minecraft;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.core.enums.EnumOS;
 import org.jetbrains.annotations.NotNull;
 
 public interface Tessellator {
-	
-    public static @NotNull TessellatorStandard instance = new TessellatorStandard(0x200000);
-    
-    public void draw();
-    public void startDrawingQuads();
-    public void startDrawing(int drawMode);
-    public void setTextureUV(double u, double v);
-    public void setLightmapCoord(int lightmapCoord);
-    public void setColorOpaque_F(float r, float g, float b);
-    public void setColorRGBA_F(float r, float g, float b, float a);
-    public void setColorOpaque(int r, int g, int b);
-    public void setColorRGBA(int r, int g, int b, int a);
-    public void setColorOpaque_I(int rgb);
-    public void setColorRGBA_I(int rgb, int a);
-    public void lockColor();
-    public void addVertexWithUV(double x, double y, double z, double u, double v);
-    public void addVertex(double x, double y, double z);
-    public void setNormal(float x, float y, float z);
-    public void setTranslation(double x, double y, double z);
-    public void offsetTranslation(double x, double y, double z);
-    public void drawRectangle(int x, int y, int width, int height);
-    public void drawRectangleWithUV(int x, int y, int width, int height, double u, double v, double uvWidth, double uvHeight);
+    boolean QUAD_EMULATION = /*Minecraft.getOs() == EnumOS.macos || */true; // I hate you so fucking much apple
+    void startDrawing(@NotNull DrawMode drawMode);
+    @Deprecated
+    default void startDrawingQuads() {
+        startDrawing(DrawMode.QUADS);
+    }
+
+    void addVertex(double x, double y, double z);
+
+    void setTranslation(double x, double y, double z);
+    void offsetTranslation(double x, double y, double z);
+
+    default void drawRectangle(int x, int y, int width, int height) {
+        this.addVertex(x, y, 0.0D);
+        this.addVertex(x, y + height, 0.0D);
+        this.addVertex(x + width, y + height, 0.0D);
+        this.addVertex(x + width, y, 0.0D);
+    }
+
+    void draw();
+    @NotNull RenderBuffer record(int vao, int vbo);
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorBase.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorBase.java
index 665b4742d..b2be309a0 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorBase.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorBase.java
@@ -1,69 +1,82 @@
 package net.minecraft.client.render.tessellator;
 
-import org.lwjgl.opengl.GL11;
+import com.mojang.logging.LogUtils;
+import net.minecraft.client.render.renderer.DrawMode;
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.BufferUtils;
+import org.slf4j.Logger;
 
-public abstract class TessellatorBase implements Tessellator {
+import java.nio.ByteBuffer;
 
-    @Override
-    public void addVertexWithUV(double x, double y, double z, double u, double v) {
-        setTextureUV(u, v);
-        addVertex(x, y, z);
-    }
+public abstract class TessellatorBase implements Tessellator{
+    private static final Logger LOGGER = LogUtils.getLogger();
 
-    @Override
-    public void drawRectangle(int x, int y, int width, int height) {
-        this.checkIsDrawing();
-        this.addVertex((double) x, (double) y, 0.0D);
-        this.addVertex((double) x, (double) (y + height), 0.0D);
-        this.addVertex((double) (x + width), (double) (y + height), 0.0D);
-        this.addVertex((double) (x + width), (double) y, 0.0D);
-    }
+    public final @NotNull String name;
+    public @NotNull ByteBuffer data;
 
-    @Override
-    public void drawRectangleWithUV(int x, int y, int width, int height, double u, double v, double uvWidth, double uvHeight) {
-        this.checkIsDrawing();
-        this.addVertexWithUV((double) x, (double) y, 0.0D, u, v);
-        this.addVertexWithUV((double) x, (double) (y + height), 0.0D, u, v + uvHeight);
-        this.addVertexWithUV((double) (x + width), (double) (y + height), 0.0D, u + uvWidth, v + uvHeight);
-        this.addVertexWithUV((double) (x + width), (double) y, 0.0D, u + uvWidth, v);
+    protected double offsetX;
+    protected double offsetY;
+    protected double offsetZ;
+
+    public @NotNull DrawMode drawMode = DrawMode.TRIANGLES;
+    public boolean drawing;
+    public int vertexCount;
+    public TessellatorBase(@NotNull String name, int initialCapacity) {
+        this.name = name;
+        this.data = BufferUtils.createByteBuffer(initialCapacity);
     }
 
     @Override
-    public void setColorOpaque(int r, int g, int b) {
-        this.setColorRGBA(r, g, b, 255);
+    public void startDrawing(@NotNull DrawMode drawMode) {
+        if (this.drawing) {
+            this.drawing = false;
+            throw new IllegalStateException(this.name + "Already drawing!");
+        }
+
+        this.drawMode = drawMode;
+        this.drawing = true;
+        this.vertexCount = 0;
+
+        this.data.clear();
     }
 
     @Override
-    public void setColorOpaque_F(float r, float g, float b) {
-        this.setColorOpaque((int) (r * 255.0F), (int) (g * 255.0F), (int) (b * 255.0F));
+    public void setTranslation(double x, double y, double z) {
+        this.offsetX = x;
+        this.offsetY = y;
+        this.offsetZ = z;
     }
 
     @Override
-    public void setColorOpaque_I(int rgb) {
-        int r = rgb >> 16 & 255;
-        int g = rgb >> 8 & 255;
-        int b = rgb & 255;
-        this.setColorOpaque(r, g, b);
+    public void offsetTranslation(double x, double y, double z) {
+        this.offsetX += x;
+        this.offsetY += y;
+        this.offsetZ += z;
     }
 
-    @Override
-    public void setColorRGBA_F(float r, float g, float b, float a) {
-        this.setColorRGBA((int) (r * 255.0F), (int) (g * 255.0F), (int) (b * 255.0F), (int) (a * 255.0F));
+    public void checkIsDrawing() {
+        if (!this.drawing) {
+            throw new IllegalStateException(this.name + " not drawing!");
+        }
     }
 
-    @Override
-    public void setColorRGBA_I(int rgb, int a) {
-        int r = rgb >> 16 & 255;
-        int g = rgb >> 8 & 255;
-        int b = rgb & 255;
-        this.setColorRGBA(r, g, b, a);
+    public void checkCanFit(int size) {
+        if(this.data.capacity() < this.data.position() + size) {
+            int newSize = this.data.capacity() * 2;
+
+            LOGGER.info("Expanding {} Buffer ({} -> {})", this.name, this.data.capacity(), newSize);
+
+            ByteBuffer newBuffer = BufferUtils.createByteBuffer(newSize);
+            this.data.flip();
+            newBuffer.put(this.data);
+            this.data = newBuffer;
+        }
     }
 
     @Override
-    public void startDrawingQuads() {
-        startDrawing(GL11.GL_QUADS);
-    }
+    public abstract void draw();
 
-    public abstract void checkIsDrawing();
+    @Override
+    public abstract @NotNull RenderBuffer record(int vao, int vbo);
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorColor.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorColor.java
new file mode 100644
index 000000000..6e297d8c9
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorColor.java
@@ -0,0 +1,26 @@
+package net.minecraft.client.render.tessellator;
+
+import net.minecraft.core.util.helper.Color;
+
+public interface TessellatorColor extends Tessellator {
+    default void setColorOpaque3f(float r, float g, float b) {
+        setColor1i(Color.floatToIntARGB(1f, r, g, b));
+    }
+    default void setColor4f(float r, float g, float b, float a) {
+        setColor1i(Color.floatToIntARGB(a, r, g, b));
+    }
+    default void setColorOpaque3i(int r, int g, int b) {
+        setColor1i(Color.intToIntARGB(255, r, g, b));
+    }
+    default void setColor4i(int r, int g, int b, int a) {
+        setColor1i(Color.intToIntARGB(a, r, g, b));
+    }
+    default void setColorOpaque1i(int rgb) {
+        setColor1i(rgb | 0xFF000000);
+    }
+    default void setColor2i(int rgb, int a) {
+        setColor1i((rgb & 0xFFFFFF) | (a << 24) & 0xFF000000);
+    }
+    void setColor1i(int argb);
+    void lockColor();
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorFont.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorFont.java
new file mode 100644
index 000000000..f2a5d17ed
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorFont.java
@@ -0,0 +1,149 @@
+package net.minecraft.client.render.tessellator;
+
+import com.mojang.logging.LogUtils;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.BufferUtils;
+import org.lwjgl.opengl.GL41;
+import org.slf4j.Logger;
+
+import java.nio.ByteBuffer;
+import java.util.Arrays;
+
+public class TessellatorFont {
+    private static final Logger LOGGER = LogUtils.getLogger();
+    private boolean drawing = false;
+
+    private int color;
+
+    private final int vao;
+    private final int vbo;
+
+    private final @NotNull String name;
+    private ByteBuffer data;
+    private int vertexCount;
+
+    public TessellatorFont(@NotNull String name, int initialCapacity) {
+        this.name = name;
+        this.data = BufferUtils.createByteBuffer(initialCapacity);
+
+        this.vao = GL41.glGenVertexArrays();
+        this.vbo = GL41.glGenBuffers();
+
+        GL41.glBindVertexArray(this.vao);
+        GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+
+        int vertSize = 9 * Float.BYTES + 4;
+        int offset = 0;
+        GL41.glVertexAttribPointer(0, 2, GL41.GL_FLOAT, false,          vertSize, offset); offset += Float.BYTES * 2; // Pos XY
+        GL41.glVertexAttribPointer(1, 2, GL41.GL_FLOAT, false,          vertSize, offset); offset += Float.BYTES * 2; // Width Height
+        GL41.glVertexAttribPointer(2, 1, GL41.GL_FLOAT, false,          vertSize, offset); offset += Float.BYTES * 1; // Shift
+        GL41.glVertexAttribPointer(3, 4, GL41.GL_UNSIGNED_BYTE, true,   vertSize, offset); offset += 4;               // Color
+        GL41.glVertexAttribPointer(4, 2, GL41.GL_FLOAT, false,          vertSize, offset); offset += Float.BYTES * 2; // UV
+        GL41.glVertexAttribPointer(5, 2, GL41.GL_FLOAT, false,          vertSize, offset); offset += Float.BYTES * 2; // UV Sizes
+        GL41.glVertexAttrib2f(6, 15.5f/16f, 15.5f/16f);
+
+        GL41.glEnableVertexAttribArray(0);
+        GL41.glEnableVertexAttribArray(1);
+        GL41.glEnableVertexAttribArray(2);
+        GL41.glEnableVertexAttribArray(3);
+        GL41.glEnableVertexAttribArray(4);
+        GL41.glEnableVertexAttribArray(5);
+        GL41.glBindVertexArray(0);
+    }
+
+    public void startDrawing() {
+        if (this.drawing) {
+            this.drawing = false;
+            throw new IllegalStateException(this.name + " already drawing!");
+        }
+
+        this.drawing = true;
+        this.vertexCount = 0;
+        this.data.clear();
+
+        setColor1i(0xFFFFFFFF);
+    }
+
+
+    public void addChar(double x, double y, double width, double height, double shift, double u, double v, double uSize, double vSize) {
+        checkIsDrawing();
+        checkCanFit(64);
+
+        this.data.putFloat((float) x);
+        this.data.putFloat((float) y);
+
+        this.data.putFloat((float) width);
+        this.data.putFloat((float) height);
+
+        this.data.putFloat((float) shift);
+
+        this.data.putInt(this.color);
+
+//        this.data.put((byte) (u * 255));
+//        this.data.put((byte) (v * 255));
+//        this.data.put((byte) (uSize * 255));
+//        this.data.put((byte) (vSize * 255));
+
+        this.data.putFloat((float) (u));
+        this.data.putFloat((float) (v));
+        this.data.putFloat((float) (uSize));
+        this.data.putFloat((float) (vSize));
+
+        this.vertexCount++;
+    }
+
+    public void draw() {
+        if(!this.drawing) {
+            throw new IllegalStateException(this.name + " not drawing!");
+        }
+        this.drawing = false;
+
+        if (this.vertexCount == 0) return;
+
+        GL41.glBindVertexArray(this.vao);
+        GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+
+        GL41.glVertexAttrib2f(6, GLRenderer.getLightmapBlock(), GLRenderer.getLightmapSky());
+        GL41.glBufferData(GL41.GL_ARRAY_BUFFER, this.data.flip(), GL41.GL_STREAM_DRAW);
+
+        GL41.glDrawArrays(DrawMode.POINTS.cap, 0, this.vertexCount);
+        GL41.glBindVertexArray(0);
+    }
+
+    public void setColor1i(int argb) {
+        checkIsDrawing();
+
+        int a = (argb >> 24) & 0xFF;
+        int r = (argb >> 16) & 0xFF;
+        int g = (argb >> 8) & 0xFF;
+        int b = argb & 0xFF;
+
+        this.color = a << 24 | b << 16 | g << 8 | r;
+    }
+
+    public void setColor2i(int rgb, int a) {
+        setColor1i((rgb & 0xFFFFFF) | (a << 24) & 0xFF000000);
+    }
+
+
+    public void checkIsDrawing() {
+        if (!this.drawing) {
+            throw new IllegalStateException(this.name + " not drawing!");
+        }
+    }
+
+    public void checkCanFit(int size) {
+        if(this.data.capacity() < this.data.position() + size) {
+            int newSize = this.data.capacity() * 2;
+
+            LOGGER.info("Expanding {} Buffer ({} -> {})", this.name, this.data.capacity(), newSize);
+
+            ByteBuffer newBuffer = BufferUtils.createByteBuffer(newSize);
+            this.data.flip();
+            newBuffer.put(this.data);
+            this.data = newBuffer;
+        }
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorGeneral.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorGeneral.java
new file mode 100644
index 000000000..1f51a346f
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorGeneral.java
@@ -0,0 +1,6 @@
+package net.minecraft.client.render.tessellator;
+
+public interface TessellatorGeneral extends TessellatorColor, TessellatorTextured, TessellatorLightmap, TessellatorNormal, TessellatorTerrain, Tessellator {
+
+
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorLightmap.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorLightmap.java
new file mode 100644
index 000000000..10f74ccaa
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorLightmap.java
@@ -0,0 +1,10 @@
+package net.minecraft.client.render.tessellator;
+
+import net.minecraft.client.render.LightmapHelper;
+
+public interface TessellatorLightmap extends Tessellator{
+    void setLightmapCoord1i(int lightmapCoord);
+    default void setLightmapCoord2i(int blockLight, int skyLight) {
+        setLightmapCoord1i(LightmapHelper.getLightmapCoord(skyLight, blockLight));
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorNormal.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorNormal.java
new file mode 100644
index 000000000..809c5500b
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorNormal.java
@@ -0,0 +1,5 @@
+package net.minecraft.client.render.tessellator;
+
+public interface TessellatorNormal extends Tessellator{
+    void setNormal(float x, float y, float z);
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/ParticleTessellator.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorParticle.java
similarity index 57%
rename from game/client/src/main/java/net/minecraft/client/render/tessellator/ParticleTessellator.java
rename to game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorParticle.java
index 5791da58f..47c24ffe1 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tessellator/ParticleTessellator.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorParticle.java
@@ -3,16 +3,16 @@ package net.minecraft.client.render.tessellator;
 import net.minecraft.client.render.camera.ICamera;
 import org.jetbrains.annotations.NotNull;
 
-public interface ParticleTessellator {
+public interface TessellatorParticle {
 
     void startDrawingParticles();
-    void setLightmapCoord(int lightmapCoord);
-    void setColorOpaque_F(float r, float g, float b);
-    void setColorRGBA_F(float r, float g, float b, float a);
-    void setColorOpaque(int r, int g, int b);
-    void setColorRGBA(int r, int g, int b, int a);
-    void setColorOpaque_I(int rgb);
-    void setColorRGBA_I(int rgb, int a);
+    void setLightmapCoord1i(int lightmapCoord);
+    void setColorOpaque3f(float r, float g, float b);
+    void setColor4f(float r, float g, float b, float a);
+    void setColorOpaque3i(int r, int g, int b);
+    void setColor4i(int r, int g, int b, int a);
+    void setColorOpaque1i(int rgb);
+    void setColor2i(int rgb, int a);
     void setupParticleValues(@NotNull ICamera camera, float partialTick);
     void addParticle(double x, double y, double z, float scale, double u, double v, double uSize, double vSize);
     void drawParticles();
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorParticleShader.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorParticleShader.java
new file mode 100644
index 000000000..86b3f3c11
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorParticleShader.java
@@ -0,0 +1,177 @@
+package net.minecraft.client.render.tessellator;
+
+import com.mojang.logging.LogUtils;
+import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.camera.ICamera;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.core.util.helper.Buffer;
+import net.minecraft.core.util.helper.MathHelper;
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.opengl.GL41;
+import org.slf4j.Logger;
+
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+
+public class TessellatorParticleShader implements TessellatorParticle {
+    private static final Logger LOGGER = LogUtils.getLogger();
+    private boolean drawing = false;
+    private ByteBuffer buffer;
+
+    private int count = 0;
+    private final int vao;
+    private final int vbo;
+
+    private int color;
+    private int lightmapCoord;
+
+    private double offsetX;
+    private double offsetY;
+    private double offsetZ;
+
+    public TessellatorParticleShader(int size) {
+        this.buffer = Buffer.createBuffer(size);
+        this.vao = GL41.glGenVertexArrays();
+        this.vbo = GL41.glGenBuffers();
+
+        GL41.glBindVertexArray(this.vao);
+        GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+
+        int offset = 0;
+        int vertexSize = 38;
+        GL41.glVertexAttribPointer(0, 3, GL41.GL_FLOAT, false, vertexSize, offset); offset += 3 * Float.BYTES;    // Pos
+        GL41.glVertexAttribPointer(1, 1, GL41.GL_FLOAT, false, vertexSize, offset); offset += Float.BYTES;        // Scale
+        GL41.glVertexAttribPointer(2, 4, GL41.GL_UNSIGNED_BYTE, true, vertexSize, offset);  offset += 4;          // Color
+        GL41.glVertexAttribPointer(3, 2, GL41.GL_FLOAT, false, vertexSize, offset); offset += 2 * Float.BYTES;    // UV
+        GL41.glVertexAttribPointer(4, 2, GL41.GL_FLOAT, false, vertexSize, offset); offset += 2 * Float.BYTES;    // UVSizes
+        GL41.glVertexAttribPointer(5, 2, GL41.GL_UNSIGNED_BYTE, true, vertexSize, offset); offset += 2;           // Lightmap
+
+        GL41.glEnableVertexAttribArray(0);
+        GL41.glEnableVertexAttribArray(1);
+        GL41.glEnableVertexAttribArray(2);
+        GL41.glEnableVertexAttribArray(3);
+        GL41.glEnableVertexAttribArray(4);
+        GL41.glEnableVertexAttribArray(5);
+
+        GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, 0);
+        GL41.glBindVertexArray(0);
+    }
+
+    public void startDrawingParticles() {
+        if(this.drawing) {
+            throw new IllegalStateException("Already drawing!");
+        }
+        this.drawing = true;
+        this.color = 0xFFFFFFFF;
+        this.lightmapCoord = LightmapHelper.getLightmapCoord(15, 15);
+        this.count = 0;
+        this.buffer.clear();
+    }
+
+    public void setLightmapCoord1i(int lightmapCoord) {
+        checkIsDrawing();
+
+        this.lightmapCoord = lightmapCoord;
+    }
+
+    public void addParticle(double x, double y, double z, float scale, double u, double v, double uSize, double vSize) {
+        checkIsDrawing();
+        if(this.buffer.capacity() < this.buffer.position() + 64) {
+            int newSize = this.buffer.capacity() * 2;
+
+            LOGGER.info("Expanding Particle Tessellator Buffer ({} -> {})", this.buffer.capacity(), newSize);
+
+            ByteBuffer newBuffer = ByteBuffer.allocateDirect(newSize).order(ByteOrder.nativeOrder());
+            this.buffer.flip();
+            newBuffer.put(this.buffer);
+            this.buffer = newBuffer;
+        }
+
+        this.buffer.putFloat((float) (x + this.offsetX)).putFloat((float)(y + this.offsetY)).putFloat((float)(z + this.offsetZ)).putFloat(scale);
+        this.buffer.putInt(this.color);
+        this.buffer.putFloat((float) u).putFloat((float) v);
+        this.buffer.putFloat((float) uSize).putFloat((float) vSize);
+        this.buffer.put((byte) ((LightmapHelper.getBlockLightFromCoord(this.lightmapCoord) << 4) + 7)).put((byte) ((LightmapHelper.getSkyLightFromCoord(this.lightmapCoord) << 4) + 7));
+
+
+        this.count++;
+    }
+
+    public void drawParticles() {
+        checkIsDrawing();
+        this.drawing = false;
+
+        if (this.count == 0) return;
+
+        GL41.glBindVertexArray(this.vao);
+        GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+        GL41.glBufferData(GL41.GL_ARRAY_BUFFER, this.buffer.flip(), GL41.GL_STREAM_DRAW);
+
+        GLRenderer.render(this.vao, this.vbo, 0, this.count, DrawMode.POINTS);
+    }
+
+    public void checkIsDrawing() {
+        if(!this.drawing) {
+            throw new IllegalStateException("Not drawing!");
+        }
+    }
+
+    public void setTranslation(double x, double y, double z) {
+        this.offsetX = x;
+        this.offsetY = y;
+        this.offsetZ = z;
+    }
+    public void offsetTranslation(double x, double y, double z) {
+        this.offsetX += x;
+        this.offsetY += y;
+        this.offsetZ += z;
+    }
+
+    @Override
+    public void setColorOpaque3i(int r, int g, int b) {
+        this.setColor4i(r, g, b, 255);
+    }
+
+    @Override
+    public void setColorOpaque3f(float r, float g, float b) {
+        this.setColorOpaque3i((int) (r * 255.0F), (int) (g * 255.0F), (int) (b * 255.0F));
+    }
+
+    @Override
+    public void setColorOpaque1i(int rgb) {
+        int r = rgb >> 16 & 255;
+        int g = rgb >> 8 & 255;
+        int b = rgb & 255;
+        this.setColorOpaque3i(r, g, b);
+    }
+
+    @Override
+    public void setColor4f(float r, float g, float b, float a) {
+        this.setColor4i((int) (r * 255.0F), (int) (g * 255.0F), (int) (b * 255.0F), (int) (a * 255.0F));
+    }
+
+    @Override
+    public void setColor2i(int rgb, int a) {
+        int r = rgb >> 16 & 255;
+        int g = rgb >> 8 & 255;
+        int b = rgb & 255;
+        this.setColor4i(r, g, b, a);
+    }
+
+    @Override
+    public void setupParticleValues(@NotNull ICamera camera, float partialTick) {
+        // Do nothing shader handles everything already
+    }
+
+    @Override
+    public void setColor4i(int r, int g, int b, int a) {
+        checkIsDrawing();
+        r = MathHelper.clamp(r, 0, 255);
+        g = MathHelper.clamp(g, 0, 255);
+        b = MathHelper.clamp(b, 0, 255);
+        a = MathHelper.clamp(a, 0, 255);
+
+        this.color = a << 24 | b << 16 | g << 8 | r;
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorShader.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorShader.java
new file mode 100644
index 000000000..82a565cf2
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorShader.java
@@ -0,0 +1,253 @@
+package net.minecraft.client.render.tessellator;
+
+import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.opengl.GL41;
+
+public class TessellatorShader extends TessellatorBase implements TessellatorGeneral{
+
+    private boolean lockColor = false;
+    private boolean quadEmulation = false;
+
+    private boolean enableColor;
+    private boolean enableTexture;
+    private boolean enableLightmap;
+    private boolean enableNormal;
+
+    private int color;
+    private int lightmap;
+
+    private float texU;
+    private float texV;
+
+    private byte normalX;
+    private byte normalY;
+    private byte normalZ;
+
+    public final int vao;
+    public final int vbo;
+
+    private int quadVertCount = 0;
+
+    public TessellatorShader(@NotNull String name, int initialCapacity) {
+        super(name, initialCapacity);
+        this.vao = GL41.glGenVertexArrays();
+        this.vbo = GL41.glGenBuffers();
+    }
+
+    @Override
+    public void startDrawing(@NotNull DrawMode drawMode) {
+        super.startDrawing(drawMode);
+
+        this.lockColor = false;
+        this.enableColor = false;
+        this.enableTexture = false;
+        this.enableLightmap = false;
+        this.enableNormal = false;
+
+        this.quadEmulation = drawMode == DrawMode.QUADS && Tessellator.QUAD_EMULATION;
+        if (this.quadEmulation) {
+            this.drawMode = DrawMode.TRIANGLES;
+        }
+        this.quadVertCount = 0;
+    }
+
+    @Override
+    public void addVertex(double x, double y, double z) {
+        checkIsDrawing();
+        checkCanFit(64);
+
+        this.data.putFloat((float) (this.offsetX + x));
+        this.data.putFloat((float) (this.offsetY + y));
+        this.data.putFloat((float) (this.offsetZ + z));
+
+        if(this.enableColor) {
+            this.data.putInt(this.color);
+        }
+
+        if(this.enableTexture) {
+            this.data.putFloat(this.texU);
+            this.data.putFloat(this.texV);
+        }
+
+        if(this.enableLightmap) {
+            this.data.put((byte) ((LightmapHelper.getBlockLightFromCoord(this.lightmap) << 4) + 7));
+            this.data.put((byte) ((LightmapHelper.getSkyLightFromCoord(this.lightmap) << 4) + 7));
+        }
+
+        if(this.enableNormal) {
+            this.data.put(this.normalX);
+            this.data.put(this.normalY);
+            this.data.put(this.normalZ);
+        }
+        this.vertexCount++;
+
+        if (this.quadEmulation && this.quadVertCount % 4 == 2) {
+            int vertSize = getVertexSize();
+
+            checkCanFit(128);
+            this.data.put(this.data.position(), this.data, this.data.position() - vertSize * 3, vertSize);
+            this.data.put(this.data.position() + vertSize, this.data, this.data.position() - vertSize, vertSize);
+            this.data.position(this.data.position() + vertSize * 2);
+            this.vertexCount += 2;
+        }
+
+        this.quadVertCount++;
+    }
+
+    @Override
+    public void lockColor() {
+        checkIsDrawing();
+        this.lockColor = true;
+    }
+
+    @Override
+    public void setColor1i(int argb) {
+        checkIsDrawing();
+        if (this.lockColor) {
+            return;
+        }
+        if (!this.enableColor) {
+            if (this.vertexCount > 0) {
+                this.drawing = false;
+                throw new IllegalStateException(this.name + " color is disabled!");
+            }
+            this.enableColor = true;
+        }
+
+        int a = (argb >> 24) & 0xFF;
+        int r = (argb >> 16) & 0xFF;
+        int g = (argb >> 8) & 0xFF;
+        int b = argb & 0xFF;
+
+        this.color = a << 24 | b << 16 | g << 8 | r;
+    }
+
+    @Override
+    public void setTextureUV(double u, double v) {
+        checkIsDrawing();
+        if (!this.enableTexture) {
+            if (this.vertexCount > 0) {
+                this.drawing = false;
+                throw new IllegalStateException(this.name + " texture is disabled!");
+            }
+            this.enableTexture = true;
+        }
+
+        this.texU = (float) u;
+        this.texV = (float) v;
+    }
+
+    @Override
+    public void setLightmapCoord1i(int lightmapCoord) {
+        checkIsDrawing();
+        if (!this.enableLightmap) {
+            if (this.vertexCount > 0) {
+                this.drawing = false;
+                throw new IllegalStateException(this.name + " lightmap is disabled!");
+            }
+            this.enableLightmap = true;
+        }
+
+        this.lightmap = lightmapCoord;
+    }
+
+    @Override
+    public void setNormal(float x, float y, float z) {
+        checkIsDrawing();
+        if (!this.enableNormal) {
+            if (this.vertexCount > 0) {
+                this.drawing = false;
+                throw new IllegalStateException(this.name + " normal is disabled!");
+            }
+            this.enableNormal = true;
+        }
+
+        this.normalX = (byte) (x * 127.0f);
+        this.normalY = (byte) (y * 127.0f);
+        this.normalZ = (byte) (z * 127.0f);
+    }
+
+    @Override
+    public void draw() {
+        checkIsDrawing();
+        this.drawing = false;
+
+        if (this.vertexCount == 0) return;
+
+        enableVertexAttribs(this.vao, this.vbo);
+        GL41.glBufferData(GL41.GL_ARRAY_BUFFER, this.data.flip(), GL41.GL_STREAM_DRAW);
+        GLRenderer.render(this.vao, this.vbo, 0, this.vertexCount, this.drawMode);
+    }
+
+    @Override
+    public @NotNull RenderBuffer record(int vao, int vbo) {
+        checkIsDrawing();
+        this.drawing = false;
+
+        enableVertexAttribs(vao, vbo);
+        GL41.glBufferData(GL41.GL_ARRAY_BUFFER, this.data.flip(), GL41.GL_STATIC_DRAW);
+        GL41.glBindVertexArray(0);
+        return new RenderBuffer(vao, vbo, 0, this.vertexCount, this.drawMode);
+    }
+
+    protected int getVertexSize() {
+        int size = Float.BYTES * 3;
+        if(this.enableColor) {
+            size += 4;
+        }
+        if(this.enableTexture) {
+            size += Float.BYTES * 2;
+        }
+        if(this.enableNormal) {
+            size += 3;
+        }
+        if(this.enableLightmap) {
+            size += 2;
+        }
+
+        return size;
+    }
+
+    protected void enableVertexAttribs(int vao, int vbo) {
+        GL41.glBindVertexArray(vao);
+        GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, vbo);
+
+        int vertexSize = getVertexSize();
+        int offset = 0;
+        GL41.glVertexAttribPointer(0, 3, GL41.GL_FLOAT, false, vertexSize, offset); offset += 3 * Float.BYTES;    // Pos
+        GL41.glEnableVertexAttribArray(0);
+        if (this.enableColor) {
+            GL41.glVertexAttribPointer(1, 4, GL41.GL_UNSIGNED_BYTE, true, vertexSize, offset); offset += 4;    // Color
+            GL41.glEnableVertexAttribArray(1);
+        } else {
+            GL41.glDisableVertexAttribArray(1);
+            GL41.glVertexAttrib4f(1, 1f, 1f, 1f, 1f);
+        }
+
+        if (this.enableTexture) {
+            GL41.glVertexAttribPointer(2, 2, GL41.GL_FLOAT, false, vertexSize, offset); offset += 2 * Float.BYTES;    // UV
+            GL41.glEnableVertexAttribArray(2);
+        } else {
+            GL41.glDisableVertexAttribArray(2);
+        }
+
+        if (this.enableLightmap) {
+            GL41.glVertexAttribPointer(3, 2, GL41.GL_UNSIGNED_BYTE, true, vertexSize, offset); offset += 2;    // Lightmap
+            GL41.glEnableVertexAttribArray(3);
+        } else {
+            GL41.glDisableVertexAttribArray(3);
+            GL41.glVertexAttrib2f(3, GLRenderer.getLightmapBlock(), GLRenderer.getLightmapSky());
+        }
+
+        if (this.enableNormal) {
+            GL41.glVertexAttribPointer(4, 3, GL41.GL_BYTE, true, vertexSize, offset); offset += 3;    // Normal
+            GL41.glEnableVertexAttribArray(4);
+        } else {
+            GL41.glDisableVertexAttribArray(4);
+            GL41.glVertexAttrib3f(4, 0, -1, 0);
+        }
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorStandard.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorStandard.java
deleted file mode 100644
index bc47b2f60..000000000
--- a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorStandard.java
+++ /dev/null
@@ -1,248 +0,0 @@
-package net.minecraft.client.render.tessellator;
-
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-
-import com.mojang.logging.LogUtils;
-import net.minecraft.client.render.camera.ICamera;
-import net.minecraft.client.render.terrain.VertexConfig;
-import net.minecraft.client.render.terrain.VertexData;
-import net.minecraft.core.util.helper.MathHelper;
-import org.jetbrains.annotations.NotNull;
-import org.slf4j.Logger;
-
-public class TessellatorStandard extends TessellatorBase implements ParticleTessellator {
-	private static final Logger LOGGER = LogUtils.getLogger();
-	public VertexData data;
-	public boolean drawing;
-
-	private int color;
-	private int lightmapCoord;
-	
-	private double textureU;
-	private double textureV;
-	
-	private byte normalX;
-	private byte normalY;
-	private byte normalZ;
-	
-	private double offsetX;
-	private double offsetY;
-	private double offsetZ;
-	
-	private boolean lockedColor = false;
-	
-	public TessellatorStandard(int bufferSize) {
-		data = new VertexData(bufferSize);
-	}
-	
-	@Override
-	public void startDrawing(int drawMode) {
-		if(drawing) {
-			throw new IllegalStateException("Already drawing!");
-		}
-		
-		VertexConfig config = data.config;
-		
-		config.drawMode = drawMode;
-		this.drawing = true;
-		data.vertexCount = 0;
-		
-		config.enableColor = false;
-		config.enableTexture = false;
-		config.enableLightmap = false;
-		config.enableNormal = false;
-
-		this.lockedColor = false;
-		
-		data.buffer.clear();
-	}
-
-	@Override
-	public void draw() {
-		checkIsDrawing();
-		this.drawing = false;
-		
-		if(data.vertexCount == 0) {
-			return;
-		}
-		
-		data.buffer.flip();
-		data.drawAll();
-	}
-	
-	public int getVertexSize() {
-		return data.config.getVertexSize();
-	}
-
-	@Override
-	public void addVertex(double x, double y, double z) {
-		checkIsDrawing();
-
-		if(data.buffer.capacity() < data.buffer.position() + 64) {
-			int newSize = data.buffer.capacity() * 2;
-
-            LOGGER.info("Expanding Tessellator Buffer ({} -> {})", this.data.buffer.capacity(), newSize);
-
-			ByteBuffer newBuffer = ByteBuffer.allocateDirect(newSize).order(ByteOrder.nativeOrder());
-			data.buffer.flip();
-			newBuffer.put(data.buffer);
-			data.buffer = newBuffer;
-		}
-		
-		ByteBuffer buffer = data.buffer;
-		
-		buffer.putFloat((float) (offsetX + x));
-		buffer.putFloat((float) (offsetY + y));
-		buffer.putFloat((float) (offsetZ + z));
-
-		VertexConfig config = data.config;
-		
-		if(config.enableColor) {
-			buffer.putInt(color);
-		}
-		if(config.enableTexture) {
-			buffer.putFloat((float) textureU);
-			buffer.putFloat((float) textureV);
-		}
-		if(config.enableLightmap) {
-			buffer.putInt(lightmapCoord);
-		}
-		if(config.enableNormal) {
-			buffer.put(normalX);
-			buffer.put(normalY);
-			buffer.put(normalZ);
-		}
-		
-		data.vertexCount++;
-	}
-
-	@Override
-	public void setTextureUV(double u, double v) {
-		checkIsDrawing();
-		if(!data.config.enableTexture) {
-			if(data.vertexCount > 0) {
-				throw new IllegalStateException("Texture is disabled!");
-			}
-			data.config.enableTexture = true;
-		}
-		
-		this.textureU = u;
-		this.textureV = v;
-	}
-
-	@Override
-	public void startDrawingParticles() {
-		startDrawingQuads();
-	}
-
-	@Override
-	public void setLightmapCoord(int lightmapCoord) {
-		checkIsDrawing();
-		if(!data.config.enableLightmap) {
-			if(data.vertexCount > 0) {
-				throw new IllegalStateException("Lightmap is disabled!");
-			}
-			data.config.enableLightmap = true;
-		}
-		
-		this.lightmapCoord = lightmapCoord;
-	}
-
-	@Override
-	public void setColorRGBA(int r, int g, int b, int a) {
-		checkIsDrawing();
-		if(lockedColor) {
-			return;
-		}
-		if(!data.config.enableColor) {
-			if(data.vertexCount > 0) {
-				throw new IllegalStateException("Color is disabled!");
-			}
-			data.config.enableColor = true;
-		}
-		
-		r = MathHelper.clamp(r, 0, 255);
-		g = MathHelper.clamp(g, 0, 255);
-		b = MathHelper.clamp(b, 0, 255);
-		a = MathHelper.clamp(a, 0, 255);
-		
-		this.color = a << 24 | b << 16 | g << 8 | r;
-	}
-
-	private double particleYRot;
-	private double particleXRot;
-	private double particleXA;
-	private double particleZA;
-	private double particleXA2;
-	private double particleZA2;
-	private double particleYA;
-
-	@Override
-	public void setupParticleValues(@NotNull ICamera camera, float partialTick) {
-		particleYRot = camera.getYRot(partialTick);
-		particleXRot = camera.getXRot(partialTick);
-		particleXA = MathHelper.cos((float) (particleYRot * Math.PI) / 180F);
-		particleZA = MathHelper.sin((float) (particleYRot * Math.PI) / 180F);
-		particleXA2 = -particleZA * MathHelper.sin((float) ((particleXRot * Math.PI) / 180F));
-		particleZA2 = particleXA * MathHelper.sin((float) ((particleXRot * Math.PI) / 180F));
-		particleYA = MathHelper.cos((float) ((particleXRot * Math.PI) / 180F));
-	}
-
-	@Override
-	public void addParticle(double x, double y, double z, float scale, double u, double v, double uSize, double vSize) {
-		addVertexWithUV(x - particleXA * scale - particleXA2 * scale, y - particleYA * scale, z - particleZA * scale - particleZA2 * scale, u + uSize, v + vSize);
-		addVertexWithUV(x - particleXA * scale + particleXA2 * scale, y + particleYA * scale, z - particleZA * scale + particleZA2 * scale, u + uSize, v);
-		addVertexWithUV(x + particleXA * scale + particleXA2 * scale, y + particleYA * scale, z + particleZA * scale + particleZA2 * scale, u, v);
-		addVertexWithUV(x + particleXA * scale - particleXA2 * scale, y - particleYA * scale, z + particleZA * scale - particleZA2 * scale, u, v + vSize);
-	}
-
-	@Override
-	public void drawParticles() {
-		draw();
-	}
-
-	@Override
-	public void setNormal(float x, float y, float z) {
-		checkIsDrawing();
-		if(!data.config.enableNormal) {
-			if(data.vertexCount > 0) {
-				throw new IllegalStateException("Texture is disabled!");
-			}
-			data.config.enableNormal = true;
-		}
-		
-		this.normalX = (byte) (x * 127.0f);
-		this.normalY = (byte) (y * 127.0f);
-		this.normalZ = (byte) (z * 127.0f);
-	}
-
-	@Override
-	public void lockColor() {
-		checkIsDrawing();
-		
-		this.lockedColor = true;
-	}
-
-	@Override
-	public void setTranslation(double x, double y, double z) {
-		this.offsetX = x;
-		this.offsetY = y;
-		this.offsetZ = z;
-	}
-
-	@Override
-	public void offsetTranslation(double x, double y, double z) {
-		this.offsetX += x;
-		this.offsetY += y;
-		this.offsetZ += z;
-	}
-	
-	@Override
-	public void checkIsDrawing() {
-		if(!drawing) {
-			throw new IllegalStateException("Not drawing!");
-		}
-	}
-	
-}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTerrain.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTerrain.java
new file mode 100644
index 000000000..0e5bc837b
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTerrain.java
@@ -0,0 +1,4 @@
+package net.minecraft.client.render.tessellator;
+
+public interface TessellatorTerrain extends TessellatorColor, TessellatorTextured, TessellatorLightmap {
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTerrainImpl.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTerrainImpl.java
new file mode 100644
index 000000000..70f190ca4
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTerrainImpl.java
@@ -0,0 +1,233 @@
+package net.minecraft.client.render.tessellator;
+
+import java.nio.ByteBuffer;
+
+import com.mojang.logging.LogUtils;
+import net.minecraft.client.render.LightmapHelper;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.terrain.VertexConfig;
+import net.minecraft.client.render.terrain.VertexData;
+import org.jetbrains.annotations.NotNull;
+import org.lwjgl.BufferUtils;
+import org.lwjgl.opengl.GL41;
+import org.slf4j.Logger;
+
+public class TessellatorTerrainImpl implements TessellatorTerrain {
+	private static final Logger LOGGER = LogUtils.getLogger();
+	public TerrainVertexData data;
+	public boolean drawing;
+
+	private int color;
+	private int lightmapCoord;
+	
+	private double textureU;
+	private double textureV;
+	
+	private double offsetX;
+	private double offsetY;
+	private double offsetZ;
+
+	private boolean lockedColor = false;
+	private int quadVertCount = 0;
+	
+	public TessellatorTerrainImpl(int bufferSize) {
+        this.data = new TerrainVertexData(bufferSize);
+	}
+	
+	@Override
+	public void startDrawing(@NotNull DrawMode drawMode) {
+		if(this.drawing) {
+			this.drawing = false;
+			throw new IllegalStateException("Already drawing!");
+		}
+
+		this.drawing = true;
+        this.data.vertexCount = 0;
+		this.quadVertCount = 0;
+
+		setLightmapCoord1i(LightmapHelper.getLightmapCoord(15, 15));
+		setColor4i(255, 255, 255, 255);
+		setTextureUV(0.0, 0.0);
+
+		this.lockedColor = false;
+        this.data.buffer.clear();
+	}
+
+	@Override
+	public void draw() {
+		throw new UnsupportedOperationException();
+	}
+
+	@Override
+	public @NotNull RenderBuffer record(int vao, int vbo) {
+		throw new UnsupportedOperationException();
+	}
+
+	@Override
+	public void addVertex(double x, double y, double z) {
+		checkIsDrawing();
+		checkCanFit(64);
+		
+		ByteBuffer buffer = this.data.buffer;
+		
+		buffer.putFloat((float) (this.offsetX + x));
+		buffer.putFloat((float) (this.offsetY + y));
+		buffer.putFloat((float) (this.offsetZ + z));
+
+        buffer.putInt(this.color);
+
+        buffer.putFloat((float) this.textureU);
+        buffer.putFloat((float) this.textureV);
+
+        buffer
+            .put((byte) ((LightmapHelper.getBlockLightFromCoord(this.lightmapCoord) << 4) + 7))
+            .put((byte) ((LightmapHelper.getSkyLightFromCoord(this.lightmapCoord) << 4) + 7));
+
+
+        this.data.vertexCount++;
+
+		if (Tessellator.QUAD_EMULATION && this.quadVertCount % 4 == 2) {
+			int vertSize = this.data.config.getVertexSize();
+
+			checkCanFit(128);
+			this.data.buffer.put(this.data.buffer.position(), this.data.buffer, this.data.buffer.position() - vertSize * 3, vertSize);
+			this.data.buffer.put(this.data.buffer.position() + vertSize, this.data.buffer, this.data.buffer.position() - vertSize, vertSize);
+			this.data.buffer.position(this.data.buffer.position() + vertSize * 2);
+			this.data.vertexCount += 2;
+		}
+
+		this.quadVertCount++;
+	}
+
+	public void checkCanFit(int size) {
+		if(this.data.buffer.capacity() < this.data.buffer.position() + size) {
+			int newSize = this.data.buffer.capacity() * 2;
+
+			LOGGER.info("Expanding {} Buffer ({} -> {})", "Entity Tessellator", this.data.buffer.capacity(), newSize);
+
+			ByteBuffer newBuffer = BufferUtils.createByteBuffer(newSize);
+			this.data.buffer.flip();
+			newBuffer.put(this.data.buffer);
+			this.data.buffer = newBuffer;
+		}
+	}
+
+	@Override
+	public void setTextureUV(double u, double v) {
+		checkIsDrawing();
+
+		this.textureU = u;
+		this.textureV = v;
+	}
+
+	@Override
+	public void setLightmapCoord1i(int lightmapCoord) {
+		checkIsDrawing();
+
+		this.lightmapCoord = lightmapCoord;
+	}
+
+	@Override
+	public void setColor1i(int argb) {
+		checkIsDrawing();
+		if (this.lockedColor) {
+			return;
+		}
+
+		int a = (argb >> 24) & 0xFF;
+		int r = (argb >> 16) & 0xFF;
+		int g = (argb >> 8) & 0xFF;
+		int b = argb & 0xFF;
+
+		this.color = a << 24 | b << 16 | g << 8 | r;
+	}
+
+	@Override
+	public void lockColor() {
+		checkIsDrawing();
+		
+		this.lockedColor = true;
+	}
+
+	@Override
+	public void setTranslation(double x, double y, double z) {
+		this.offsetX = x;
+		this.offsetY = y;
+		this.offsetZ = z;
+	}
+
+	@Override
+	public void offsetTranslation(double x, double y, double z) {
+		this.offsetX += x;
+		this.offsetY += y;
+		this.offsetZ += z;
+	}
+
+	public void checkIsDrawing() {
+		if(!this.drawing) {
+			throw new IllegalStateException("Not drawing!");
+		}
+	}
+
+	public static class TerrainVertexData extends VertexData {
+
+		public TerrainVertexData(int size) {
+			super(size);
+			this.config = new TerrainVertexConfig();
+		}
+	}
+
+	public static class TerrainVertexConfig implements VertexConfig<TerrainVertexConfig> {
+
+		@Override
+		public @NotNull DrawMode drawmode() {
+			return Tessellator.QUAD_EMULATION ? DrawMode.TRIANGLES : DrawMode.QUADS;
+		}
+
+		public void enable(int vao, int vbo) {
+			GL41.glBindVertexArray(vao);
+			GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, vbo);
+
+			int vertexSize = getVertexSize();
+			int offset = 0;
+			GL41.glVertexAttribPointer(0, 3, GL41.GL_FLOAT, false, vertexSize, offset); offset += 3 * Float.BYTES;    // Pos
+            GL41.glVertexAttribPointer(1, 4, GL41.GL_UNSIGNED_BYTE, true, vertexSize, offset); offset += 4;    // Color
+			GL41.glVertexAttribPointer(2, 2, GL41.GL_FLOAT, false, vertexSize, offset); offset += 2 * Float.BYTES;    // UV
+			GL41.glVertexAttribPointer(3, 2, GL41.GL_UNSIGNED_BYTE, true, vertexSize, offset); offset += 2;    // Lightmap
+
+			GL41.glEnableVertexAttribArray(0);
+			GL41.glEnableVertexAttribArray(1);
+			GL41.glEnableVertexAttribArray(2);
+			GL41.glEnableVertexAttribArray(3);
+
+			GL41.glVertexAttrib3f(4, 0, -1, 0);
+		}
+
+		public void disable() {
+			GL41.glDisableVertexAttribArray(0);
+			GL41.glDisableVertexAttribArray(1);
+			GL41.glDisableVertexAttribArray(2);
+			GL41.glDisableVertexAttribArray(3);
+
+			GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, 0);
+			GL41.glBindVertexArray(0);
+		}
+
+		public int getVertexSize() {
+			int size = Float.BYTES * 3;
+            size += 4;
+            size += Float.BYTES * 2;
+            size += 2;
+			return size;
+		}
+
+		public @NotNull TerrainVertexConfig copy() {
+            return this;
+		}
+
+		@Override
+		public boolean equals(Object obj) {
+            return obj instanceof TerrainVertexConfig;
+        }
+	}
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTextured.java b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTextured.java
new file mode 100644
index 000000000..90a2348c4
--- /dev/null
+++ b/game/client/src/main/java/net/minecraft/client/render/tessellator/TessellatorTextured.java
@@ -0,0 +1,17 @@
+package net.minecraft.client.render.tessellator;
+
+public interface TessellatorTextured extends Tessellator {
+    void setTextureUV(double u, double v);
+
+    default void addVertexWithUV(double x, double y, double z, double u, double v) {
+        setTextureUV(u, v);
+        addVertex(x, y, z);
+    }
+
+    default void drawRectangleWithUV(int x, int y, int width, int height, double u, double v, double uvWidth, double uvHeight) {
+        this.addVertexWithUV(x, y, 0.0D, u, v);
+        this.addVertexWithUV(x, y + height, 0.0D, u, v + uvHeight);
+        this.addVertexWithUV(x + width, y + height, 0.0D, u + uvWidth, v + uvHeight);
+        this.addVertexWithUV(x + width, y, 0.0D, u + uvWidth, v);
+    }
+}
diff --git a/game/client/src/main/java/net/minecraft/client/render/texture/Texture.java b/game/client/src/main/java/net/minecraft/client/render/texture/Texture.java
index 308593ce1..40c29ed80 100644
--- a/game/client/src/main/java/net/minecraft/client/render/texture/Texture.java
+++ b/game/client/src/main/java/net/minecraft/client/render/texture/Texture.java
@@ -2,6 +2,7 @@ package net.minecraft.client.render.texture;
 
 import static net.minecraft.core.util.helper.Buffer.buffer;
 import static org.lwjgl.opengl.GL11.*;
+import static org.lwjgl.opengl.GL12.GL_CLAMP_TO_EDGE;
 import static org.lwjgl.opengl.GL12.GL_TEXTURE_MAX_LEVEL;
 
 import com.mojang.logging.LogUtils;
@@ -125,8 +126,8 @@ public class Texture {
 		}
 
 		if(clampTexture) {
-			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
+			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
 		}else {
 			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
 			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
diff --git a/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/AtlasStitcher.java b/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/AtlasStitcher.java
index bdc586798..1b7b5f9c7 100644
--- a/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/AtlasStitcher.java
+++ b/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/AtlasStitcher.java
@@ -3,11 +3,11 @@ package net.minecraft.client.render.texture.stitcher;
 import java.awt.AlphaComposite;
 import java.awt.Graphics2D;
 import java.awt.image.BufferedImage;
-import java.io.File;
+import java.io.IOException;
 import java.io.InputStream;
+import java.net.URISyntaxException;
 import java.util.ArrayList;
 import java.util.Collections;
-import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
 import java.util.concurrent.Callable;
@@ -17,9 +17,11 @@ import java.util.concurrent.Executors;
 import java.util.concurrent.Future;
 
 import com.mojang.logging.LogUtils;
+import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.client.render.texturepack.TexturePack;
+import net.minecraft.client.render.texturepack.TexturePackList;
 import net.minecraft.core.util.collection.NamespaceID;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
@@ -31,46 +33,68 @@ import org.slf4j.Logger;
 public class AtlasStitcher extends Texture {
     private static final Logger LOGGER = LogUtils.getLogger();
     public static final String rootAssetPath = "/assets";
-    public Map<NamespaceID, IconCoordinate> textureMap = new HashMap<>();
+    public @NotNull Map<NamespaceID, IconCoordinate> textureMap = new Object2ObjectOpenHashMap<>();
+    public @NotNull Map<String, String> idDirMap = new Object2ObjectOpenHashMap<>();
+    public final @Nullable BufferedImage defaultTexture;
     public BufferedImage atlas;
-    public final String directoryPath;
-    @Nullable
-    public final String defaultTexture;
     private int atlasWidth;
     private int atlasHeight;
     private double invWidth;
     private double invHeight;
     private final boolean mipmap;
     private final boolean tickPaused;
-    public AtlasStitcher(String directoryPath, boolean tickWhenPaused, boolean mipmap, @Nullable String defaultTexture){
-        this.directoryPath = directoryPath;
+    public AtlasStitcher(boolean tickWhenPaused, boolean mipmap, @Nullable BufferedImage defaultTexture){
         this.tickPaused = tickWhenPaused;
         this.mipmap = mipmap;
         this.defaultTexture = defaultTexture;
     }
 
-    protected @NotNull IconCoordinate getTexture(@NotNull NamespaceID sourceId, @NotNull NamespaceID id){
-        IconCoordinate cached = textureMap.get(id); // Changed to read cached value this way as somehow this method previously managed to return null https://bugs.betterthanadventure.net/scp/tickets.php?id=246
+    public @NotNull AtlasStitcher addDirectory(@NotNull String id, @NotNull String path) {
+        this.idDirMap.put(id, path);
+        return this;
+    }
+
+    protected @NotNull IconCoordinate getTexture(@NotNull NamespaceID id){
+        IconCoordinate cached = this.textureMap.get(id); // Changed to read cached value this way as somehow this method previously managed to return null https://bugs.betterthanadventure.net/scp/tickets.php?id=246
         if (cached != null) return cached;
 
-        id.makePermanent();
-        IconCoordinate iconCoordinate = new IconCoordinate(this, sourceId.makePermanent(), id, getSourceImagePath(id));
-        textureMap.put(id, iconCoordinate);
+        IconCoordinate iconCoordinate = new IconCoordinate(this, id, getSourceImagePath(id));
+        this.textureMap.put(id, iconCoordinate);
         return iconCoordinate;
     }
-    public String getSourceImagePath(@NotNull NamespaceID id){
-        return String.format("%s/%s/%s/%s.png", rootAssetPath, id.namespace(), directoryPath, id.value());
+
+    public @NotNull String getSourceImagePath(@NotNull NamespaceID id){
+        String value = id.value();
+        int slashIndex = value.indexOf("/");
+        if (slashIndex != -1) {
+            String dir = this.idDirMap.get(value.substring(0, slashIndex));
+            return String.format("%s/%s/%s/%s.png", rootAssetPath, id.namespace(), dir, value.substring(slashIndex + 1));
+        } else {
+            throw new IllegalArgumentException("Id " + id + " does not specify an id!");
+        }
+    }
+
+    public void initializeAll(@NotNull String namespace, boolean searchSubDirectories) throws IOException, URISyntaxException {
+        for (Map.Entry<String, String> e : this.idDirMap.entrySet()) {
+            String folder = String.format("%s/%s/%s/", rootAssetPath, namespace, e.getValue());
+
+            String[] paths = TextureRegistry.getFilesAndSubFiles(folder, searchSubDirectories);
+
+            for (String p : paths) {
+                getTexture(new NamespaceID(namespace, e.getKey() + "/" + p.replace(".png", "")));
+            }
+        }
     }
 
     public void preinit() {
         generate();
         long startTime = System.nanoTime();
         Minecraft mc = Minecraft.getMinecraft();
-        List<IconCoordinate> coordinateList = new ArrayList<>(textureMap.values());
+        List<IconCoordinate> coordinateList = new ArrayList<>(this.textureMap.values());
         List<Future<?>> futures = new ArrayList<>();
         ExecutorService service = Executors.newFixedThreadPool(32);
         for (IconCoordinate coordinate : coordinateList){
-            futures.add(service.submit(new SetupTexture(mc, coordinate, defaultTexture)));
+            futures.add(service.submit(new SetupTexture(mc.texturePackList, coordinate, this.defaultTexture)));
         }
 
         for (Future<?> f : futures) {
@@ -89,7 +113,7 @@ public class AtlasStitcher extends Texture {
         // Load all individual textures and the store the widths
         int area = 0;
         int maxWidth = 0;
-        List<IconCoordinate> coordinateList = new ArrayList<>(textureMap.values());
+        List<IconCoordinate> coordinateList = new ArrayList<>(this.textureMap.values());
         for (IconCoordinate coordinate : coordinateList){
             if (coordinate.needsDimensions()) {
                 BufferedImage image = coordinate.getImageStorage();
@@ -121,11 +145,10 @@ public class AtlasStitcher extends Texture {
         // Generate and then copy the data to a new image with the dimensions needed
         BufferedImage generatedAtlas = new BufferedImage(targetWidth, Integer.highestOneBit(nextY) << 1, BufferedImage.TYPE_INT_ARGB);
 
-        atlasWidth = generatedAtlas.getWidth();
-        atlasHeight = generatedAtlas.getHeight();
-        invWidth = 1d/atlasWidth;
-        invHeight = 1d/atlasHeight;
-        this.atlas = generatedAtlas;
+        this.atlasWidth = generatedAtlas.getWidth();
+        this.atlasHeight = generatedAtlas.getHeight();
+        this.invWidth = 1d/ this.atlasWidth;
+        this.invHeight = 1d/ this.atlasHeight;
 
         Graphics2D atlas = generatedAtlas.createGraphics();
         atlas.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 1f));
@@ -135,68 +158,69 @@ public class AtlasStitcher extends Texture {
         }
         atlas.dispose();
 
-        setupTexture(this.atlas, false, false, mipmap);
+        setupTexture(generatedAtlas, false, false, this.mipmap);
+
+        this.atlas = generatedAtlas;
     }
 
     public int getAtlasWidth(){
-        return atlasWidth;
+        return this.atlasWidth;
     }
     public int getAtlasHeight(){
-        return atlasHeight;
+        return this.atlasHeight;
     }
     public double getInverseWidth(){
-        return invWidth;
+        return this.invWidth;
     }
     public double getInverseHeight(){
-        return invHeight;
+        return this.invHeight;
     }
-    public boolean tickWhenPaused() {return tickPaused;}
-    public boolean hasMipmaps() {return mipmap;}
+    public boolean tickWhenPaused() {return this.tickPaused;}
+    public boolean hasMipmaps() {return this.mipmap;}
 
     public static class SetupTexture implements Callable<IconCoordinate> {
-        private final Minecraft mc;
-        private final IconCoordinate coordinate;
-        private final String defaultTexture;
-        public SetupTexture(Minecraft mc, IconCoordinate coordinate, String defaultTexture) {
-            this.mc = mc;
+        private final @NotNull TexturePackList packList;
+        private final @NotNull IconCoordinate coordinate;
+        private final @Nullable BufferedImage defaultTexture;
+        public SetupTexture(@NotNull TexturePackList packList, @NotNull IconCoordinate coordinate, @Nullable BufferedImage defaultTexture) {
+            this.packList = packList;
             this.coordinate = coordinate;
             this.defaultTexture = defaultTexture;
         }
         @Override
         public IconCoordinate call() {
-            coordinate.resetMetadata();
-            BufferedImage image = CustomAtlasHandler.getTextureOverride(mc.texturePackList, coordinate.sourceImage);
+            this.coordinate.resetMetadata();
+            BufferedImage image = CustomAtlasHandler.getTextureOverride(this.packList, this.coordinate.sourceImagePath);
             if(image == null) {
-                TexturePack pack = mc.texturePackList.getHighestPriorityTexturePackWithFile(coordinate.sourceImage);
+                TexturePack pack = this.packList.getHighestPriorityTexturePackWithFile(this.coordinate.sourceImagePath);
                 if (pack != null) {
                     for (int attempt = 0; attempt < 3; attempt++) {
                         try {
-                            image = Textures.readImageUnhandled(pack.getResourceAsStream(coordinate.sourceImage));
+                            image = Textures.readImageUnhandled(pack.getResourceAsStream(this.coordinate.sourceImagePath));
                             if (image != null) break;
                         } catch (Exception e) {
                             LOGGER.error("", e);
                         }
                     }
-                    String metaPath = coordinate.sourceImage + ".mcmeta";
+                    String metaPath = this.coordinate.sourceImagePath + ".mcmeta";
                     if (pack.hasFile(metaPath)) {
                         try (InputStream stream = pack.getResourceAsStream(metaPath)){
-                            coordinate.initMetadata(stream);
+                            this.coordinate.initMetadata(stream);
                         } catch (Exception e) {
-                            LOGGER.error("Failed to initiate metadata for '{}'!", coordinate.namespaceId, e);
+                            LOGGER.error("Failed to initiate metadata for '{}'!", this.coordinate.namespaceId, e);
                         }
                     }
                 }
-
             }
             if (image == null || image == Textures.missingTexture){
-                LOGGER.warn("{} could not be found!", coordinate.sourceImage);
-                if (defaultTexture != null){
-                    image = Textures.readImage(mc.texturePackList.getResourceAsStream(defaultTexture));
+                LOGGER.warn("{} could not be found!", this.coordinate.sourceImagePath);
+                if (this.defaultTexture != null){
+                    image = this.defaultTexture;
                 }
                 if (image == null) image = Textures.missingTexture; // If this ever happens I'll be very sad
             }
-            coordinate.setImage(image);
-            return coordinate;
+            this.coordinate.setImage(image);
+            return this.coordinate;
         }
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/IconCoordinate.java b/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/IconCoordinate.java
index 22f1800b3..ccf2bee8b 100644
--- a/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/IconCoordinate.java
+++ b/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/IconCoordinate.java
@@ -24,18 +24,16 @@ public class IconCoordinate implements Comparable<IconCoordinate> {
     private double uSize;
     private double vSize;
     private boolean pendingDimensions;
-    protected final String sourceImage;
-    protected final TextureMetaHandler metaHandler = new TextureMetaHandler();
-    public final NamespaceID namespaceId;
-    public final NamespaceID sourceNamespaceId;
-    public final AtlasStitcher parentAtlas;
+    protected final @NotNull String sourceImagePath;
+    protected final @NotNull TextureMetaHandler metaHandler = new TextureMetaHandler();
+    public final @NotNull NamespaceID namespaceId;
+    public final @NotNull AtlasStitcher parentAtlas;
     private BufferedImage _imageStorage;
 
-    public IconCoordinate(AtlasStitcher stitcher, NamespaceID sourceNamespaceId, NamespaceID namespaceId, String sourceImage) {
+    public IconCoordinate(@NotNull AtlasStitcher stitcher, @NotNull NamespaceID namespaceId, @NotNull String sourceImagePath) {
         this.parentAtlas = stitcher;
-        this.sourceNamespaceId = sourceNamespaceId;
         this.namespaceId = namespaceId;
-        this.sourceImage = sourceImage;
+        this.sourceImagePath = sourceImagePath;
     }
 
     protected void setImage(@NotNull BufferedImage image) {
@@ -81,7 +79,7 @@ public class IconCoordinate implements Comparable<IconCoordinate> {
     }
 
     protected void drawToAtlas(Graphics2D atlas) {
-        assert this._imageStorage != null : "Image storage should not be null!! something went wrong with image '" + this.namespaceId + "' at '" + this.sourceImage + "'!";
+        assert this._imageStorage != null : "Image storage should not be null!! something went wrong with image '" + this.namespaceId + "' at '" + this.sourceImagePath + "'!";
         if (this.width != this._imageStorage.getWidth() || this.height != this._imageStorage.getHeight()) {
             int[] subImage = this._imageStorage.getRGB(0, 0, this.width, this.height, null, 0, this.width);
             BufferedImage _img = new BufferedImage(this.width, this.height, BufferedImage.TYPE_INT_ARGB);
@@ -125,11 +123,11 @@ public class IconCoordinate implements Comparable<IconCoordinate> {
     }
 
     public String toString() {
-        return String.format("W:%d, H:%d, X:%d, Y:%d | ID:%s, Source:%s", this.width, this.height, this.iconX, this.iconY, this.namespaceId, this.sourceImage);
+        return String.format("W:%d, H:%d, X:%d, Y:%d | ID:%s, Source:%s", this.width, this.height, this.iconX, this.iconY, this.namespaceId, this.sourceImagePath);
     }
 
     public String getImageSource() {
-        return this.sourceImage;
+        return this.sourceImagePath;
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/TextureRegistry.java b/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/TextureRegistry.java
index 88be83130..446c67f22 100644
--- a/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/TextureRegistry.java
+++ b/game/client/src/main/java/net/minecraft/client/render/texture/stitcher/TextureRegistry.java
@@ -3,12 +3,15 @@ package net.minecraft.client.render.texture.stitcher;
 
 
 import com.mojang.logging.LogUtils;
+import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
+import it.unimi.dsi.fastutil.objects.ObjectArrayList;
 import net.minecraft.core.Global;
 import net.minecraft.core.util.HardIllegalArgumentException;
 import net.minecraft.core.util.collection.NamespaceID;
 import org.jetbrains.annotations.NotNull;
 import org.slf4j.Logger;
 
+import java.awt.image.BufferedImage;
 import java.io.File;
 import java.io.FileWriter;
 import java.io.IOException;
@@ -33,20 +36,44 @@ import java.util.stream.Stream;
 
 public class TextureRegistry {
     private static final Logger LOGGER = LogUtils.getLogger();
-    public static HashMap<String, AtlasStitcher> stitcherMap = new HashMap<>();
-    public static HashMap<AtlasStitcher, String> stitcherMapReverse = new HashMap<>();
-    @SuppressWarnings("unused")
-    public static AtlasStitcher blockAtlas = register("block", new AtlasStitcher("textures/block", false, true, "/assets/minecraft/textures/block/texture_missing.png"));
-    @SuppressWarnings("unused")
-    public static AtlasStitcher itemAtlas =  register("item", new AtlasStitcher("textures/item", false, true, "/assets/minecraft/textures/item/texture_missing.png"));
+    public static List<AtlasStitcher> atlases = new ObjectArrayList<>();
+    public static Map<String, AtlasStitcher> stitcherMap = new Object2ObjectOpenHashMap<>();
+    public static final BufferedImage missingIconImage = new BufferedImage(16, 16, BufferedImage.TYPE_INT_ARGB);
+    static {
+        for (int x = 0; x < 16; x++) {
+            for (int y = 0; y < 16; y++) {
+                if ((((x/8) + (y/8)) & 0b1) == 0) {
+                    missingIconImage.setRGB(x, y, 0xFFFF00FF);
+                } else {
+                    missingIconImage.setRGB(x, y, 0xFF000000);
+                }
+            }
+        }
+    }
+
     @SuppressWarnings("unused")
-    public static AtlasStitcher particleAtlas = register("particle", new AtlasStitcher("textures/particle", false, true, null));
+    public static AtlasStitcher worldAtlas = register(
+        new AtlasStitcher(false, true, missingIconImage)
+            .addDirectory("block", "textures/block")
+            .addDirectory("item", "textures/item")
+            .addDirectory("particle", "textures/particle")
+    );
+
     @SuppressWarnings("unused")
-    public static AtlasStitcher artAtlas = register("art", new AtlasStitcher("textures/art", false, true, null));
+    public static AtlasStitcher artAtlas = register(
+        new AtlasStitcher(false, true, null)
+            .addDirectory("art", "textures/art")
+    );
     @SuppressWarnings("unused")
-    public static AtlasStitcher guiSpriteAtlas = register("gui", new AtlasStitcher("textures/gui/sprites", true, false, null));
+    public static AtlasStitcher guiSpriteAtlas = register(
+        new AtlasStitcher(true, false, null)
+            .addDirectory("gui", "textures/gui/sprites")
+    );
     @SuppressWarnings("unused")
-    public static AtlasStitcher signAtlas = register("sign", new AtlasStitcher("textures/gui/sign", false, false, null));
+    public static AtlasStitcher signAtlas = register(
+        new AtlasStitcher(false, false, null)
+            .addDirectory("sign", "textures/gui/sign")
+    );
 
     public static @NotNull IconCoordinate getTexture(@NotNull String key){
         try {
@@ -57,10 +84,11 @@ public class TextureRegistry {
     }
     public static @NotNull IconCoordinate getTexture(@NotNull NamespaceID id){
         final int slashIndex = id.value().indexOf("/");
-        final AtlasStitcher atlas = stitcherMap.get(id.value().substring(0, slashIndex));
-        if (atlas == null) throw new IllegalArgumentException("Failed to find atlas '" + id.value().substring(0, slashIndex) + "'!");
+        String atlasId = id.value().substring(0, slashIndex);
+        final AtlasStitcher atlas = stitcherMap.get(atlasId);
+        if (atlas == null) throw new IllegalArgumentException("Failed to find atlas '" + atlasId + "'! From ID: " + id);
 
-        return atlas.getTexture(id, NamespaceID.fromPool(id.namespace(), id.value().substring(slashIndex + 1)));
+        return atlas.getTexture(id);
     }
     public static boolean hasTexture(@NotNull String key) {
         try {
@@ -71,20 +99,23 @@ public class TextureRegistry {
     }
     public static boolean hasTexture(@NotNull NamespaceID id){
         final int slashIndex = id.value().indexOf("/");
-        final AtlasStitcher atlas = stitcherMap.get(id.value().substring(0, slashIndex));
-        if (atlas == null) throw new IllegalArgumentException("Failed to find atlas '" + id.value().substring(0, slashIndex) + "'!");
+        String atlasId = id.value().substring(0, slashIndex);
+        final AtlasStitcher atlas = stitcherMap.get(atlasId);
+        if (atlas == null) throw new IllegalArgumentException("Failed to find atlas '" + atlasId + "'!");
 
         return atlas.textureMap.containsKey(NamespaceID.fromPool(id.namespace(), id.value().substring(slashIndex + 1)));
     }
-    public static AtlasStitcher register(String id, AtlasStitcher atlas){
-        stitcherMap.put(id, atlas);
-        stitcherMapReverse.put(atlas, id);
+    public static @NotNull AtlasStitcher register(@NotNull AtlasStitcher atlas){
+        for (String id : atlas.idDirMap.keySet()) {
+            stitcherMap.put(id, atlas);
+        }
+        atlases.add(atlas);
         return atlas;
     }
     static {
         // Initialize all textures in case they aren't normally done before the textures are first refreshed
         try {
-            for (AtlasStitcher stitcher : stitcherMap.values()){
+            for (AtlasStitcher stitcher : atlases){
                 initializeAllFiles("minecraft", stitcher, stitcher != artAtlas);
             }
         } catch (Exception e) {
@@ -92,18 +123,8 @@ public class TextureRegistry {
         }
     }
 
-    public static void initializeAllFiles(String namespace, AtlasStitcher atlas, boolean subDirectories) throws URISyntaxException, IOException, NullPointerException {
-        String path = String.format("%s/%s/%s", AtlasStitcher.rootAssetPath, namespace, atlas.directoryPath);
-
-        String[] files = getFilesAndSubFiles(path, subDirectories);
-
-//        System.out.println("Printing " + path);
-        for (String s : files) {
-//            System.out.println(s);
-
-            NamespaceID id = NamespaceID.fromPool(namespace, s.replace(".png", "").replace("//", "/"));
-            atlas.getTexture(NamespaceID.fromPool(id.namespace(), stitcherMapReverse.get(atlas) + "/" + id.value()), id);
-        }
+    public static void initializeAllFiles(@NotNull String namespace, @NotNull AtlasStitcher atlas, boolean subDirectories) throws URISyntaxException, IOException, NullPointerException {
+        atlas.initializeAll(namespace, subDirectories);
     }
 
     public static String[] getFilesAndSubFiles(String directory, boolean searchSubDirectories) throws IOException, URISyntaxException {
@@ -176,7 +197,7 @@ public class TextureRegistry {
                 try (final FileWriter writer = new FileWriter(tileFile)) {
                     writer.append("# Auto generated tiles mapping for atlas '").append(stitcherEntry.getKey()).append("'\n");
                     writer.append("# generated for version '").append(Global.VERSION).append("' at '").append(dateFormat.format(new Date())).append("'\n");
-                    writer.append("size=").append(Integer.toString(stitcher.atlas.getWidth())).append("x").append(Integer.toString(stitcher.atlas.getHeight())).append("\n");
+                    writer.append("size=").append(Integer.toString(stitcher.getAtlasWidth())).append("x").append(Integer.toString(stitcher.getAtlasHeight())).append("\n");
                     for (final Map.Entry<NamespaceID, IconCoordinate> entry : stitcher.textureMap.entrySet()) {
                         final IconCoordinate coordinate = entry.getValue();
                         writer.append(Integer.toString(coordinate.iconX)).append(",").append(Integer.toString(coordinate.iconY));
diff --git a/game/client/src/main/java/net/minecraft/client/render/texturepack/TexturePackList.java b/game/client/src/main/java/net/minecraft/client/render/texturepack/TexturePackList.java
index 23aed9361..1e1312569 100644
--- a/game/client/src/main/java/net/minecraft/client/render/texturepack/TexturePackList.java
+++ b/game/client/src/main/java/net/minecraft/client/render/texturepack/TexturePackList.java
@@ -4,7 +4,7 @@ import com.mojang.logging.LogUtils;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.gui.TooltipElement;
 import net.minecraft.client.gui.keyboard.KeyboardLayout;
-import net.minecraft.client.render.EntityRenderDispatcher;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import net.minecraft.client.render.TileEntityRenderDispatcher;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
@@ -108,7 +108,7 @@ public class TexturePackList
 		BlockModelDispatcher.getInstance().reload();
 		ItemModelDispatcher.getInstance().reload();
 		EntityGeometryMojangData.Cache.reload(this);
-		EntityRenderDispatcher.instance.reload();
+		EntityRendererDispatcher.instance.reload();
 		TileEntityRenderDispatcher.instance.reload();
 		KeyboardLayout.defaultLayout = new KeyboardLayout();
 		TooltipElement.reloadStyles(this);
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRenderer.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRenderer.java
index 30c7370a0..a4dbff3c8 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRenderer.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRenderer.java
@@ -4,7 +4,7 @@ import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.TileEntityRenderDispatcher;
 import net.minecraft.client.render.camera.ICamera;
 import net.minecraft.client.render.font.FontRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.entity.TileEntity;
 import net.minecraft.core.block.entity.TileEntityDispatcher;
 import net.minecraft.core.util.collection.NamespaceID;
@@ -29,7 +29,7 @@ public abstract class TileEntityRenderer<T extends TileEntity>
 
     public void tick() {}
 
-    public abstract void doRender(Tessellator tessellator, T tileEntity, double x, double y, double z,
+    public abstract void doRender(TessellatorGeneral tessellator, T tileEntity, double x, double y, double z,
                                   float partialTick);
 
     protected void bindTexture(final String texturePath)
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererFlag.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererFlag.java
index 8f049ddda..79a43b13a 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererFlag.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererFlag.java
@@ -2,7 +2,10 @@ package net.minecraft.client.render.tileentity;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.FlagRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.block.entity.TileEntityFlag;
 
@@ -10,13 +13,10 @@ import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
 import net.minecraft.core.world.wind.WindProvider;
 import org.jetbrains.annotations.NotNull;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
 
-public class TileEntityRendererFlag extends TileEntityRenderer<TileEntityFlag>
-{
+public class TileEntityRendererFlag extends TileEntityRenderer<TileEntityFlag> {
 
     private final @NotNull FlagRenderer flagRenderer = new FlagRenderer(Minecraft.getMinecraft().textureManager);
     public final Minecraft mc = Minecraft.getMinecraft();
@@ -26,7 +26,7 @@ public class TileEntityRendererFlag extends TileEntityRenderer<TileEntityFlag>
     }
 
     @Override
-    public void doRender(final @NotNull Tessellator tessellator, @NotNull final TileEntityFlag tileEntity, final double x, final double y, final double z, final float partialTick) {
+    public void doRender(final @NotNull TessellatorGeneral tessellator, @NotNull final TileEntityFlag tileEntity, final double x, final double y, final double z, final float partialTick) {
         final World theWorld = Minecraft.getMinecraft().currentWorld;
         final int blockUnder = theWorld.getBlockId(tileEntity.x, tileEntity.y - 1, tileEntity.z);
         final boolean shortPole = blockUnder == Blocks.FLAG.id();
@@ -35,57 +35,56 @@ public class TileEntityRendererFlag extends TileEntityRenderer<TileEntityFlag>
 
         final float windDirection = theWind.getWindDirection(this.mc.currentWorld, 0.0f, 500.0f, 0.0f) * 360f;
         final float windIntensity = theWind.getWindIntensity(this.mc.currentWorld, 0.0f, 500.0f, 0.0f);
-        
+
         doRender(tessellator, tileEntity, x, y, z, partialTick, shortPole, windDirection, windIntensity);
     }
 
     private long lastTick = 0;
-    public void doRender(final @NotNull Tessellator tessellator, final @NotNull TileEntityFlag tileEntityFlag, final double x, final double y, final double z, final float partialTick, final boolean shortPole, final float windDirection, final float windIntensity)
-    {
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+
+    public void doRender(final @NotNull TessellatorGeneral tessellator, final @NotNull TileEntityFlag tileEntityFlag, final double x, final double y, final double z, final float partialTick, final boolean shortPole, final float windDirection, final float windIntensity) {
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
         final World theWorld = this.mc.currentWorld;
         if (theWorld.getWorldTime() != this.lastTick) {
             this.lastTick = theWorld.getWorldTime();
             this.flagRenderer.tick();
         }
-        
+
         final float swayInterpolated = tileEntityFlag.sway + partialTick;
-        
+
         float sway = (float) ((swayInterpolated / 1.5) % (2 * Math.PI));
         sway = (float) (Math.sin(sway) * windIntensity * 2.0f);
-        
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float) x + 0.5F, (float) y, (float) z + 0.5F);
-        GL11.glScalef(1/16F, 1/16F, -1/16F);
+
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x + 0.5F, (float) y, (float) z + 0.5F);
+        GLRenderer.modelM4f().scale(1 / 16F, 1 / 16F, -1 / 16F);
         bindTexture("/assets/minecraft/textures/entity/flag.png");
         final StaticEntityModel flagModel = shortPole ? getModel("pole.short") : getModel("pole.long");
 
         if (shortPole) {
-            GL11.glTranslatef(0, 18, 0);
+            GLRenderer.modelM4f().translate(0, 18, 0);
         }
 
         flagModel.getTransform("flag").rotY = (windDirection + sway) * MathHelper.DEG_TO_RAD;
-        flagModel.render(tessellator);
+        flagModel.render();
 
         flagModel.translateToBone("flag");
         bindTexture("/assets/minecraft/textures/entity/flag_ui.png");
         if (tileEntityFlag.getFlipped()) {
-            getModel("cloth.mirror").render(tessellator);
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glBlendFunc(GL11.GL_ONE_MINUS_SRC_COLOR, GL11.GL_SRC_COLOR);
+            getModel("cloth.mirror").render();
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.ONE_MINUS_SRC_COLOR, BlendFactor.SRC_COLOR);
             this.renderDispatcher.textureManager.bindTexture(this.flagRenderer.getTexture(tileEntityFlag));
-            getModel("cloth.mirror").render(tessellator);
+            getModel("cloth.mirror").render();
         } else {
-            getModel("cloth").render(tessellator);
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glBlendFunc(GL11.GL_ONE_MINUS_SRC_COLOR, GL11.GL_SRC_COLOR);
+            getModel("cloth").render();
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.setBlendFunc(BlendFactor.ONE_MINUS_SRC_COLOR, BlendFactor.SRC_COLOR);
             this.renderDispatcher.textureManager.bindTexture(this.flagRenderer.getTexture(tileEntityFlag));
-            getModel("cloth").render(tessellator);
+            getModel("cloth").render();
         }
-        GL11.glDisable(GL11.GL_BLEND);
+        GLRenderer.disableState(State.BLEND);
 
-        GL11.glPopMatrix();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.popFrame();
     }
 
     @Override
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererFlowerJar.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererFlowerJar.java
index 739e5400a..90869313a 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererFlowerJar.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererFlowerJar.java
@@ -1,17 +1,13 @@
 package net.minecraft.client.render.tileentity;
 
-import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.Lighting;
-import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.block.entity.TileEntityFlowerJar;
-import net.minecraft.core.enums.LightLayer;
-import net.minecraft.core.world.World;
-import net.minecraft.core.world.WorldSource;
 import org.lwjgl.opengl.GL11;
 
 import static org.lwjgl.opengl.GL11.GL_BLEND;
@@ -21,28 +17,23 @@ import static org.lwjgl.opengl.GL11.GL_SRC_ALPHA;
 public class TileEntityRendererFlowerJar extends TileEntityRenderer<TileEntityFlowerJar> {
 
     @Override
-    public void doRender(Tessellator tessellator, TileEntityFlowerJar tileEntity, double x, double y, double z, float renderPartialTicks) {
-        GL11.glPushMatrix();
+    public void doRender(TessellatorGeneral tessellator, TileEntityFlowerJar tileEntity, double x, double y, double z, float renderPartialTicks) {
+        GLRenderer.pushFrame();
         Block<?> block = Blocks.getBlock(tileEntity.flowerInPot);
-        if(block != null){
-            GL11.glTranslatef((float)x, (float)y, (float)z);
-            TextureRegistry.blockAtlas.bind();
+        if (block != null) {
+            GLRenderer.modelM4f().translate((float) x, (float) y, (float) z);
+            TextureRegistry.worldAtlas.bind();
             float scaleValue = 0.75F;
-            GL11.glScalef(scaleValue, scaleValue, scaleValue);
-            GL11.glTranslatef(0.66F, 0.75F, 0.66F);
+            GLRenderer.modelM4f().scale(scaleValue, scaleValue, scaleValue);
+            GLRenderer.modelM4f().translate(0.66F, 0.75F, 0.66F);
             GL11.glEnable(GL_BLEND);
             GL11.glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
             Lighting.disable();
-            BlockModelDispatcher.getInstance().getDispatch(block).renderStandalone(tessellator, tileEntity.flowerData, getBlockBrightness(tileEntity.worldObj, tileEntity.x, tileEntity.y, tileEntity.z), 1f, tileEntity.worldObj.getLightmapCoord(tileEntity.x, tileEntity.y, tileEntity.z, Minecraft.getMinecraft().isFullbrightEnabled() ? 15 : 0));
+            BlockModelDispatcher.getInstance().getDispatch(block).renderStandalone(tessellator, tileEntity.flowerData, tileEntity.worldObj.getLightmapCoord(tileEntity.x, tileEntity.y, tileEntity.z, 0));
             Lighting.enableLight();
             GL11.glDisable(GL_BLEND);
         }
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
     }
 
-    public float getBlockBrightness(WorldSource blockAccess, int x, int y, int z)
-    {
-        if (Minecraft.getMinecraft().fullbright || LightmapHelper.isLightmapEnabled()) return 1.0f;
-        return blockAccess.getBrightness(x, y, z, 0);
-    }
 }
\ No newline at end of file
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererJarButterfly.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererJarButterfly.java
index 3f95b2e7f..6c5206ab9 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererJarButterfly.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererJarButterfly.java
@@ -1,13 +1,13 @@
 package net.minecraft.client.render.tileentity;
 
 import net.minecraft.client.render.entity.MobRendererButterfly;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.entity.TileEntityJarButterfly;
 import net.minecraft.core.util.helper.MathHelper;
 
 public class TileEntityRendererJarButterfly extends TileEntityRenderer<TileEntityJarButterfly>{
     @Override
-    public void doRender(Tessellator tessellator, TileEntityJarButterfly tileEntity, double x, double y, double z, float partialTick) {
+    public void doRender(TessellatorGeneral tessellator, TileEntityJarButterfly tileEntity, double x, double y, double z, float partialTick) {
         MobRendererButterfly.drawButterfly(tessellator, tileEntity.ticksRan, 0.70f, 0, x + 0.5, y - 0.125 + MathHelper.sin((tileEntity.ticksRan + partialTick)/20) * (0.0625), z + 0.5, partialTick, renderDispatcher.textureManager, "/assets/minecraft/textures/entity/butterfly/" + tileEntity.color.name + "/0_0.png");
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMeshGold.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMeshGold.java
index 29862758c..209b75455 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMeshGold.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMeshGold.java
@@ -1,31 +1,30 @@
 package net.minecraft.client.render.tileentity;
 
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.core.block.entity.TileEntityMeshGold;
-import org.lwjgl.opengl.GL11;
 
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
-import net.minecraft.core.Global;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.util.helper.MathHelper;
-import org.lwjgl.opengl.GL12;
-import org.useless.dragonfly.DisplayPos;
+import net.minecraft.core.world.pos.TilePos;
 
 public class TileEntityRendererMeshGold extends TileEntityRenderer<TileEntityMeshGold> {
 
     @Override
-    public void doRender(Tessellator tessellator, TileEntityMeshGold tileEntity, double x, double y, double z, float renderPartialTicks) {
-        if(tileEntity.filterItem == null) return;
-        GL11.glPushMatrix();
+    public void doRender(TessellatorGeneral tessellator, TileEntityMeshGold tileEntity, double x, double y, double z, float renderPartialTicks) {
+        if (tileEntity.filterItem == null) return;
+        GLRenderer.pushFrame();
 
         final float bobbingOffset = MathHelper.sin((tileEntity.ticksRan + renderPartialTicks) / 10F) * 0.1F + 0.1F;
         final float yaw = (float) Math.toDegrees(((tileEntity.ticksRan + renderPartialTicks) / 20F));
 
-        GL11.glTranslatef((float) x + 0.5f, (float) y + bobbingOffset + 0.25f, (float) z + 0.5f);
+        GLRenderer.modelM4f().translate((float) x + 0.5f, (float) y + bobbingOffset + 0.25f, (float) z + 0.5f);
 
-        float lightLevel = Minecraft.getMinecraft().currentWorld.getLightBrightness(tileEntity.x, tileEntity.y, tileEntity.z);
-        if (Global.accessor.isFullbrightEnabled()) lightLevel = 1.0f;
-        ItemModelDispatcher.getInstance().getDispatch(tileEntity.filterItem).renderItemEntity(tessellator, tileEntity.filterItem, Minecraft.getMinecraft().gameSettings.items3D.value, 1, tileEntity.ticksRan, yaw, lightLevel, 1f, renderPartialTicks);
-        GL11.glPopMatrix();
+
+        ItemModelDispatcher.getInstance().getDispatch(tileEntity.filterItem).renderItemEntity(tessellator, tileEntity.filterItem,
+            Minecraft.getMinecraft().gameSettings.items3D.value, 1, tileEntity.ticksRan, yaw,
+            Minecraft.getMinecraft().currentWorld.getLightmapCoord(new TilePos(tileEntity.x, tileEntity.y, tileEntity.z), 0), renderPartialTicks);
+        GLRenderer.popFrame();
     }
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMobSpawner.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMobSpawner.java
index c3b23b9bf..5b20c4cc1 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMobSpawner.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMobSpawner.java
@@ -3,57 +3,53 @@ package net.minecraft.client.render.tileentity;
 import java.util.HashMap;
 import java.util.Map;
 
-import net.minecraft.client.render.EntityRenderDispatcher;
+import net.minecraft.client.render.EntityRendererDispatcher;
 import net.minecraft.client.render.entity.EntityRenderer;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.world.WorldClient;
 import net.minecraft.core.block.entity.TileEntityMobSpawner;
 import net.minecraft.core.entity.Entity;
 import net.minecraft.core.entity.EntityDispatcher;
 import net.minecraft.core.world.World;
-import org.lwjgl.opengl.GL11;
+import org.joml.Math;
 
-public class TileEntityRendererMobSpawner extends TileEntityRenderer<TileEntityMobSpawner>
-{
+public class TileEntityRendererMobSpawner extends TileEntityRenderer<TileEntityMobSpawner> {
 
-    public TileEntityRendererMobSpawner()
-    {
-        entityHashMap = new HashMap<>();
+    private final Map<String, Entity> entityHashMap;
+
+    public TileEntityRendererMobSpawner() {
+        this.entityHashMap = new HashMap<>();
     }
-    public void onWorldChanged(World world)
-    {
-        entityHashMap.clear();
+
+    public void onWorldChanged(World world) {
+        this.entityHashMap.clear();
     }
 
     @Override
-	public void doRender(Tessellator tessellator, TileEntityMobSpawner mobSpawner, double x, double y, double z,
-                         float partialTick)
-    {
-        GL11.glPushMatrix();
-        GL11.glTranslatef((float)x + 0.5F, (float)y, (float)z + 0.5F);
-        Entity entity = entityHashMap.get(mobSpawner.getMobId());
-        if(entity == null)
-        {
+    public void doRender(TessellatorGeneral tessellator, TileEntityMobSpawner mobSpawner, double x, double y, double z,
+                         float partialTick) {
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) x + 0.5F, (float) y, (float) z + 0.5F);
+        Entity entity = this.entityHashMap.get(mobSpawner.getMobId());
+        if (entity == null) {
             entity = EntityDispatcher.getInstance().createEntityInWorld(mobSpawner.getMobId(), WorldClient.EMPTY_WORLD);
-            entityHashMap.put(mobSpawner.getMobId(), entity);
+            this.entityHashMap.put(mobSpawner.getMobId(), entity);
         }
-        if(entity != null)
-        {
+        if (entity != null) {
             entity.setWorld(mobSpawner.worldObj);
             float f1 = 0.4375F;
-            GL11.glTranslatef(0.0F, 0.4F, 0.0F);
-            GL11.glRotatef((float)(mobSpawner.yaw2 + (mobSpawner.yaw - mobSpawner.yaw2) * (double)partialTick) * 10F, 0.0F, 1.0F, 0.0F);
-            GL11.glRotatef(-30F, 1.0F, 0.0F, 0.0F);
-            GL11.glTranslatef(0.0F, -0.4F, 0.0F);
-            GL11.glScalef(f1, f1, f1);
+            GLRenderer.modelM4f().translate(0.0F, 0.4F, 0.0F);
+            GLRenderer.modelM4f().rotateY((float) Math.toRadians((mobSpawner.yaw2 + (mobSpawner.yaw - mobSpawner.yaw2) * (double) partialTick) * 10F));
+            GLRenderer.modelM4f().rotateX(Math.toRadians(-30F));
+            GLRenderer.modelM4f().translate(0.0F, -0.4F, 0.0F);
+            GLRenderer.modelM4f().scale(f1, f1, f1);
 //            System.out.printf("X: %f, Y: %f, Z: %f\n", x, y, z);
             entity.moveTo(mobSpawner.x, mobSpawner.y, mobSpawner.z, 0.0F, 0.0F);
             EntityRenderer.renderShadows = false;
-            EntityRenderDispatcher.instance.renderEntityWithPosYaw(tessellator, entity, 0.0D, 0.0D, 0.0D, 0.0F, partialTick);
+            EntityRendererDispatcher.instance.renderEntityWithPosYaw(tessellator, entity, 0.0D, 0.0D, 0.0D, 0.0F, partialTick);
             EntityRenderer.renderShadows = true;
         }
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
     }
-
-    private final Map<String, Entity> entityHashMap;
 }
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMovingPiston.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMovingPiston.java
index b319d7bf8..ddab17cb8 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMovingPiston.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererMovingPiston.java
@@ -6,8 +6,11 @@ import net.minecraft.client.render.Lighting;
 import net.minecraft.client.render.block.model.BlockModelDispatcher;
 import net.minecraft.client.render.block.model.BlockModelPiston;
 import net.minecraft.client.render.block.model.BlockModelPistonHead;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.block.entity.TileEntity;
@@ -28,7 +31,7 @@ public class TileEntityRendererMovingPiston extends TileEntityRenderer<TileEntit
     }
 
     @Override
-    public void doRender(Tessellator tessellator, TileEntityMovingPistonBlock tileEntity, double x, double y, double z,
+    public void doRender(TessellatorGeneral tessellator, TileEntityMovingPistonBlock tileEntity, double x, double y, double z,
                          float partialTick) {
         Block<?> block = Blocks.getBlock(tileEntity.getMovedId());
         if (block != null && tileEntity.getProgress(partialTick) < 1.0F) {
@@ -36,11 +39,11 @@ public class TileEntityRendererMovingPiston extends TileEntityRenderer<TileEntit
                 this.container = new BlocksContainer(tileEntity.worldObj);
             }
             TilePos tileEntPos = new TilePos(tileEntity.x, tileEntity.y, tileEntity.z);
-            TextureRegistry.blockAtlas.bind();
+            TextureRegistry.worldAtlas.bind();
             Lighting.disable();
-            GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
-            GL11.glEnable(GL11.GL_BLEND);
-            GL11.glDisable(GL11.GL_CULL_FACE);
+            GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+            GLRenderer.enableState(State.BLEND);
+            GLRenderer.disableState(State.CULL_FACE);
             if (this.mc.isAmbientOcclusionEnabled()) {
                 GL11.glShadeModel(GL11.GL_SMOOTH);
             } else {
@@ -79,10 +82,10 @@ public class TileEntityRendererMovingPiston extends TileEntityRenderer<TileEntit
             TileEntity movedEntity = tileEntity.getMovedEntity();
             TileEntityRenderer<TileEntity> renderer = TileEntityRenderDispatcher.instance.getRenderer(movedEntity);
             if (renderer != null) {
-                GL11.glPushMatrix();
-                GL11.glTranslatef(tileEntity.getXOff(partialTick), tileEntity.getYOff(partialTick), tileEntity.getZOff(partialTick));
+                GLRenderer.pushFrame();
+                GLRenderer.modelM4f().translate(tileEntity.getXOff(partialTick), tileEntity.getYOff(partialTick), tileEntity.getZOff(partialTick));
                 renderer.doRender(tessellator, movedEntity, x, y, z, partialTick);
-                GL11.glPopMatrix();
+                GLRenderer.popFrame();
             }
         }
     }
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererSign.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererSign.java
index 2f6bcfcc5..d88f1ddb7 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererSign.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererSign.java
@@ -8,7 +8,9 @@ import net.minecraft.client.render.LightmapHelper;
 import net.minecraft.client.render.camera.ICamera;
 import net.minecraft.client.render.font.FontRenderer;
 import net.minecraft.client.render.font.SF;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.client.util.helper.Colors;
@@ -23,9 +25,8 @@ import net.minecraft.core.util.helper.DyeColor;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
 import org.jetbrains.annotations.NotNull;
+import org.joml.Math;
 import org.joml.primitives.AABBd;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
 import java.util.ArrayList;
@@ -47,50 +48,40 @@ public class TileEntityRendererSign extends TileEntityRenderer<TileEntitySign> {
     }
 
     @Override
-    public void doRender(final @NotNull Tessellator t, final @NotNull TileEntitySign tileEntity, final double x, final double y, final double z, final float partialTick) {
+    public void doRender(final @NotNull TessellatorGeneral t, final @NotNull TileEntitySign tileEntity, final double x, final double y, final double z, final float partialTick) {
         final Block<?> block = tileEntity.getBlock();
         if (block == null || !(block.getLogic() instanceof BlockLogicSign sign))
             return; // Check to make sure the block for the entity is present before rendering, some edge cases have the tile entity loaded before the block data and can cause a crash
 
-        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glPushMatrix();
+//        GL11.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.pushFrame();
 
         final StaticEntityModel model;
 
         final float scale = 2 / 3f * 1 / 16f;
         final float height;
-        GL11.glTranslatef((float) x + 0.5F, (float) y, (float) z + 0.5F);
+        GLRenderer.modelM4f().translate((float) x + 0.5F, (float) y, (float) z + 0.5F);
         final int meta = tileEntity.getBlockMeta();
         if (sign.isFreeStanding) {
             final float angle = (float) ((meta & BlockLogicSign.MASK_SIDE) * 360) / 16F;
-            GL11.glRotatef(-angle, 0.0F, 1.0F, 0.0F);
+            GLRenderer.modelM4f().rotateY(Math.toRadians(-angle));
             model = getModel("post");
             height = 20;
         } else {
-            final float angle;
-            switch (meta & BlockLogicSign.MASK_SIDE) {
-                case BlockLogicSign.SIDE_NORTH:
-                    angle = 180F;
-                    break;
-                case BlockLogicSign.SIDE_SOUTH:
-                    angle = 0.0F;
-                    break;
-                case BlockLogicSign.SIDE_WEST:
-                    angle = 90F;
-                    break;
-                case BlockLogicSign.SIDE_EAST:
-                default:
-                    angle = -90F;
-                    break;
-            }
-            GL11.glRotatef(-angle, 0.0F, 1.0F, 0.0F);
-            GL11.glTranslatef(0, 0, -11 * scale);
+            final float angle = switch (meta & BlockLogicSign.MASK_SIDE) {
+                case BlockLogicSign.SIDE_NORTH -> 180F;
+                case BlockLogicSign.SIDE_SOUTH -> 0.0F;
+                case BlockLogicSign.SIDE_WEST -> 90F;
+                default -> -90F;
+            };
+            GLRenderer.modelM4f().rotateY(Math.toRadians(-angle));
+            GLRenderer.modelM4f().translate(0, 0, -11 * scale);
             model = getModel("wall");
             height = 13;
         }
 
-        GL11.glPushMatrix();
-        GL11.glScalef(scale, scale, -scale);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().scale(scale, scale, -scale);
         final int colorSign;
         if (Block.hasLogicClass(block, BlockLogicSignPainted.class)) {
             final DyeColor c = ((IPainted) block.getLogic()).fromMetadata(meta);
@@ -101,45 +92,41 @@ public class TileEntityRendererSign extends TileEntityRenderer<TileEntitySign> {
 //            colorSign = 0xa57319;
             colorSign = 0x695e43;
         }
-        GL11.glDisable(GL11.GL_BLEND);
-        model.render(t);
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glPopMatrix();
+        GLRenderer.disableState(State.BLEND);
+        model.render();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.popFrame();
 
         // Render overlay
-        GL11.glPushMatrix();
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glTranslatef(0 * scale, height * scale, 1.05f * scale);
-        GL11.glNormal3f(0, 0, 1);
-        GL11.glDepthMask(false);
-        GL11.glColor4f(1, 1, 1, 1);
+        GLRenderer.pushFrame();
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.modelM4f().translate(0 * scale, height * scale, 1.05f * scale);
+//        GL11.glNormal3f(0, 0, 1);
+        GLRenderer.setDepthMask(false);
+        GLRenderer.setColor4f(1, 1, 1, 1);
         final EnumSignPicture picture = tileEntity.getPicture();
         if (picture != EnumSignPicture.NONE)
             drawTexturedModalRect(1, 0.5, colorSign, TextureRegistry.getTexture(picture.getTextureKey()));
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glPopMatrix();
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.popFrame();
 
         // Render text
         final FontRenderer sr = getFont();
-        float lightLevel = (LightmapHelper.isLightmapEnabled() || this.mc.isFullbrightEnabled()) ? 1 : this.mc.currentWorld.getLightBrightness(tileEntity.x, tileEntity.y, tileEntity.z);
         float lightOffset = 0f;
         if (tileEntity.isGlowing()) {
-            lightLevel = 1f;
             lightOffset = 96f;
-            if (LightmapHelper.isLightmapEnabled()) {
-                LightmapHelper.setLightmapCoord(LightmapHelper.getLightmapCoord(15, 15));
-            }
+            GLRenderer.setLightmapCoord1i(LightmapHelper.getLightmapCoord(15, 15));
         }
 
-        GL11.glPushMatrix();
+        GLRenderer.pushFrame();
         final float scale2 = 0.2666667f * scale;
-        GL11.glTranslatef(0.0F, height * scale, 1.1f * scale);
-        GL11.glScalef(scale2, -scale2, scale2);
-        GL11.glDepthMask(false);
+        GLRenderer.modelM4f().translate(0.0F, height * scale, 1.1f * scale);
+        GLRenderer.modelM4f().scale(scale2, -scale2, scale2);
+        GLRenderer.setDepthMask(false);
         int color = Colors.allSignColors[tileEntity.getColor().id].getARGB();
-        final int r = (int) MathHelper.clamp((Color.redFromInt(color) * lightLevel + lightOffset), 0, 255);
-        final int g = (int) MathHelper.clamp((Color.greenFromInt(color) * lightLevel + lightOffset), 0, 255);
-        final int b = (int) MathHelper.clamp((Color.blueFromInt(color) * lightLevel + lightOffset), 0, 255);
+        final int r = (int) MathHelper.clamp((Color.redFromInt(color) + lightOffset), 0, 255);
+        final int g = (int) MathHelper.clamp((Color.greenFromInt(color) + lightOffset), 0, 255);
+        final int b = (int) MathHelper.clamp((Color.blueFromInt(color) + lightOffset), 0, 255);
         color = Color.intToIntARGB(0, r, g, b);
 
         CharSequence line1 = tileEntity.signText[0];
@@ -172,19 +159,19 @@ public class TileEntityRendererSign extends TileEntityRenderer<TileEntitySign> {
         } else {
             this.textMeshRenderer.render(sr, t, line1, line2, line3, line4, _x, _y, SF.setColor(0, color));
         }
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
 
-        GL11.glDepthMask(true);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glPopMatrix();
-        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.setDepthMask(true);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.popFrame();
+//        GL11.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 
     private static void drawTexturedModalRect(final double width, final double height, final int color, final @NotNull IconCoordinate coordinate) {
         coordinate.parentAtlas.bind();
-        final Tessellator tessellator = Tessellator.instance;
+        final TessellatorGeneral tessellator = GLRenderer.getTessellator();
         tessellator.startDrawingQuads();
-        tessellator.setColorRGBA_I(color, 128);
+        tessellator.setColor2i(color, 128);
         tessellator.addVertexWithUV(-width / 2, height / 2, 0, coordinate.getIconUMin(), coordinate.getIconVMin());
         tessellator.addVertexWithUV(-width / 2, -height / 2, 0, coordinate.getIconUMin(), coordinate.getIconVMax());
         tessellator.addVertexWithUV(width / 2, -height / 2, 0, coordinate.getIconUMax(), coordinate.getIconVMax());
@@ -238,20 +225,20 @@ public class TileEntityRendererSign extends TileEntityRenderer<TileEntitySign> {
         }
 
         public void render(@NotNull final FontRenderer sr,
-                           @NotNull final Tessellator t,
+                           @NotNull final TessellatorGeneral t,
                            @NotNull final CharSequence line1,
                            @NotNull final CharSequence line2,
                            @NotNull final CharSequence line3,
                            @NotNull final CharSequence line4,
                            final int x, final int y, final long config) {
-            GL11.glPushMatrix();
-            GL11.glTranslatef(x, y, 0);
+            GLRenderer.pushFrame();
+            GLRenderer.modelM4f().translate(x, y, 0);
             renderInternal(sr, t, line1, line2, line3, line4, config);
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         }
 
-        private void renderInternal(@NotNull final FontRenderer sr,
-                                    @NotNull final Tessellator t,
+        private void renderInternal(@NotNull final FontRenderer sr, // TODO Rework text caching!
+                                    @NotNull final TessellatorGeneral t,
                                     @NotNull final CharSequence line1,
                                     @NotNull final CharSequence line2,
                                     @NotNull final CharSequence line3,
@@ -263,34 +250,34 @@ public class TileEntityRendererSign extends TileEntityRenderer<TileEntitySign> {
             this.referenceEntry.line4 = line4.toString();
             this.referenceEntry.config = config;
 
-            MeshEntry entry = null;
-            final int size = this.bufferedMeshes.size();
-            for (int i = 0; i < size; i++) {
-                final MeshEntry e = this.bufferedMeshes.get(i);
-                if (this.referenceEntry.equals(e)) {
-                    entry = e;
-                    break;
-                }
-            }
-
-            if (entry != null) {
-                entry.lastUse = System.currentTimeMillis();
-                GL11.glCallList(entry.list);
-            } else {
-                entry = new MeshEntry(line1, line2, line3, line4, config);
-                entry.lastUse = System.currentTimeMillis();
-                entry.list = getDisplayList();
-
-                GL11.glNewList(entry.list, GL11.GL_COMPILE);
-                sr.render(t, line1, -sr.stringWidth(line1) / 2, 0).setConfig(config).call();
-                sr.render(t, line2, -sr.stringWidth(line2) / 2, 10).setConfig(config).call();
-                sr.render(t, line3, -sr.stringWidth(line3) / 2, 20).setConfig(config).call();
-                sr.render(t, line4, -sr.stringWidth(line4) / 2, 30).setConfig(config).call();
-                GL11.glEndList();
-                GL11.glCallList(entry.list);
-
-                this.bufferedMeshes.add(entry);
-            }
+//            MeshEntry entry = null;
+//            final int size = this.bufferedMeshes.size();
+//            for (int i = 0; i < size; i++) {
+//                final MeshEntry e = this.bufferedMeshes.get(i);
+//                if (this.referenceEntry.equals(e)) {
+//                    entry = e;
+//                    break;
+//                }
+//            }
+
+//            if (entry != null) {
+//                entry.lastUse = System.currentTimeMillis();
+//                GL11.glCallList(entry.list);
+//            } else {
+//                entry = new MeshEntry(line1, line2, line3, line4, config);
+//                entry.lastUse = System.currentTimeMillis();
+//                entry.list = getDisplayList();
+//
+//                GL11.glNewList(entry.list, GL11.GL_COMPILE);
+                sr.render(line1, -sr.stringWidth(line1) / 2, 0).setConfig(config).call();
+                sr.render(line2, -sr.stringWidth(line2) / 2, 10).setConfig(config).call();
+                sr.render(line3, -sr.stringWidth(line3) / 2, 20).setConfig(config).call();
+                sr.render(line4, -sr.stringWidth(line4) / 2, 30).setConfig(config).call();
+//                GL11.glEndList();
+//                GL11.glCallList(entry.list);
+//
+//                this.bufferedMeshes.add(entry);
+//            }
 
         }
 
diff --git a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererStatue.java b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererStatue.java
index 2c115e831..822ba11e4 100644
--- a/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererStatue.java
+++ b/game/client/src/main/java/net/minecraft/client/render/tileentity/TileEntityRendererStatue.java
@@ -3,7 +3,10 @@ package net.minecraft.client.render.tileentity;
 import net.minecraft.client.Minecraft;
 import net.minecraft.client.render.TextureManager;
 import net.minecraft.client.render.item.model.ItemModelDispatcher;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.Global;
 import net.minecraft.core.block.Block;
 import net.minecraft.core.block.Blocks;
@@ -12,11 +15,11 @@ import net.minecraft.core.entity.IArmorWearing;
 import net.minecraft.core.enums.HumanArmorShape;
 import net.minecraft.core.item.*;
 import net.minecraft.core.world.World;
+import net.minecraft.core.world.pos.TilePos;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
+import org.joml.Math;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
-import org.lwjgl.opengl.GL12;
 import org.useless.dragonfly.DisplayPos;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
@@ -50,22 +53,22 @@ public class TileEntityRendererStatue extends TileEntityRenderer<TileEntityStatu
         }
     }
 
-    public void renderAt(@NotNull final Tessellator tessellator, @Nullable final ItemStack heldStack, final int meta, final @NotNull Block<?> lowerBlock, final @NotNull TileEntityStatue.Pose pose, final @Nullable IArmorWearing<HumanArmorShape> armorWearer, final double x, final double y, final double z) {
+    public void renderAt(@NotNull final TessellatorGeneral tessellator, @NotNull TileEntityStatue statue, @Nullable final ItemStack heldStack, final int meta, final @NotNull Block<?> lowerBlock, final @NotNull TileEntityStatue.Pose pose, final @Nullable IArmorWearing<HumanArmorShape> armorWearer, final double x, final double y, final double z) {
         final boolean isPigman = lowerBlock == Blocks.STATUE_PIGMAN_LOWER;
 
         final StaticEntityModel model = model(isPigman);
 
-        GL12.glEnable(GL12.GL_RESCALE_NORMAL);
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+//        GL12.glEnable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
         bindTexture(BLOCK_SKIN_MAP.getOrDefault(lowerBlock, BLOCK_SKIN_MAP.get(Blocks.STATUE_STONE_LOWER)));
-        GL11.glPushMatrix();
-        GL11.glTranslated(x + 0.5, y, z + 0.5);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().translate((float) (x + 0.5f), (float) y, (float) (z + 0.5f));
         final float rotation = (float) (meta * 360) / 16F;
-        GL11.glRotatef(-rotation, 0.0F, 1.0F, 0.0F);
-        GL11.glDisable(GL11.GL_CULL_FACE);
+        GLRenderer.modelM4f().rotateY(Math.toRadians(-rotation));
+        GLRenderer.disableState(State.CULL_FACE);
 
-        GL11.glPushMatrix();
-        GL11.glScalef(1 / ENTITY_RENDER_SCALE, 1 / ENTITY_RENDER_SCALE, -1 / ENTITY_RENDER_SCALE);
+        GLRenderer.pushFrame();
+        GLRenderer.modelM4f().scale(1 / ENTITY_RENDER_SCALE, 1 / ENTITY_RENDER_SCALE, -1 / ENTITY_RENDER_SCALE);
         model.resetBones();
         renderModel(tessellator, model, pose);
         if (armorWearer != null) {
@@ -73,45 +76,46 @@ public class TileEntityRendererStatue extends TileEntityRenderer<TileEntityStatu
                 renderArmor(tessellator, armorWearer, i, pose);
             }
         }
-        renderHeldItem(heldStack, isPigman);
-        GL11.glPopMatrix();
+        renderHeldItem(heldStack, Minecraft.getMinecraft().currentWorld.getLightmapCoord(new TilePos(statue.x, statue.y, statue.z), 0), isPigman);
+        GLRenderer.popFrame();
 
-        GL11.glEnable(GL11.GL_CULL_FACE);
-        GL11.glPopMatrix();
-        GL12.glDisable(GL12.GL_RESCALE_NORMAL);
+        GLRenderer.enableState(State.CULL_FACE);
+        GLRenderer.popFrame();
+//        GL12.glDisable(GL12.GL_RESCALE_NORMAL);
     }
 
-    private void renderHeldItem(final @Nullable ItemStack itemStack, final boolean isPigman) {
+    private void renderHeldItem(final @Nullable ItemStack itemStack, int lightmap, final boolean isPigman) {
         if (itemStack != null) {
-            GL12.glEnable(GL12.GL_RESCALE_NORMAL);
-            GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+//            GL12.glEnable(GL12.GL_RESCALE_NORMAL);
+            GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
             model(isPigman).translateToBone("rightItem");
-            GL11.glScalef(-1, 1, 1);
-            GL11.glScalef(ENTITY_RENDER_SCALE, ENTITY_RENDER_SCALE, ENTITY_RENDER_SCALE);
-            ItemModelDispatcher.getInstance().getDispatch(itemStack).render(Tessellator.instance, null, itemStack, DisplayPos.THIRD_PERSON_RIGHT_HAND, true, 1, 1f, 1f, 1f, false);
-            GL11.glEnable(GL11.GL_CULL_FACE);
-            GL12.glDisable(GL12.GL_RESCALE_NORMAL);
+            GLRenderer.modelM4f().scale(-1, 1, 1);
+            GLRenderer.modelM4f().scale(ENTITY_RENDER_SCALE, ENTITY_RENDER_SCALE, ENTITY_RENDER_SCALE);
+            ItemModelDispatcher.getInstance().getDispatch(itemStack).render(GLRenderer.getTessellator(), null, itemStack, DisplayPos.THIRD_PERSON_RIGHT_HAND, true, 1,
+               lightmap, 1f, false);
+            GLRenderer.enableState(State.CULL_FACE);
+//            GL12.glDisable(GL12.GL_RESCALE_NORMAL);
         }
     }
 
 
-    private void renderModel(@NotNull final Tessellator tessellator, @NotNull final StaticEntityModel model, @NotNull final TileEntityStatue.Pose pose) {
+    private void renderModel(@NotNull final TessellatorGeneral tessellator, @NotNull final StaticEntityModel model, @NotNull final TileEntityStatue.Pose pose) {
         model.getTransform("leftArm").rotX = pose.leftArmPitch;
         model.getTransform("rightArm").rotX = pose.rightArmPitch;
         model.getTransform("leftLeg").rotX = pose.leftLegPitch;
         model.getTransform("rightLeg").rotX = pose.rightLegPitch;
         model.getTransform("head").rotX = pose.headPitch;
         model.getTransform("head").rotY = pose.headYaw;
-        model.render(tessellator);
+        model.render();
     }
 
     @Override
-    public void doRender(@NotNull final Tessellator tessellator, @NotNull final TileEntityStatue tileEntity, final double x, final double y, final double z, final float partialTick) {
-        renderAt(tessellator, tileEntity.getHeldItem(), tileEntity.getBlockMeta(), tileEntity.getBlock(), tileEntity.getPose(), tileEntity, x, y, z);
+    public void doRender(@NotNull final TessellatorGeneral tessellator, @NotNull final TileEntityStatue tileEntity, final double x, final double y, final double z, final float partialTick) {
+        renderAt(tessellator, tileEntity, tileEntity.getHeldItem(), tileEntity.getBlockMeta(), tileEntity.getBlock(), tileEntity.getPose(), tileEntity, x, y, z);
         renderShadow(Minecraft.getMinecraft().currentWorld, tessellator, tileEntity.x, tileEntity.y, tileEntity.z, x, y, z, 2.0f, partialTick);
     }
 
-    private boolean renderArmor(final @NotNull Tessellator tessellator, final @NotNull IArmorWearing<? super HumanArmorShape> armorWearer, final int layer, final TileEntityStatue.@NotNull Pose pose) {
+    private boolean renderArmor(final @NotNull TessellatorGeneral tessellator, final @NotNull IArmorWearing<? super HumanArmorShape> armorWearer, final int layer, final TileEntityStatue.@NotNull Pose pose) {
         final ItemStack itemstack = armorWearer.getItemInArmorSlot(HumanArmorShape.values()[(armorWearer.getNumArmorSlots() - 1) - layer]);
         if (itemstack != null) {
             final Item item = itemstack.getItem();
@@ -170,14 +174,14 @@ public class TileEntityRendererStatue extends TileEntityRenderer<TileEntityStatu
         return false;
     }
 
-    private void renderShadow(final @NotNull World world, final @NotNull Tessellator tessellator, final int bx, final int by, final int bz, final double rx, final double ry, final double rz, final float opacity, final float partialTick) {
-        GL11.glEnable(GL11.GL_BLEND);
-        GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
+    private void renderShadow(final @NotNull World world, final @NotNull TessellatorGeneral tessellator, final int bx, final int by, final int bz, final double rx, final double ry, final double rz, final float opacity, final float partialTick) {
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
         final TextureManager textureManager = this.renderDispatcher.textureManager;
         textureManager.bindTexture(textureManager.loadTexture("/assets/minecraft/textures/misc/shadow.png"));
         final float shadowSize = 0.5f;
         final float shadowOffs = 0.8f / 2.0f;
-        GL11.glDepthMask(false);
+        GLRenderer.setDepthMask(false);
         tessellator.startDrawingQuads();
 
         final int blockId = world.getBlockId(bx, by - 1, bz);
@@ -186,12 +190,12 @@ public class TileEntityRendererStatue extends TileEntityRenderer<TileEntityStatu
         }
 
         tessellator.draw();
-        GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F);
-        GL11.glDisable(GL11.GL_BLEND);
-        GL11.glDepthMask(true);
+        GLRenderer.setColor4f(1.0F, 1.0F, 1.0F, 1.0F);
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.setDepthMask(true);
     }
 
-    private void renderShadowOnBlock(final @NotNull World world, final @NotNull Tessellator tessellator, final @NotNull Block<?> block, final int bx, final int by, final int bz, final double rx, final double ry, final double rz,
+    private void renderShadowOnBlock(final @NotNull World world, final @NotNull TessellatorGeneral tessellator, final @NotNull Block<?> block, final int bx, final int by, final int bz, final double rx, final double ry, final double rz,
                                      final float opacity, final float size) {
         if (!block.isCubeShaped()) {
             return;
@@ -205,7 +209,7 @@ public class TileEntityRendererStatue extends TileEntityRenderer<TileEntityStatu
         if (alpha > 1.0D) {
             alpha = 1.0D;
         }
-        tessellator.setColorRGBA_F(1.0F, 1.0F, 1.0F, (float) alpha);
+        tessellator.setColor4f(1.0F, 1.0F, 1.0F, (float) alpha);
         final AABBdc aabb = block.getCollisionBoundingBoxFromPool(world, bx, by - 1, bz);
         if (aabb == null) {
             return;
diff --git a/game/client/src/main/java/net/minecraft/client/render/window/GameWindowGLFW.java b/game/client/src/main/java/net/minecraft/client/render/window/GameWindowGLFW.java
index 9b7cac3e1..130968d24 100644
--- a/game/client/src/main/java/net/minecraft/client/render/window/GameWindowGLFW.java
+++ b/game/client/src/main/java/net/minecraft/client/render/window/GameWindowGLFW.java
@@ -20,11 +20,13 @@ import javax.swing.JFrame;
 
 import com.mojang.logging.CategorizedLogger;
 import com.mojang.logging.LogUtils;
+import net.minecraft.client.render.OpenGLHelper;
 import net.minecraft.client.util.debug.GLFWLoggerCallback;
 import net.minecraft.client.util.debug.OpenGLLoggerCallback;
 import net.minecraft.core.BuildChannel;
 import net.minecraft.core.Global;
 import net.minecraft.core.Version;
+import net.minecraft.core.enums.EnumOS;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.lwjgl.PointerBuffer;
@@ -104,15 +106,39 @@ public class GameWindowGLFW implements GameWindow {
         glfwWindowHint(GLFW_VISIBLE, 0);
         glfwWindowHint(GLFW_AUTO_ICONIFY, 1);
         glfwWindowHint(GLFW_DECORATED, 1);
-
-        // Create window
-        this.window = glfwCreateWindow(width, height, "Better than Adventure! " + Global.VERSION, 0, 0);
-        if (this.window == NULL) {
-            try (MemoryStack stack = MemoryStack.stackPush()) {
-                PointerBuffer b = stack.callocPointer(1);
-                glfwGetError(b);
-                throw new NullPointerException(b.getStringASCII());
+        glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GLFW_TRUE);
+
+        // Iterating through GL versions because theres not way to just request "Highest but atleast X.X" and if forward compat is set on then not request a version causes a crash
+        for (int i = 0; i < OpenGLHelper.versionPairs.length; i += 2) {
+            glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, OpenGLHelper.versionPairs[i]);
+            glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, OpenGLHelper.versionPairs[i + 1]);
+
+            // Create window
+            this.window = glfwCreateWindow(width, height, "Better than Adventure! " + Global.VERSION, 0, 0);
+            if (this.window == NULL) {
+                if (i == (OpenGLHelper.versionPairs.length - 2)) {
+                    try (MemoryStack stack = MemoryStack.stackPush()) {
+                        PointerBuffer b = stack.callocPointer(1);
+                        glfwGetError(b);
+                        throw new NullPointerException("Failed to create window: " + b.getStringASCII());
+                    }
+                }
+                continue;
             }
+            break;
+        }
+        // OpenGL setup
+        glfwMakeContextCurrent(this.window);
+        GLCapabilities capabilities = GL.createCapabilities(true);
+        OpenGLHelper.testCapabilities(capabilities);
+
+        if (capabilities.OpenGL43 && debug) {
+            GL11.glEnable(GL43.GL_DEBUG_OUTPUT);
+            this.glDebugMessageCallback = new OpenGLLoggerCallback();
+            GL43.glDebugMessageCallback(this.glDebugMessageCallback, NULL);
+            LOGGER.info("GL4.3 supported, enabling GL Error logging");
+        } else {
+            LOGGER.info("GL4.3 not supported, cannot enable GL Error logging");
         }
 
         // Set widths and heights
@@ -154,39 +180,29 @@ public class GameWindowGLFW implements GameWindow {
         });
 
         // Setup Icon
-        iconLabel:
-        {
-            int[] resolutions = new int[]{16, 32, 64, 128, 256};
-            GLFWImage.Buffer gb = GLFWImage.create(resolutions.length);
-            for (int res : resolutions) {
-                ByteBuffer icon = getImageBuffer("/icon/" + res + ".png");
-                if (icon == null) {
-                    LOGGER.error("Icon at resolution '{}' is null! Skipping icons!", res);
-                    gb.close();
-                    break iconLabel;
+        if (Minecraft.getOs() != EnumOS.macos) { // MacOs doesn't support icons
+            iconLabel:
+            {
+                int[] resolutions = new int[]{16, 32, 64, 128, 256};
+                GLFWImage.Buffer gb = GLFWImage.create(resolutions.length);
+                for (int res : resolutions) {
+                    ByteBuffer icon = getImageBuffer("/icon/" + res + ".png");
+                    if (icon == null) {
+                        LOGGER.error("Icon at resolution '{}' is null! Skipping icons!", res);
+                        gb.close();
+                        break iconLabel;
+                    }
+                    GLFWImage iconGI = GLFWImage.create().set(res, res, icon);
+                    gb.put(iconGI);
+                    this.stbiIconImages.add(icon);
                 }
-                GLFWImage iconGI = GLFWImage.create().set(res, res, icon);
-                gb.put(iconGI);
-                this.stbiIconImages.add(icon);
+                glfwSetWindowIcon(this.window, gb.flip());
             }
-            glfwSetWindowIcon(this.window, gb.flip());
         }
 
         // Show window
         glfwShowWindow(this.window);
 
-        // OpenGL setup
-        glfwMakeContextCurrent(this.window);
-        GLCapabilities capabilities = GL.createCapabilities();
-        if (capabilities.OpenGL43 && debug) {
-            GL11.glEnable(GL43.GL_DEBUG_OUTPUT);
-            this.glDebugMessageCallback = new OpenGLLoggerCallback();
-            GL43.glDebugMessageCallback(this.glDebugMessageCallback, NULL);
-            LOGGER.info("GL4.3 supported, enabling GL Error logging");
-        } else {
-            LOGGER.info("GL4.3 not supported, cannot enable GL Error logging");
-        }
-
         // Input setup
         Display.setWindow(this);
 
diff --git a/game/client/src/main/java/net/minecraft/client/util/debug/DebugRender.java b/game/client/src/main/java/net/minecraft/client/util/debug/DebugRender.java
index 8d1c17267..61584af1b 100644
--- a/game/client/src/main/java/net/minecraft/client/util/debug/DebugRender.java
+++ b/game/client/src/main/java/net/minecraft/client/util/debug/DebugRender.java
@@ -1,218 +1,218 @@
 package net.minecraft.client.util.debug;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import net.minecraft.client.render.font.FontRenderer;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.Shaders;
+import net.minecraft.client.render.renderer.State;
 import net.minecraft.core.util.debug.Debug;
 import org.lwjgl.input.Keyboard;
 import org.lwjgl.opengl.Display;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
 import net.minecraft.core.util.debug.Debug.Profiler;
 import net.minecraft.core.util.helper.MathHelper;
 
 public class DebugRender {
-	
-	private static Profiler selectedProfiler = Debug.baseProfiler;
-	private static final long[] frametimes = new long[512];
-	private static final long[] baseframetimes = new long[512];
-	private static int pos = 0;
-	private static int scale = 200000;
-	private static int selection = 0;
-	
-	public static void onDebugMenuOpened() {
-	}
-	
-	public static boolean keyPressed(int key) {
-		if(key == Keyboard.KEY_LEFT) {
-			if(selectedProfiler.parent != null) {
-				Profiler prev = selectedProfiler;
-				set(selectedProfiler.parent);
-				selection = selectedProfiler.allProfilers.indexOf(prev);
-			}
-			return true;
-		}
-		if(key == Keyboard.KEY_UP) {
-			if(selection == 0) {
-				selection = selectedProfiler.allProfilers.size() - 1;
-			}else {
-				selection--;
-			}
-			return true;
-		}
-		if(key == Keyboard.KEY_DOWN) {
-			if(selection >= selectedProfiler.allProfilers.size() - 1) {
-				selection = 0;
-			}else {
-				selection++;
-			}
-			return true;
-		}
-		if(key == Keyboard.KEY_RIGHT) {
-			if(selection >= 0 && selection < selectedProfiler.allProfilers.size()) {
-				set(selectedProfiler.allProfilers.get(selection));
-				selection = 0;
-			}
-			return true;
-		}
-		
-		return false;
-	}
-	
-	private static void set(Profiler profiler) {
-		selectedProfiler = profiler;
-		resetFrametimes();
-	}
-	
-	public static void render(FontRenderer sr) {
-		frametimes[pos] = selectedProfiler.time;
-		baseframetimes[pos] = Debug.baseProfiler.time;
-		pos++;
-		if(pos >= frametimes.length) pos = 0;
-		
-		int w = Display.getWidth();
-		int h = Display.getHeight();
-		
-		glMatrixMode(GL_PROJECTION);
-		glLoadIdentity();
-		glOrtho(0, w, h, 0, -1, 1);
-		
-		glMatrixMode(GL_MODELVIEW);
-		glLoadIdentity();
-		
-		glDisable(GL_DEPTH_TEST);
-		glEnable(GL_ALPHA_TEST);
-		glDisable(GL_TEXTURE_2D);
-		glDisable(GL_CULL_FACE);
-		glDisable(GL_LIGHTING);
-		glEnable(GL_BLEND);
-		glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-		
-		Tessellator t = Tessellator.instance;
-		
-		int x = w - frametimes.length;
-		int y = h;
-		
-		if(selectedProfiler != Debug.baseProfiler) {
-			if(w > frametimes.length + baseframetimes.length) {
-				drawFrameTimes(t, x, y, baseframetimes);
-			}
-			drawFrameTimes(t, 0, y, frametimes);
-		}else {
-			drawFrameTimes(t, 0, y, baseframetimes);
-		}
-
-		glDisable(GL_BLEND);
-		glEnable(GL_TEXTURE_2D);
-		glColor4d(1.0, 1.0, 1.0, 1.0);
-		
-		int lineHeight = 8;
-		int x1 = frametimes.length;
-		int y1 = h - (selectedProfiler.allProfilers.size() + 1) * lineHeight * 2;
+
+    private static Profiler selectedProfiler = Debug.baseProfiler;
+    private static final long[] frametimes = new long[512];
+    private static final long[] baseframetimes = new long[512];
+    private static int pos = 0;
+    private static int scale = 200000;
+    private static int selection = 0;
+
+    public static void onDebugMenuOpened() {
+    }
+
+    public static boolean keyPressed(int key) {
+        if (key == Keyboard.KEY_LEFT) {
+            if (selectedProfiler.parent != null) {
+                Profiler prev = selectedProfiler;
+                set(selectedProfiler.parent);
+                selection = selectedProfiler.allProfilers.indexOf(prev);
+            }
+            return true;
+        }
+        if (key == Keyboard.KEY_UP) {
+            if (selection == 0) {
+                selection = selectedProfiler.allProfilers.size() - 1;
+            } else {
+                selection--;
+            }
+            return true;
+        }
+        if (key == Keyboard.KEY_DOWN) {
+            if (selection >= selectedProfiler.allProfilers.size() - 1) {
+                selection = 0;
+            } else {
+                selection++;
+            }
+            return true;
+        }
+        if (key == Keyboard.KEY_RIGHT) {
+            if (selection >= 0 && selection < selectedProfiler.allProfilers.size()) {
+                set(selectedProfiler.allProfilers.get(selection));
+                selection = 0;
+            }
+            return true;
+        }
+
+        return false;
+    }
+
+    private static void set(Profiler profiler) {
+        selectedProfiler = profiler;
+        resetFrametimes();
+    }
+
+    public static void render(FontRenderer sr) {
+        frametimes[pos] = selectedProfiler.time;
+        baseframetimes[pos] = Debug.baseProfiler.time;
+        pos++;
+        if (pos >= frametimes.length) pos = 0;
+
+        int w = Display.getWidth();
+        int h = Display.getHeight();
+
+        GLRenderer.pushFrame();
+        GLRenderer.projectionM4f().identity().ortho(0, w, h, 0, -1, 1);
+        GLRenderer.viewM4f().identity();
+        GLRenderer.modelM4f().identity();
+
+//		glEnable(GL_ALPHA_TEST);
+        GLRenderer.setShader(Shaders.COLOR);
+        GLRenderer.disableState(State.DEPTH_TEST);
+        GLRenderer.disableState(State.CULL_FACE);
+//		glDisable(GL_LIGHTING);
+        GLRenderer.enableState(State.BLEND);
+        GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+
+        TessellatorGeneral t = GLRenderer.getTessellator();
+
+        int x = w - frametimes.length;
+        int y = h;
+
+        if (selectedProfiler != Debug.baseProfiler) {
+            if (w > frametimes.length + baseframetimes.length) {
+                drawFrameTimes(t, x, y, baseframetimes);
+            }
+            drawFrameTimes(t, 0, y, frametimes);
+        } else {
+            drawFrameTimes(t, 0, y, baseframetimes);
+        }
+
+        GLRenderer.disableState(State.BLEND);
+        GLRenderer.setShader(Shaders.INTERFACE);
+        GLRenderer.setColor4f(1f, 1f, 1f, 1f);
+
+        int lineHeight = 8;
+        int x1 = frametimes.length;
+        int y1 = h - (selectedProfiler.allProfilers.size() + 1) * lineHeight * 2;
 //		int y1 = h - 33333333 / scale;
-		glTranslated(x1, y1, 0);
-		x1 = 0;
-		y1 = 0;
-		glScaled(2.0, 2.0, 2.0);
-		
-		int fps = Debug.getFps();
-		if(fps >= 0) {
-			sr.render(t, "fps: " + fps, x1, y1 - 2 * lineHeight).call();
-		}
-		sr.render(t, "avg: " + (getAvgTime(frametimes) / 1000.0) + " ms", x1, y1 - lineHeight).call();
-		sr.render(t, selectedProfiler.name + ": ", x1, y1).call();
-		for(int i=0; i < selectedProfiler.allProfilers.size(); i++) {
-			Profiler profiler = selectedProfiler.allProfilers.get(i);
-
-			int color = 0xFFFFFFFF;
-			if(i == selection) {
-				color = 0xFF00FFFF;
-			}
-			sr.render(t, i + ": " + profiler.name, x1, y1 + (i + 1) * lineHeight).setColor(color).call();
-		}
-		glEnable(GL_ALPHA_TEST);
-	}
-	
-	private static long getAvgTime(long[] frametimes) {
-		long avg = 0;
-		int count = 0;
-		for(int i=0; i < frametimes.length; i++) {
-			long time = frametimes[i];
-			if(time > 0) {
-				avg += frametimes[i] / 1000;
-				count++;
-			}
-		}
-		if(count == 0) {
-			return 1;
-		}
-		avg /= count;
-		return avg;
-	}
-	
-	private static void drawFrameTimes(Tessellator tessellator, int x, int y, long[] frametimes) {
-		int h1 = 16666666 / scale;
-		int h2 = 33333333 / scale;
-		
-		tessellator.startDrawingQuads();
-		tessellator.setColorRGBA(0, 0, 0, 127);
-		drawRectangle(tessellator, x, y - h2, frametimes.length, h2);
-		drawRectangle(tessellator, x, y - h1, frametimes.length, h1);
-		tessellator.setColorOpaque_I(0xFFFFFF);
-
-
-		
-		for(int i=0; i < frametimes.length; i++) {
-			float brightness = ((i - pos) & (frametimes.length - 1)) / (float) frametimes.length;
-			brightness = brightness * brightness;
-			int b = MathHelper.clamp((int) (brightness * 255.0f), 0, 255);
-			tessellator.setColorOpaque_I(b << 16 | b << 8 | b);
-			
-			int time = (int) (frametimes[i] / scale);
-			drawRectangle(tessellator, x + i, y - time, 1, time);
-		}
-
-		final int tickLagHeight = (int) ((1000/20d * 1000 * 1000)/(double) scale);
-
-		tessellator.setColorOpaque_I(0xFF0000);
-		drawRectangle(tessellator, x, y - tickLagHeight, frametimes.length, 1);
-
-		Minecraft mc = Minecraft.getMinecraft();
-		if (mc.gameSettings.customFpsLimit.value > 0 || mc.gameSettings.enableVsync.value){
-			tessellator.setColorOpaque_I(0x00FF00);
-			int fps;
-			if (mc.gameSettings.enableVsync.value){
-				fps = mc.gameWindow.getFrequency(); // Cap fps when minimized
-			} else {
-				fps = mc.gameSettings.customFpsLimit.value;
-			}
-
-			int frameLagHeight = (int) ((1000d/fps * 1000 * 1000)/scale);
-			drawRectangle(tessellator, x, y - frameLagHeight, frametimes.length, 1);
-		}
-
-		tessellator.draw();
-	}
-	
-	private static void drawRectangle(Tessellator tessellator, int x, int y, int w, int h) {
-		tessellator.addVertex(x, y, 0);
-		tessellator.addVertex(x+w, y, 0);
-		tessellator.addVertex(x+w, y+h, 0);
-		tessellator.addVertex(x, y+h, 0);
-	}
-	
-	private static void resetFrametimes() {
-		for(int i=0; i < frametimes.length; i++) {
-			frametimes[i] = 0L;
-		}
+        GLRenderer.modelM4f().translate(x1, y1, 0);
+        x1 = 0;
+        y1 = 0;
+        GLRenderer.modelM4f().scale(2.0f, 2.0f, 2.0f);
+
+        int fps = Debug.getFps();
+        if (fps >= 0) {
+            sr.render("fps: " + fps, x1, y1 - 2 * lineHeight).call();
+        }
+        sr.render("avg: " + (getAvgTime(frametimes) / 1000.0) + " ms", x1, y1 - lineHeight).call();
+        sr.render(selectedProfiler.name + ": ", x1, y1).call();
+        for (int i = 0; i < selectedProfiler.allProfilers.size(); i++) {
+            Profiler profiler = selectedProfiler.allProfilers.get(i);
+
+            int color = 0xFFFFFFFF;
+            if (i == selection) {
+                color = 0xFF00FFFF;
+            }
+            sr.render(i + ": " + profiler.name, x1, y1 + (i + 1) * lineHeight).setColor(color).call();
+        }
+//		glEnable(GL_ALPHA_TEST);
+        GLRenderer.popFrame();
+    }
+
+    private static long getAvgTime(long[] frametimes) {
+        long avg = 0;
+        int count = 0;
+        for (int i = 0; i < frametimes.length; i++) {
+            long time = frametimes[i];
+            if (time > 0) {
+                avg += frametimes[i] / 1000;
+                count++;
+            }
+        }
+        if (count == 0) {
+            return 1;
+        }
+        avg /= count;
+        return avg;
+    }
+
+    private static void drawFrameTimes(TessellatorGeneral tessellator, int x, int y, long[] frametimes) {
+        int h1 = 16666666 / scale;
+        int h2 = 33333333 / scale;
+
+        tessellator.startDrawingQuads();
+        tessellator.setColor4i(0, 0, 0, 127);
+        drawRectangle(tessellator, x, y - h2, frametimes.length, h2);
+        drawRectangle(tessellator, x, y - h1, frametimes.length, h1);
+        tessellator.setColorOpaque1i(0xFFFFFF);
+
+
+        for (int i = 0; i < frametimes.length; i++) {
+            float brightness = ((i - pos) & (frametimes.length - 1)) / (float) frametimes.length;
+            brightness = brightness * brightness;
+            int b = MathHelper.clamp((int) (brightness * 255.0f), 0, 255);
+            tessellator.setColorOpaque1i(b << 16 | b << 8 | b);
+
+            int time = (int) (frametimes[i] / scale);
+            drawRectangle(tessellator, x + i, y - time, 1, time);
+        }
+
+        final int tickLagHeight = (int) ((1000 / 20d * 1000 * 1000) / (double) scale);
+
+        tessellator.setColorOpaque1i(0xFF0000);
+        drawRectangle(tessellator, x, y - tickLagHeight, frametimes.length, 1);
+
+        Minecraft mc = Minecraft.getMinecraft();
+        if (mc.gameSettings.customFpsLimit.value > 0 || mc.gameSettings.enableVsync.value) {
+            tessellator.setColorOpaque1i(0x00FF00);
+            int fps;
+            if (mc.gameSettings.enableVsync.value) {
+                fps = mc.gameWindow.getFrequency(); // Cap fps when minimized
+            } else {
+                fps = mc.gameSettings.customFpsLimit.value;
+            }
+
+            int frameLagHeight = (int) ((1000d / fps * 1000 * 1000) / scale);
+            drawRectangle(tessellator, x, y - frameLagHeight, frametimes.length, 1);
+        }
+
+        tessellator.draw();
+    }
+
+    private static void drawRectangle(TessellatorGeneral tessellator, int x, int y, int w, int h) {
+        tessellator.addVertex(x, y, 0);
+        tessellator.addVertex(x + w, y, 0);
+        tessellator.addVertex(x + w, y + h, 0);
+        tessellator.addVertex(x, y + h, 0);
+    }
+
+    private static void resetFrametimes() {
+        for (int i = 0; i < frametimes.length; i++) {
+            frametimes[i] = 0L;
+        }
 //		for(int i=0; i < baseframetimes.length; i++) {
 //			baseframetimes[i] = 0L;
 //		}
-	}
-	
-	public static void dontRender() {
-		
-	}
+    }
+
+    public static void dontRender() {
+
+    }
 
 }
diff --git a/game/client/src/main/java/net/minecraft/client/util/helper/ItemDragHandler.java b/game/client/src/main/java/net/minecraft/client/util/helper/ItemDragHandler.java
index 063c8600f..85b158547 100644
--- a/game/client/src/main/java/net/minecraft/client/util/helper/ItemDragHandler.java
+++ b/game/client/src/main/java/net/minecraft/client/util/helper/ItemDragHandler.java
@@ -1,14 +1,13 @@
 package net.minecraft.client.util.helper;
 
-import static org.lwjgl.opengl.GL11.*;
-
 import java.util.ArrayList;
-import java.util.HashSet;
 import java.util.List;
-import java.util.Set;
 
 import it.unimi.dsi.fastutil.ints.IntArraySet;
 import it.unimi.dsi.fastutil.ints.IntSet;
+import net.minecraft.client.render.renderer.BlendFactor;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.renderer.State;
 import org.lwjgl.input.Keyboard;
 
 import net.minecraft.client.Minecraft;
@@ -28,7 +27,7 @@ public class ItemDragHandler extends Gui {
 	private int renderOffsetX;
 	private int renderOffsetY;
 	
-	private IntSet cancelRelease = new IntArraySet();
+	private final IntSet cancelRelease = new IntArraySet();
 	
 	///////////////////////
 	
@@ -54,36 +53,36 @@ public class ItemDragHandler extends Gui {
 	}
 	
 	public void drawScreen(int mouseX, int mouseY, float partialTicks) {
-		renderOffsetX = 0;
-		renderOffsetY = 0;
+        this.renderOffsetX = 0;
+        this.renderOffsetY = 0;
 		
 		if(isDragging()) {
 			Slot slot = getSlotAt(mouseX, mouseY);
 			
 			onDragOverSlot(slot);
 			
-			if(draggedSlots.size() > 1) {
-				renderItemStack = draggingItemStack.copy();
-				renderItemStack.stackSize = 1;
+			if(this.draggedSlots.size() > 1) {
+                this.renderItemStack = this.draggingItemStack.copy();
+                this.renderItemStack.stackSize = 1;
 
-				boolean isCreativeDragging = draggingButton == 2 && !mc.thePlayer.getGamemode().consumeBlocks();
+				boolean isCreativeDragging = this.draggingButton == 2 && !this.mc.thePlayer.getGamemode().consumeBlocks();
 				
 				if(isCreativeDragging) {
-					renderItemStackCount = draggingItemStack.getMaxStackSize();
-				}else if(draggingButton == 1) {
-					renderItemStackCount = 1;
+                    this.renderItemStackCount = this.draggingItemStack.getMaxStackSize();
+				}else if(this.draggingButton == 1) {
+                    this.renderItemStackCount = 1;
 				}else {
-					renderItemStackCount = draggingItemStack.stackSize / draggedSlots.size();
+                    this.renderItemStackCount = this.draggingItemStack.stackSize / this.draggedSlots.size();
 				}
 				
-				for(int i=0; i < draggedSlots.size(); i++) {
-					drawSlotOverlayWhileDragging(draggedSlots.get(i));
+				for(int i = 0; i < this.draggedSlots.size(); i++) {
+					drawSlotOverlayWhileDragging(this.draggedSlots.get(i));
 				}
 				
 				if(isCreativeDragging) {
-					renderItemStack.stackSize = 1;
+                    this.renderItemStack.stackSize = 1;
 				}else {
-					renderItemStack.stackSize = draggingItemStack.stackSize - (draggedSlots.size() * renderItemStackCount);	
+                    this.renderItemStack.stackSize = this.draggingItemStack.stackSize - (this.draggedSlots.size() * this.renderItemStackCount);
 				}
 			}
 		}
@@ -92,15 +91,15 @@ public class ItemDragHandler extends Gui {
 	private void onDragOverSlot(Slot slot) {
 		if(slot == null) return;
 		
-		boolean isCreativeDragging = draggingButton == 2 && !mc.thePlayer.getGamemode().consumeBlocks();
-		if(draggedSlots.size() >= draggingItemStack.stackSize && !isCreativeDragging) {
+		boolean isCreativeDragging = this.draggingButton == 2 && !this.mc.thePlayer.getGamemode().consumeBlocks();
+		if(this.draggedSlots.size() >= this.draggingItemStack.stackSize && !isCreativeDragging) {
 			return;
 		}
 		
-		if(slot.mayPlace(draggingItemStack) && slot.enableDragAndPickup()) {
-			if(slot.getItemStack() == null || slot.getItemStack().canStackWith(draggingItemStack)) {
-				if(!draggedSlots.contains(slot)) {
-					draggedSlots.add(slot);
+		if(slot.mayPlace(this.draggingItemStack) && slot.enableDragAndPickup()) {
+			if(slot.getItemStack() == null || slot.getItemStack().canStackWith(this.draggingItemStack)) {
+				if(!this.draggedSlots.contains(slot)) {
+                    this.draggedSlots.add(slot);
 				}
 			}
 		}
@@ -108,24 +107,23 @@ public class ItemDragHandler extends Gui {
 	
 	private void drawSlotOverlayWhileDragging(Slot slot) {
 		if(slot == null) throw new NullPointerException("Slot is null");
-		if(draggingItemStack == null) throw new NullPointerException("Stack is null!");
+		if(this.draggingItemStack == null) throw new NullPointerException("Stack is null!");
 
 		ItemStack stack = slot.getItemStack();
-		
-		glDisable(GL_TEXTURE_2D);
-		glEnable(GL_BLEND);
-		glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-		
-		drawRectWidthHeight(renderOffsetX + slot.x, renderOffsetY + slot.y, 16, 16, 0x80ffffff);
-		
-		glDisable(GL_BLEND);
-		glEnable(GL_TEXTURE_2D);
-		
-		renderItemStack.stackSize = renderItemStackCount;
+
+		GLRenderer.pushFrame();
+		GLRenderer.enableState(State.BLEND);
+		GLRenderer.setBlendFunc(BlendFactor.SRC_ALPHA, BlendFactor.ONE_MINUS_SRC_ALPHA);
+
+		drawRectWidthHeight(this.renderOffsetX + slot.x, this.renderOffsetY + slot.y, 16, 16, 0x80ffffff);
+
+		GLRenderer.popFrame();
+
+        this.renderItemStack.stackSize = this.renderItemStackCount;
 		if(stack != null) {
-			renderItemStack.stackSize = Math.min(renderItemStack.getMaxStackSize(), renderItemStack.stackSize + stack.stackSize);
+            this.renderItemStack.stackSize = Math.min(this.renderItemStack.getMaxStackSize(), this.renderItemStack.stackSize + stack.stackSize);
 		}
-		itemElement.render(renderItemStack, slot.x, slot.y);
+        this.itemElement.render(this.renderItemStack, slot.x, slot.y);
 	}
 	
 	public void mouseEvent(final int x, final int y, int button, boolean pressed) {
@@ -142,24 +140,23 @@ public class ItemDragHandler extends Gui {
 		
 		if(pressed) {
 			if(mod) {
-				cancelRelease.add(button);
-				container.clickInventory(x, y, button);
+                this.cancelRelease.add(button);
+                this.container.clickInventory(x, y, button);
 			}else {
 				mousePressed(x, y, slot, button);
 			}
 		}else {
-			if(cancelRelease.contains(button)) {
-				cancelRelease.remove(button);
+			if(this.cancelRelease.contains(button)) {
+                this.cancelRelease.remove(button);
 				return;
 			}
 			mouseReleased(x, y, slot, button);
 		}
-		
-		return;
-	}
+
+    }
 	
 	public void click(InventoryAction action, int[] args) {
-		mc.playerController.handleInventoryMouseClick(container.inventorySlots.containerId, action, args, mc.thePlayer);
+        this.mc.playerController.handleInventoryMouseClick(this.container.inventorySlots.containerId, action, args, this.mc.thePlayer);
 	}
 	
 	private void mousePressed(final int x, final int y, final Slot slot, int button) {
@@ -167,26 +164,22 @@ public class ItemDragHandler extends Gui {
 		
 		if(button == 0) {
 			long now = System.currentTimeMillis();
-			long sinceLast = now - lastClickTime;
-			if(lastClickSlot != null && lastClickSlot == slot && sinceLast < 250 && stack != null && !lastClickHoldingItem) {
-				doubleClick = true;
-			}else {
-				doubleClick = false;
-			}
-			
-			lastClickSlot = slot;
-			lastClickTime = now;
-			lastClickHoldingItem = stack != null;
+			long sinceLast = now - this.lastClickTime;
+            this.doubleClick = this.lastClickSlot != null && this.lastClickSlot == slot && sinceLast < 250 && stack != null && !this.lastClickHoldingItem;
+
+            this.lastClickSlot = slot;
+            this.lastClickTime = now;
+            this.lastClickHoldingItem = stack != null;
 		}
 		
 		if(stack == null) {
-			container.clickInventory(x, y, button);
-			cancelButtonRelease = button;
+            this.container.clickInventory(x, y, button);
+            this.cancelButtonRelease = button;
 		}else {
 			if(!isDragging()) {
-				draggingButton = button;
-				draggingItemStack = stack;
-				draggedSlots.clear();
+                this.draggingButton = button;
+                this.draggingItemStack = stack;
+                this.draggedSlots.clear();
 			}
 		}
 	}
@@ -198,9 +191,9 @@ public class ItemDragHandler extends Gui {
 			return;
 		}
 		
-		if(cancelButtonRelease != -1) {
-			int cancelButton = cancelButtonRelease;
-			cancelButtonRelease = -1;
+		if(this.cancelButtonRelease != -1) {
+			int cancelButton = this.cancelButtonRelease;
+            this.cancelButtonRelease = -1;
 			if(cancelButton == button) {
 				return;
 			}
@@ -208,59 +201,59 @@ public class ItemDragHandler extends Gui {
 		
 		boolean doClick = true;
 		
-		if(button == 0 && doubleClick && slot != null && slot.enableDragAndPickup()) {
+		if(button == 0 && this.doubleClick && slot != null && slot.enableDragAndPickup()) {
 			doClick = false;
 			pickupSimilarItems(slot);
-			doubleClick = false;
+            this.doubleClick = false;
 			stopDragging();
 		}
 		
 		if(isDragging()) {
-			if(button == draggingButton) {
-				if(draggedSlots.size() > 0) {
+			if(button == this.draggingButton) {
+				if(!this.draggedSlots.isEmpty()) {
 					spreadItemsAcrossDraggedSlots(x, y, button);
 					doClick = false;
 				}
 			}else {
-				cancelButtonRelease = draggingButton;
+                this.cancelButtonRelease = this.draggingButton;
 				doClick = false;
 			}
 			stopDragging();
 		}
 		
 		if(doClick) {
-			container.clickInventory(x, y, button);
+            this.container.clickInventory(x, y, button);
 		}
 	}
 	
 	private void stopDragging() {
-		draggingButton = -1;
-		draggingItemStack = null;
-		draggedSlots.clear();
+        this.draggingButton = -1;
+        this.draggingItemStack = null;
+        this.draggedSlots.clear();
 	}
 	
 	private void spreadItemsAcrossDraggedSlots(int x, int y, int mode) {
-		if(draggedSlots.size() < 1) {
+		if(this.draggedSlots.isEmpty()) {
 			return;
 		}
 		
-		if(draggedSlots.size() == 1) {
-			container.clickInventory(x, y, mode);
+		if(this.draggedSlots.size() == 1) {
+            this.container.clickInventory(x, y, mode);
 			return;
 		}
 		
 		InventoryAction action = mode == 1 ? InventoryAction.DRAG_ITEMS_ONE : InventoryAction.DRAG_ITEMS_ALL;
 		
-		if(mode == 2 && !mc.thePlayer.getGamemode().consumeBlocks()) {
+		if(mode == 2 && !this.mc.thePlayer.getGamemode().consumeBlocks()) {
 			action = InventoryAction.CREATIVE_DRAG;
 		}
 		
-		int[] slots = new int[draggedSlots.size()];
+		int[] slots = new int[this.draggedSlots.size()];
 		for(int i=0; i < slots.length; i++) {
-			slots[i] = draggedSlots.get(i).index;
+			slots[i] = this.draggedSlots.get(i).index;
 		}
-		
-		mc.playerController.handleInventoryMouseClick(container.inventorySlots.containerId, action, slots, mc.thePlayer);
+
+        this.mc.playerController.handleInventoryMouseClick(this.container.inventorySlots.containerId, action, slots, this.mc.thePlayer);
 		
 	}
 	
@@ -268,29 +261,29 @@ public class ItemDragHandler extends Gui {
 		if(!slot.enableDragAndPickup()) {
 			return;
 		}
-		
-		mc.playerController.handleInventoryMouseClick(container.inventorySlots.containerId, InventoryAction.PICKUP_SIMILAR, null, mc.thePlayer);
+
+        this.mc.playerController.handleInventoryMouseClick(this.container.inventorySlots.containerId, InventoryAction.PICKUP_SIMILAR, null, this.mc.thePlayer);
 	}
 	
 	public boolean isDragging() {
-		return draggingButton != -1;
+		return this.draggingButton != -1;
 	}
 	
 	private Slot getSlotAt(int x, int y) {
-		return container.getSlotAtPosition(x, y);
+		return this.container.getSlotAtPosition(x, y);
 	}
 	
 	private ItemStack getGrabbedItem() {
-		return mc.thePlayer.inventory.getHeldItemStack();
+		return this.mc.thePlayer.inventory.getHeldItemStack();
 	}
 	
 	public boolean isSlotDragged(Slot slot) {
-		return draggedSlots.size() > 1 && draggedSlots.contains(slot);
+		return this.draggedSlots.size() > 1 && this.draggedSlots.contains(slot);
 	}
 	
 	public ItemStack getHeldItemRenderOverride() {
-		if(isDragging() && draggedSlots.size() > 1) {
-			return renderItemStack;
+		if(isDragging() && this.draggedSlots.size() > 1) {
+			return this.renderItemStack;
 		}
 		return null;
 	}
diff --git a/game/client/src/main/java/net/minecraft/client/util/helper/ScreenshotHelper.java b/game/client/src/main/java/net/minecraft/client/util/helper/ScreenshotHelper.java
index 820e2d145..87889a252 100644
--- a/game/client/src/main/java/net/minecraft/client/util/helper/ScreenshotHelper.java
+++ b/game/client/src/main/java/net/minecraft/client/util/helper/ScreenshotHelper.java
@@ -3,6 +3,7 @@ package net.minecraft.client.util.helper;
 import static net.minecraft.core.util.helper.Buffer.*;
 import static org.lwjgl.opengl.ARBFramebufferObject.*;
 import static org.lwjgl.opengl.GL11.*;
+import static org.lwjgl.opengl.GL12.GL_CLAMP_TO_EDGE;
 
 import java.awt.Graphics;
 import java.awt.image.BufferedImage;
@@ -11,8 +12,7 @@ import java.io.File;
 import javax.imageio.ImageIO;
 
 import net.minecraft.client.Minecraft;
-import net.minecraft.client.render.FallbackRenderer;
-import net.minecraft.client.render.Framebuffer;
+import net.minecraft.client.render.FrameBuffer;
 import net.minecraft.client.render.Renderer;
 import net.minecraft.client.render.texture.Texture;
 import net.minecraft.core.Global;
@@ -22,12 +22,12 @@ public class ScreenshotHelper {
 	
 	public final Minecraft minecraft;
 	
-	private final Framebuffer framebuffer = new Framebuffer();
+	private final FrameBuffer framebuffer = new FrameBuffer();
 	private final Texture colortex = new Texture();
 	private final Texture depthtex = new Texture();
 	
-	private int width = 1024;
-	private int height = 1024;
+	private final int width = 1024;
+	private final int height = 1024;
 	
 	private float fov;
 	private float yaw;
@@ -45,19 +45,17 @@ public class ScreenshotHelper {
 		try {
 			setup();
 			takeScreenshot();
-		}catch (Exception e) {
-			throw e;
-		}finally {
+		} finally {
 			delete();
 		}
 	}
 	
 	private void takeScreenshot() throws Exception {
-		minecraft.gameSettings.FoV.value = 0.6056338f; //90 Degrees
-		minecraft.thePlayer.yRot = 0.0f;
-		minecraft.thePlayer.xRot = 0.0f;
-		minecraft.thePlayer.yRotO = minecraft.thePlayer.yRot;
-		minecraft.thePlayer.xRotO = minecraft.thePlayer.xRot;
+        this.minecraft.gameSettings.FoV.value = 0.6056338f; //90 Degrees
+        this.minecraft.thePlayer.yRot = 0.0f;
+        this.minecraft.thePlayer.xRot = 0.0f;
+        this.minecraft.thePlayer.yRotO = this.minecraft.thePlayer.yRot;
+        this.minecraft.thePlayer.xRotO = this.minecraft.thePlayer.xRot;
 		
 //		minecraft.entityRenderer.renderWorld(0, 0);
 		
@@ -68,22 +66,22 @@ public class ScreenshotHelper {
 		File[] files = new File[4];
 		
 		for(int i=0; i < 4; i++) {
-			minecraft.thePlayer.yRot = i * 90f;
-			minecraft.thePlayer.yRotO = minecraft.thePlayer.yRot;
-			
-			minecraft.worldRenderer.updateCameraAndRender(0);
+            this.minecraft.thePlayer.yRot = i * 90f;
+            this.minecraft.thePlayer.yRotO = this.minecraft.thePlayer.yRot;
+
+            this.minecraft.worldRenderer.updateCameraAndRender(0);
 			
-			BufferedImage image = Textures.getTextureAsImage(colortex.id(), false, 0, true);
+			BufferedImage image = Textures.getTextureAsImage(this.colortex.id(), false, 0, true);
 			File file = new File(screenshotFolder, now + "-" + i + ".png");
 			Textures.saveImage(file, image);
 			files[i] = file;
 		}
 		
-		BufferedImage image = new BufferedImage(width * 4, height, BufferedImage.TYPE_INT_RGB);
+		BufferedImage image = new BufferedImage(this.width * 4, this.height, BufferedImage.TYPE_INT_RGB);
 		Graphics g = image.getGraphics();
 		
 		for(int i=0; i < files.length; i++) {
-			g.drawImage(ImageIO.read(files[i]), width * i, 0, null);
+			g.drawImage(ImageIO.read(files[i]), this.width * i, 0, null);
 		}
 		
 		g.dispose();
@@ -92,55 +90,55 @@ public class ScreenshotHelper {
 	}
 	
 	public void setup() {
-		framebuffer.generate();
-		colortex.generate();
-		depthtex.generate();
+        this.framebuffer.generate();
+        this.colortex.generate();
+        this.depthtex.generate();
 		
-		Buffer.checkBufferSize(width * height * 4);
+		Buffer.checkBufferSize(this.width * this.height * 4);
 		Buffer.reset();
-		
-		framebuffer.bind();
-		
-		colortex.bind();
-		glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
+
+        this.framebuffer.bind();
+
+        this.colortex.bind();
+		glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, this.width, this.height, 0, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
-		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, colortex.id(), 0);
-		
-		depthtex.bind();
-		glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, width, height, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_BYTE, buffer);
+		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, this.colortex.id(), 0);
+
+        this.depthtex.bind();
+		glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, this.width, this.height, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_BYTE, buffer);
 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
-		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
-		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, depthtex.id(), 0);
-		
-		fov = minecraft.gameSettings.FoV.value;
-		yaw = minecraft.thePlayer.yRot;
-		pitch = minecraft.thePlayer.xRot;
-		renderer = minecraft.renderer;
-		oldWidth = minecraft.gameWindow.getWidthPixels();
-		oldHeight = minecraft.gameWindow.getHeightPixels();
-		immersiveMode = minecraft.gameSettings.immersiveMode.value;
-		minecraft.gameSettings.immersiveMode.value = 2;
+		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
+		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
+		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, this.depthtex.id(), 0);
 
-		minecraft.renderer = new FallbackRenderer(minecraft);
+        this.fov = this.minecraft.gameSettings.FoV.get();
+        this.yaw = this.minecraft.thePlayer.yRot;
+        this.pitch = this.minecraft.thePlayer.xRot;
+        this.renderer = this.minecraft.renderer;
+        this.oldWidth = this.minecraft.gameWindow.getWidthPixels();
+        this.oldHeight = this.minecraft.gameWindow.getHeightPixels();
+        this.immersiveMode = this.minecraft.gameSettings.immersiveMode.value;
+        this.minecraft.gameSettings.immersiveMode.value = 2;
+
+//		minecraft.renderer = new FallbackRenderer(minecraft);
 	}
 	
 	public void delete() {
 		glBindFramebuffer(GL_FRAMEBUFFER, 0);
-		
-		framebuffer.delete();
-		colortex.delete();
-		depthtex.delete();
-		
-		minecraft.gameSettings.FoV.value = fov;
-		minecraft.thePlayer.yRot = yaw;
-		minecraft.thePlayer.xRot = pitch;
-		minecraft.renderer = renderer;
-		minecraft.gameSettings.immersiveMode.value = immersiveMode;
+
+        this.framebuffer.delete();
+        this.colortex.delete();
+        this.depthtex.delete();
+
+        this.minecraft.gameSettings.FoV.value = this.fov;
+        this.minecraft.thePlayer.yRot = this.yaw;
+        this.minecraft.thePlayer.xRot = this.pitch;
+        this.minecraft.renderer = this.renderer;
+        this.minecraft.gameSettings.immersiveMode.value = this.immersiveMode;
 	}
 	
 }
diff --git a/game/client/src/main/java/net/minecraft/client/util/helper/Textures.java b/game/client/src/main/java/net/minecraft/client/util/helper/Textures.java
index 7094b1476..5cf5452c2 100644
--- a/game/client/src/main/java/net/minecraft/client/util/helper/Textures.java
+++ b/game/client/src/main/java/net/minecraft/client/util/helper/Textures.java
@@ -21,6 +21,7 @@ import it.unimi.dsi.fastutil.ints.IntList;
 import net.minecraft.client.render.texture.stitcher.AtlasStitcher;
 import net.minecraft.client.render.texture.stitcher.TextureRegistry;
 import net.minecraft.core.util.helper.Buffer;
+import org.jetbrains.annotations.NotNull;
 import org.lwjgl.opengl.GL12;
 
 import com.b100.utils.ImageUtils;
@@ -31,8 +32,7 @@ import org.slf4j.Logger;
 
 public class Textures {
 	private static final Logger LOGGER = LogUtils.getLogger();
-	public final static BufferedImage missingTexture;
-	
+	public final static @NotNull BufferedImage missingTexture;
 	static {
 		missingTexture = new BufferedImage(64, 64, BufferedImage.TYPE_INT_ARGB);
 		
diff --git a/game/client/src/main/java/org/useless/dragonfly/models/block/StaticBlockModel.java b/game/client/src/main/java/org/useless/dragonfly/models/block/StaticBlockModel.java
index 4c3804439..4d8d941fb 100644
--- a/game/client/src/main/java/org/useless/dragonfly/models/block/StaticBlockModel.java
+++ b/game/client/src/main/java/org/useless/dragonfly/models/block/StaticBlockModel.java
@@ -2,7 +2,8 @@ package org.useless.dragonfly.models.block;
 
 import net.minecraft.client.render.block.color.BlockColor;
 import net.minecraft.client.render.block.model.BlockModel;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Side;
@@ -16,12 +17,12 @@ public interface StaticBlockModel {
     /**
      * @return True if anything rendered, false otherwise
      */
-    boolean renderStandalone(@NotNull BlockModel<? extends BlockLogic> sourceModel, @NotNull Tessellator tessellator, double x, double y, double z, int metadata, @NotNull BlockColor color, float brightness, float alpha);
+    boolean renderStandalone(@NotNull BlockModel<? extends BlockLogic> sourceModel, @NotNull TessellatorGeneral tessellator, double x, double y, double z, int metadata, @NotNull BlockColor color);
 
     /**
      * @return True if anything rendered, false otherwise
      */
-    boolean renderAttached(@NotNull BlockModel<? extends BlockLogic> sourceModel, @NotNull Tessellator tessellator, @NotNull WorldSource worldSource, int x, int y, int z, double xOff, double yOff, double zOff, boolean cullFaces, @Nullable IconCoordinate overrideTexture);
+    boolean renderAttached(@NotNull BlockModel<? extends BlockLogic> sourceModel, @NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, int x, int y, int z, double xOff, double yOff, double zOff, boolean cullFaces, @Nullable IconCoordinate overrideTexture);
 
     /**
      * @return Block texture to overlay when inside a block
diff --git a/game/client/src/main/java/org/useless/dragonfly/models/block/mojang/StaticBlockModelMojang.java b/game/client/src/main/java/org/useless/dragonfly/models/block/mojang/StaticBlockModelMojang.java
index 8e9cd0013..58d3241bf 100644
--- a/game/client/src/main/java/org/useless/dragonfly/models/block/mojang/StaticBlockModelMojang.java
+++ b/game/client/src/main/java/org/useless/dragonfly/models/block/mojang/StaticBlockModelMojang.java
@@ -7,7 +7,9 @@ import net.minecraft.client.render.block.color.BlockColor;
 import net.minecraft.client.render.block.color.BlockColorDispatcher;
 import net.minecraft.client.render.block.model.BlockModel;
 import net.minecraft.client.render.block.model.BlockModelStandard;
-import net.minecraft.client.render.tessellator.Tessellator;
+import net.minecraft.client.render.renderer.GLRenderer;
+import net.minecraft.client.render.tessellator.TessellatorGeneral;
+import net.minecraft.client.render.tessellator.TessellatorTerrain;
 import net.minecraft.client.render.texture.stitcher.IconCoordinate;
 import net.minecraft.core.block.BlockLogic;
 import net.minecraft.core.util.helper.Color;
@@ -16,7 +18,6 @@ import net.minecraft.core.util.helper.Side;
 import net.minecraft.core.world.WorldSource;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
-import org.lwjgl.opengl.GL11;
 import org.useless.dragonfly.DisplayPos;
 import org.useless.dragonfly.data.block.mojang.BlockModelMojangData;
 import org.useless.dragonfly.data.block.mojang.CompiledBlockModelMojangData;
@@ -40,66 +41,48 @@ import static org.useless.dragonfly.data.block.mojang.CompiledBlockModelMojangDa
 import static org.useless.dragonfly.data.block.mojang.CompiledBlockModelMojangData.C_Element.VERTEX_FLOAT_X;
 import static org.useless.dragonfly.data.block.mojang.CompiledBlockModelMojangData.C_Element.VERTEX_FLOAT_Y;
 import static org.useless.dragonfly.data.block.mojang.CompiledBlockModelMojangData.C_Element.VERTEX_FLOAT_Z;
-import static org.useless.dragonfly.data.block.mojang.CompiledBlockModelMojangData.C_Element.VERTEX_TOP_LEFT;
 import static org.useless.dragonfly.data.block.mojang.CompiledBlockModelMojangData.C_Element.VERTEX_TOP_RIGHT;
 
 public class StaticBlockModelMojang implements StaticBlockModel {
     protected static final Minecraft MC = Minecraft.getMinecraft();
     protected static final LightingCache LIGHTING_CACHE = new LightingCache();
 
-    protected static final byte[] V_TOP_X = new byte[] {0, 0, -1, 0, 0, 0};
-    protected static final byte[] V_TOP_Y = new byte[] {0, 0, 0, 1, 0, 0};
-    protected static final byte[] V_TOP_Z = new byte[] {1, 1, 0, 0, 1, 1};
+    protected static final byte[] V_TOP_X = new byte[]{0, 0, -1, 0, 0, 0};
+    protected static final byte[] V_TOP_Y = new byte[]{0, 0, 0, 1, 0, 0};
+    protected static final byte[] V_TOP_Z = new byte[]{1, 1, 0, 0, 1, 1};
 
-    protected static final byte[] V_LEF_X = new byte[] {-1, 1, 0, -1, 0, 0};
-    protected static final byte[] V_LEF_Y = new byte[] {0, 0, 1, 0, 1, -1};
-    protected static final byte[] V_LEF_Z = new byte[] {0, 0, 0, 0, 0, 0};
+    protected static final byte[] V_LEF_X = new byte[]{-1, 1, 0, -1, 0, 0};
+    protected static final byte[] V_LEF_Y = new byte[]{0, 0, 1, 0, 1, -1};
+    protected static final byte[] V_LEF_Z = new byte[]{0, 0, 0, 0, 0, 0};
 
     protected final CompiledBlockModelMojangData compiled;
+
     public StaticBlockModelMojang(BlockModelMojangData data) {
         this.compiled = new CompiledBlockModelMojangData(data);
     }
 
     @Override
-    public boolean renderStandalone(@NotNull BlockModel<? extends BlockLogic> sourceModel, @NotNull Tessellator tessellator, double x, double y, double z, int metadata, @NotNull BlockColor color, float brightness, float alpha) {
+    public boolean renderStandalone(@NotNull BlockModel<? extends BlockLogic> sourceModel, @NotNull TessellatorGeneral tessellator, double x, double y, double z, int metadata, @NotNull BlockColor color) {
         if (this.compiled.elements.length == 0) return false;
 
-        GL11.glPushMatrix();
+        GLRenderer.pushFrame();
         for (int i = 0; i < this.compiled.elements.length; i++) {
             C_Element element = this.compiled.elements[i];
 
-            if (element.shade) {
-                GL11.glEnable(GL11.GL_LIGHTING);
-            } else {
-                GL11.glDisable(GL11.GL_LIGHTING);
-            }
+            GLRenderer.globalSetLightEnabled(element.shade);
 
             tessellator.startDrawingQuads();
             for (int face = 0; face < element.faces; face++) {
                 IconCoordinate coordinate = this.compiled.textures.getOrDefault(element.textures[face], BlockModelStandard.BLOCK_TEXTURE_UNASSIGNED);
 
-                // Todo fix this needing to be hardcoded to get overbright looking right
-                if (LightmapHelper.isLightmapEnabled() && element.lightEmission == 15) {
-                    brightness = 1f;
-                    LightmapHelper.setLightmapCoord(15, 15);
-                } else {
-                    brightness = Math.max(brightness, element.lightEmission/15f);
-                }
-
-                float r = 1;
-                float g = 1;
-                float b = 1;
+                GLRenderer.setLightmapCoord2i(15, 15);
                 if (element.tintIndices[face] >= 0) {
-                    int c = color.getFallbackColor(metadata, element.tintIndices[face]);
-                    r = Color.redFromInt(c) / 255f;
-                    g = Color.greenFromInt(c) / 255f;
-                    b = Color.blueFromInt(c) / 255f;
+                    tessellator.setColor1i(color.getFallbackColor(metadata, element.tintIndices[face]));
                 }
 
                 final int offset = face * 4 * FLOATS_PER_VERTEX;
                 for (int v = 0; v < 4; v++) {
                     tessellator.setNormal(element.normalData[face * FLOATS_PER_NORMAL + NORMAL_FLOAT_X], element.normalData[face * FLOATS_PER_NORMAL + NORMAL_FLOAT_Y], element.normalData[face * FLOATS_PER_NORMAL + NORMAL_FLOAT_Z]);
-                    tessellator.setColorOpaque_F(r * brightness, g * brightness, b * brightness);
                     tessellator.addVertexWithUV(
                         element.vertexData[offset + v * FLOATS_PER_VERTEX + VERTEX_FLOAT_X] - 0.5f,
                         element.vertexData[offset + v * FLOATS_PER_VERTEX + VERTEX_FLOAT_Y] - 0.5f,
@@ -110,12 +93,12 @@ public class StaticBlockModelMojang implements StaticBlockModel {
             }
             tessellator.draw();
         }
-        GL11.glPopMatrix();
+        GLRenderer.popFrame();
         return true;
     }
 
     @Override
-    public boolean renderAttached(@NotNull BlockModel<? extends BlockLogic> sourceModel, @NotNull Tessellator tessellator, @NotNull WorldSource worldSource, int x, int y, int z, double xOff, double yOff, double zOff, boolean cullFaces, @Nullable IconCoordinate overrideTexture) {
+    public boolean renderAttached(@NotNull BlockModel<? extends BlockLogic> sourceModel, @NotNull TessellatorTerrain tessellator, @NotNull WorldSource worldSource, int x, int y, int z, double xOff, double yOff, double zOff, boolean cullFaces, @Nullable IconCoordinate overrideTexture) {
         if (this.compiled.elements.length == 0) return false;
         boolean didRender = false;
         LIGHTING_CACHE.setupCache(sourceModel.block, worldSource, x, y, z);
@@ -128,7 +111,7 @@ public class StaticBlockModelMojang implements StaticBlockModel {
                 final IconCoordinate coordinate = overrideTexture == null ? this.compiled.textures.getOrDefault(element.textures[face], BlockModelStandard.BLOCK_TEXTURE_UNASSIGNED) : overrideTexture;
                 final Direction direction = element.directions[face];
 
-                final float minBrightness = element.lightEmission/15f;
+                final float minBrightness = element.lightEmission / 15f;
 
                 final int topX = V_TOP_X[direction.getId()];
                 final int topY = V_TOP_Y[direction.getId()];
@@ -144,34 +127,46 @@ public class StaticBlockModelMojang implements StaticBlockModel {
                 switch (direction) {
                     case DOWN:
                         depth = 0 + element.minY;
-                        topP = element.maxZ; botP = element.minZ;
-                        lefP = 1 - element.minX; rigP = 1 - element.maxX;
+                        topP = element.maxZ;
+                        botP = element.minZ;
+                        lefP = 1 - element.minX;
+                        rigP = 1 - element.maxX;
                         break;
                     case UP:
                         depth = 1 - element.maxY;
-                        topP = element.maxZ; botP = element.minZ;
-                        lefP = element.maxX; rigP = element.minX;
+                        topP = element.maxZ;
+                        botP = element.minZ;
+                        lefP = element.maxX;
+                        rigP = element.minX;
                         break;
                     case NORTH:
                         depth = 0 + element.minZ;
-                        topP = 1 - element.minX; botP = 1 - element.maxX;
-                        lefP = element.maxY; rigP = element.minY;
+                        topP = 1 - element.minX;
+                        botP = 1 - element.maxX;
+                        lefP = element.maxY;
+                        rigP = element.minY;
                         break;
                     case SOUTH:
                         depth = 1 - element.maxZ;
-                        topP = element.maxY; botP = element.minY;
-                        lefP = 1 - element.minX; rigP = 1 - element.maxX;
+                        topP = element.maxY;
+                        botP = element.minY;
+                        lefP = 1 - element.minX;
+                        rigP = 1 - element.maxX;
                         break;
                     case WEST:
                         depth = 0 + element.minX;
-                        topP = element.maxZ; botP = element.minZ;
-                        lefP = element.maxY; rigP = element.minY;
+                        topP = element.maxZ;
+                        botP = element.minZ;
+                        lefP = element.maxY;
+                        rigP = element.minY;
                         break;
                     case EAST:
                     default:
                         depth = 1 - element.maxX;
-                        topP = element.maxZ; botP = element.minZ;
-                        lefP = 1 - element.minY; rigP = 1 - element.maxY;
+                        topP = element.maxZ;
+                        botP = element.minZ;
+                        lefP = 1 - element.minY;
+                        rigP = 1 - element.maxY;
                         break;
                 }
 
@@ -201,61 +196,54 @@ public class StaticBlockModelMojang implements StaticBlockModel {
                 final int lightmapCoordBottomRight;
                 final int lightmapCoordTopRight;
 
-                if(LightmapHelper.isLightmapEnabled()) {
-                    if (useAO) {
-                        final int dirX2;
-                        final int dirY2;
-                        final int dirZ2;
-                        if (!isFullCube) {
-                            dirX2 = 0;
-                            dirY2 = 0;
-                            dirZ2 = 0;
-                        } else {
-                            dirX2 = dirX;
-                            dirY2 = dirY;
-                            dirZ2 = dirZ;
-                        }
-
-                        final boolean topT = LIGHTING_CACHE.getOpacity(dirX2 + topX, dirY2 + topY, dirZ2 + topZ);
-                        final boolean botT = LIGHTING_CACHE.getOpacity(dirX2 - topX, dirY2 - topY, dirZ2 - topZ);
-                        final boolean lefT = LIGHTING_CACHE.getOpacity(dirX2 + lefX, dirY2 + lefY, dirZ2 + lefZ);
-                        final boolean rigT = LIGHTING_CACHE.getOpacity(dirX2 - lefX, dirY2 - lefY, dirZ2 - lefZ);
-
-                        final boolean topLefT = LIGHTING_CACHE.getOpacity(dirX2 + topX + lefX, dirY2 + topY + lefY, dirZ2 + topZ + lefZ);
-                        final boolean topRigT = LIGHTING_CACHE.getOpacity(dirX2 + topX - lefX, dirY2 + topY - lefY, dirZ2 + topZ - lefZ);
-                        final boolean botLefT = LIGHTING_CACHE.getOpacity(dirX2 - topX + lefX, dirY2 - topY + lefY, dirZ2 - topZ + lefZ);
-                        final boolean botRigT = LIGHTING_CACHE.getOpacity(dirX2 - topX - lefX, dirY2 - topY - lefY, dirZ2 - topZ - lefZ);
-
-                        final int lmcCen = getLightmap(dirX2, dirY2, dirZ2, element.lightEmission);
-
-                        final int lmcTop = topT ? lmcCen : getLightmap(dirX2 + topX, dirY2 + topY, dirZ2 + topZ, element.lightEmission);
-                        final int lmcBot = botT ? lmcCen : getLightmap(dirX2 - topX, dirY2 - topY, dirZ2 - topZ, element.lightEmission);
-                        final int lmcLef = lefT ? lmcCen : getLightmap(dirX2 + lefX, dirY2 + lefY, dirZ2 + lefZ, element.lightEmission);
-                        final int lmcRig = rigT ? lmcCen : getLightmap(dirX2 - lefX, dirY2 - lefY, dirZ2 - lefZ, element.lightEmission);
-
-                        final int lmcTopLef = topT && lefT ? lmcLef : (topLefT ? lmcCen : getLightmap(dirX2 + topX + lefX, dirY2 + topY + lefY, dirZ2 + topZ + lefZ, element.lightEmission));
-                        final int lmcBotLef = botT && lefT ? lmcLef : (botLefT ? lmcCen : getLightmap(dirX2 - topX + lefX, dirY2 - topY + lefY, dirZ2 - topZ + lefZ, element.lightEmission));
-                        final int lmcTopRig = topT && rigT ? lmcRig : (topRigT ? lmcCen : getLightmap(dirX2 + topX - lefX, dirY2 + topY - lefY, dirZ2 + topZ - lefZ, element.lightEmission));
-                        final int lmcBotRig = botT && rigT ? lmcRig : (botRigT ? lmcCen : getLightmap(dirX2 - topX - lefX, dirY2 - topY - lefY, dirZ2 - topZ - lefZ, element.lightEmission));
-
-                        lightmapCoordTopLeft = LightmapHelper.avg(lmcCen, lmcLef, lmcTop, lmcTopLef);
-                        lightmapCoordTopRight = LightmapHelper.avg(lmcCen, lmcRig, lmcTop, lmcTopRig);
-                        lightmapCoordBottomLeft = LightmapHelper.avg(lmcCen, lmcLef, lmcBot, lmcBotLef);
-                        lightmapCoordBottomRight = LightmapHelper.avg(lmcCen, lmcRig, lmcBot, lmcBotRig);
+                if (useAO) {
+                    final int dirX2;
+                    final int dirY2;
+                    final int dirZ2;
+                    if (!isFullCube) {
+                        dirX2 = 0;
+                        dirY2 = 0;
+                        dirZ2 = 0;
                     } else {
-                        final int lmc;
-                        if (!isFullCube) {
-                            lmc = getLightmap(0, 0, 0, element.lightEmission);
-                        } else {
-                            lmc = getLightmap(dirX, dirY,  dirZ, element.lightEmission);
-                        }
-                        lightmapCoordTopLeft = lightmapCoordBottomLeft = lightmapCoordBottomRight = lightmapCoordTopRight = lmc;
+                        dirX2 = dirX;
+                        dirY2 = dirY;
+                        dirZ2 = dirZ;
                     }
+
+                    final boolean topT = LIGHTING_CACHE.getOpacity(dirX2 + topX, dirY2 + topY, dirZ2 + topZ);
+                    final boolean botT = LIGHTING_CACHE.getOpacity(dirX2 - topX, dirY2 - topY, dirZ2 - topZ);
+                    final boolean lefT = LIGHTING_CACHE.getOpacity(dirX2 + lefX, dirY2 + lefY, dirZ2 + lefZ);
+                    final boolean rigT = LIGHTING_CACHE.getOpacity(dirX2 - lefX, dirY2 - lefY, dirZ2 - lefZ);
+
+                    final boolean topLefT = LIGHTING_CACHE.getOpacity(dirX2 + topX + lefX, dirY2 + topY + lefY, dirZ2 + topZ + lefZ);
+                    final boolean topRigT = LIGHTING_CACHE.getOpacity(dirX2 + topX - lefX, dirY2 + topY - lefY, dirZ2 + topZ - lefZ);
+                    final boolean botLefT = LIGHTING_CACHE.getOpacity(dirX2 - topX + lefX, dirY2 - topY + lefY, dirZ2 - topZ + lefZ);
+                    final boolean botRigT = LIGHTING_CACHE.getOpacity(dirX2 - topX - lefX, dirY2 - topY - lefY, dirZ2 - topZ - lefZ);
+
+                    final int lmcCen = getLightmap(dirX2, dirY2, dirZ2, element.lightEmission);
+
+                    final int lmcTop = topT ? lmcCen : getLightmap(dirX2 + topX, dirY2 + topY, dirZ2 + topZ, element.lightEmission);
+                    final int lmcBot = botT ? lmcCen : getLightmap(dirX2 - topX, dirY2 - topY, dirZ2 - topZ, element.lightEmission);
+                    final int lmcLef = lefT ? lmcCen : getLightmap(dirX2 + lefX, dirY2 + lefY, dirZ2 + lefZ, element.lightEmission);
+                    final int lmcRig = rigT ? lmcCen : getLightmap(dirX2 - lefX, dirY2 - lefY, dirZ2 - lefZ, element.lightEmission);
+
+                    final int lmcTopLef = topT && lefT ? lmcLef : (topLefT ? lmcCen : getLightmap(dirX2 + topX + lefX, dirY2 + topY + lefY, dirZ2 + topZ + lefZ, element.lightEmission));
+                    final int lmcBotLef = botT && lefT ? lmcLef : (botLefT ? lmcCen : getLightmap(dirX2 - topX + lefX, dirY2 - topY + lefY, dirZ2 - topZ + lefZ, element.lightEmission));
+                    final int lmcTopRig = topT && rigT ? lmcRig : (topRigT ? lmcCen : getLightmap(dirX2 + topX - lefX, dirY2 + topY - lefY, dirZ2 + topZ - lefZ, element.lightEmission));
+                    final int lmcBotRig = botT && rigT ? lmcRig : (botRigT ? lmcCen : getLightmap(dirX2 - topX - lefX, dirY2 - topY - lefY, dirZ2 - topZ - lefZ, element.lightEmission));
+
+                    lightmapCoordTopLeft = LightmapHelper.avg(lmcCen, lmcLef, lmcTop, lmcTopLef);
+                    lightmapCoordTopRight = LightmapHelper.avg(lmcCen, lmcRig, lmcTop, lmcTopRig);
+                    lightmapCoordBottomLeft = LightmapHelper.avg(lmcCen, lmcLef, lmcBot, lmcBotLef);
+                    lightmapCoordBottomRight = LightmapHelper.avg(lmcCen, lmcRig, lmcBot, lmcBotRig);
                 } else {
-                    lightmapCoordTopLeft = 0;
-                    lightmapCoordBottomLeft = 0;
-                    lightmapCoordBottomRight = 0;
-                    lightmapCoordTopRight = 0;
+                    final int lmc;
+                    if (!isFullCube) {
+                        lmc = getLightmap(0, 0, 0, element.lightEmission);
+                    } else {
+                        lmc = getLightmap(dirX, dirY, dirZ, element.lightEmission);
+                    }
+                    lightmapCoordTopLeft = lightmapCoordBottomLeft = lightmapCoordBottomRight = lightmapCoordTopRight = lmc;
                 }
 
                 float lightTR;
@@ -361,8 +349,8 @@ public class StaticBlockModelMojang implements StaticBlockModel {
 
                 final int offset = face * 4 * FLOATS_PER_VERTEX;
 
-                tessellator.setColorOpaque_F(colorRedTopLeft, colorGreenTopLeft, colorBlueTopLeft);
-                if(LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(lightmapCoordTopLeft);
+                tessellator.setColorOpaque3f(colorRedTopLeft, colorGreenTopLeft, colorBlueTopLeft);
+                tessellator.setLightmapCoord1i(lightmapCoordTopLeft);
                 tessellator.addVertexWithUV(
                     element.vertexData[offset + VERTEX_FLOAT_X] + x + xOff,
                     element.vertexData[offset + VERTEX_FLOAT_Y] + y + yOff,
@@ -370,8 +358,8 @@ public class StaticBlockModelMojang implements StaticBlockModel {
                     coordinate.getSubIconU(element.vertexData[offset + VERTEX_FLOAT_U]),
                     coordinate.getSubIconV(element.vertexData[offset + VERTEX_FLOAT_V]));
 
-                tessellator.setColorOpaque_F(colorRedBottomLeft, colorGreenBottomLeft, colorBlueBottomLeft);
-                if(LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(lightmapCoordBottomLeft);
+                tessellator.setColorOpaque3f(colorRedBottomLeft, colorGreenBottomLeft, colorBlueBottomLeft);
+                tessellator.setLightmapCoord1i(lightmapCoordBottomLeft);
                 tessellator.addVertexWithUV(
                     element.vertexData[offset + VERTEX_BOTTOM_LEFT * FLOATS_PER_VERTEX + VERTEX_FLOAT_X] + x + xOff,
                     element.vertexData[offset + VERTEX_BOTTOM_LEFT * FLOATS_PER_VERTEX + VERTEX_FLOAT_Y] + y + yOff,
@@ -379,8 +367,8 @@ public class StaticBlockModelMojang implements StaticBlockModel {
                     coordinate.getSubIconU(element.vertexData[offset + VERTEX_BOTTOM_LEFT * FLOATS_PER_VERTEX + VERTEX_FLOAT_U]),
                     coordinate.getSubIconV(element.vertexData[offset + VERTEX_BOTTOM_LEFT * FLOATS_PER_VERTEX + VERTEX_FLOAT_V]));
 
-                tessellator.setColorOpaque_F(colorRedBottomRight, colorGreenBottomRight, colorBlueBottomRight);
-                if(LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(lightmapCoordBottomRight);
+                tessellator.setColorOpaque3f(colorRedBottomRight, colorGreenBottomRight, colorBlueBottomRight);
+                tessellator.setLightmapCoord1i(lightmapCoordBottomRight);
                 tessellator.addVertexWithUV(
                     element.vertexData[offset + VERTEX_BOTTOM_RIGHT * FLOATS_PER_VERTEX + VERTEX_FLOAT_X] + x + xOff,
                     element.vertexData[offset + VERTEX_BOTTOM_RIGHT * FLOATS_PER_VERTEX + VERTEX_FLOAT_Y] + y + yOff,
@@ -388,8 +376,8 @@ public class StaticBlockModelMojang implements StaticBlockModel {
                     coordinate.getSubIconU(element.vertexData[offset + VERTEX_BOTTOM_RIGHT * FLOATS_PER_VERTEX + VERTEX_FLOAT_U]),
                     coordinate.getSubIconV(element.vertexData[offset + VERTEX_BOTTOM_RIGHT * FLOATS_PER_VERTEX + VERTEX_FLOAT_V]));
 
-                tessellator.setColorOpaque_F(colorRedTopRight, colorGreenTopRight, colorBlueTopRight);
-                if(LightmapHelper.isLightmapEnabled()) tessellator.setLightmapCoord(lightmapCoordTopRight);
+                tessellator.setColorOpaque3f(colorRedTopRight, colorGreenTopRight, colorBlueTopRight);
+                tessellator.setLightmapCoord1i(lightmapCoordTopRight);
                 tessellator.addVertexWithUV(
                     element.vertexData[offset + VERTEX_TOP_RIGHT * FLOATS_PER_VERTEX + VERTEX_FLOAT_X] + x + xOff,
                     element.vertexData[offset + VERTEX_TOP_RIGHT * FLOATS_PER_VERTEX + VERTEX_FLOAT_Y] + y + yOff,
diff --git a/game/client/src/main/java/org/useless/dragonfly/models/entity/StaticEntityModel.java b/game/client/src/main/java/org/useless/dragonfly/models/entity/StaticEntityModel.java
index 4587b933d..a57695dc8 100644
--- a/game/client/src/main/java/org/useless/dragonfly/models/entity/StaticEntityModel.java
+++ b/game/client/src/main/java/org/useless/dragonfly/models/entity/StaticEntityModel.java
@@ -1,6 +1,5 @@
 package org.useless.dragonfly.models.entity;
 
-import net.minecraft.client.render.tessellator.Tessellator;
 import org.jetbrains.annotations.NotNull;
 import org.joml.primitives.AABBdc;
 
@@ -9,5 +8,5 @@ public interface StaticEntityModel {
     @NotNull BoneTransform getTransform(@NotNull String boneId);
     @NotNull AABBdc visibleBounds();
     void translateToBone(@NotNull String boneId);
-    void render(@NotNull Tessellator tessellator);
+    void render();
 }
diff --git a/game/client/src/main/java/org/useless/dragonfly/models/entity/mojang/StaticEntityModelMojang.java b/game/client/src/main/java/org/useless/dragonfly/models/entity/mojang/StaticEntityModelMojang.java
index b0e4368c8..353e0bad8 100644
--- a/game/client/src/main/java/org/useless/dragonfly/models/entity/mojang/StaticEntityModelMojang.java
+++ b/game/client/src/main/java/org/useless/dragonfly/models/entity/mojang/StaticEntityModelMojang.java
@@ -1,12 +1,19 @@
 package org.useless.dragonfly.models.entity.mojang;
 
+import com.mojang.logging.LogUtils;
+import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
+import net.minecraft.client.render.renderer.DrawMode;
+import net.minecraft.client.render.renderer.GLRenderer;
 import net.minecraft.client.render.tessellator.Tessellator;
 import net.minecraft.core.util.helper.Direction;
 import net.minecraft.core.util.helper.MathHelper;
 import org.jetbrains.annotations.NotNull;
+import org.joml.Math;
 import org.joml.primitives.AABBd;
 import org.joml.primitives.AABBdc;
-import org.lwjgl.opengl.GL11;
+import org.lwjgl.BufferUtils;
+import org.lwjgl.opengl.GL41;
+import org.slf4j.Logger;
 import org.useless.dragonfly.data.entity.mojang.Bone;
 import org.useless.dragonfly.data.entity.mojang.Cube;
 import org.useless.dragonfly.data.entity.mojang.EntityGeometryMojangData;
@@ -14,12 +21,14 @@ import org.useless.dragonfly.data.entity.mojang.Face;
 import org.useless.dragonfly.models.entity.BoneTransform;
 import org.useless.dragonfly.models.entity.StaticEntityModel;
 
-import java.util.HashMap;
+import java.nio.ByteBuffer;
+import java.nio.FloatBuffer;
 import java.util.Map;
 
 public class StaticEntityModelMojang implements StaticEntityModel {
     private static final BoneTransform DUMMY_TRANSFORM = new BoneTransform();
-    public final @NotNull Map<@NotNull String, @NotNull BoneTransform> transformMap = new HashMap<>();
+    private static final TessellatorEntity entityTessellator = new TessellatorEntity(2048);
+    public final @NotNull Map<@NotNull String, @NotNull BoneTransform> transformMap = new Object2ObjectOpenHashMap<>();
     public final @NotNull BoneTransform @NotNull [] transforms;
     public final @NotNull Bone @NotNull [] bones;
     public final EntityGeometryMojangData data;
@@ -73,18 +82,21 @@ public class StaticEntityModelMojang implements StaticEntityModel {
         final Bone bone = this.data.bones.get(boneId);
         if (bone == null) return;
         boneTransform(bone);
-        GL11.glTranslated(bone.pivot[0], bone.pivot[1], bone.pivot[2]);
+        GLRenderer.modelM4f().translate((float) bone.pivot[0], (float) bone.pivot[1], (float) bone.pivot[2]);
     }
 
     @Override
-    public void render(@NotNull final Tessellator tessellator) {
+    public void render() {
+        GLRenderer.getShader().bind();
+        GLRenderer.globalSetUniforms(GLRenderer.getShader());
         for (int i = 0; i < this.bones.length; i++) {
             final Bone bone = this.bones[i];
-            GL11.glPushMatrix();
+            GLRenderer.pushFrame();
             if (!boneTransform(bone)) {
-                renderBone(tessellator, bone);
+                GL41.glUniformMatrix4fv(GLRenderer.getShader().getUniform("model"), false, GLRenderer.modelM4f().get(this.mat4fBuf));
+                renderBone(entityTessellator, bone);
             }
-            GL11.glPopMatrix();
+            GLRenderer.popFrame();
         }
     }
 
@@ -96,19 +108,21 @@ public class StaticEntityModelMojang implements StaticEntityModel {
         }
         final BoneTransform transform = this.transformMap.get(bone.name);
         hidden |= !transform.visible;
-        GL11.glTranslated(bone.pivot[0], bone.pivot[1], bone.pivot[2]);
-        GL11.glTranslated(transform.posX, transform.posY, transform.posZ);
-        GL11.glRotated(-(transform.rotZ * MathHelper.RAD_TO_DEG) - bone.rotation[2], 0, 0, 1);
-        GL11.glRotated((transform.rotY * MathHelper.RAD_TO_DEG) + bone.rotation[1], 0, 1, 0);
-        GL11.glRotated(-(transform.rotX * MathHelper.RAD_TO_DEG) - bone.rotation[0], 1, 0, 0);
-        GL11.glTranslated(-bone.pivot[0], -bone.pivot[1], -bone.pivot[2]);
-        GL11.glScaled(transform.scaleX, transform.scaleY, transform.scaleZ);
+        GLRenderer.modelM4f().translate((float) bone.pivot[0], (float) bone.pivot[1], (float) bone.pivot[2]);
+        GLRenderer.modelM4f().translate((float) transform.posX, (float) transform.posY, (float) transform.posZ);
+        GLRenderer.modelM4f().rotateZ((float) (-transform.rotZ - Math.toRadians(bone.rotation[2])));
+        GLRenderer.modelM4f().rotateY((float) (transform.rotY + Math.toRadians(bone.rotation[1])));
+        GLRenderer.modelM4f().rotateX((float) (-transform.rotX - Math.toRadians(bone.rotation[0])));
+        GLRenderer.modelM4f().translate((float) -bone.pivot[0], (float) -bone.pivot[1], (float) -bone.pivot[2]);
+        GLRenderer.modelM4f().scale((float) transform.scaleX, (float) transform.scaleY, (float) transform.scaleZ);
         return hidden;
     }
 
+    private final FloatBuffer mat4fBuf = BufferUtils.createFloatBuffer(16);
+
     private final double[] uvsBuffer = new double[8];
 
-    protected void renderBone(@NotNull final Tessellator tessellator, @NotNull final Bone bone) {
+    protected void renderBone(@NotNull final TessellatorEntity tessellator, @NotNull final Bone bone) {
         tessellator.startDrawingQuads();
         for (final Cube cube : bone.cubes) {
             final double minX = cube.origin[0] - (cube.inflate + bone.inflate + this.inflation);
@@ -425,7 +439,7 @@ public class StaticEntityModelMojang implements StaticEntityModel {
         tessellator.draw();
     }
 
-    protected static void addRotatedVertex(@NotNull final Tessellator tessellator, final double x, final double y, final double z, final double u, final double v, final double @NotNull [] pivot, final double @NotNull [] rotation) {
+    protected static void addRotatedVertex(@NotNull final TessellatorEntity tessellator, final double x, final double y, final double z, final double u, final double v, final double @NotNull [] pivot, final double @NotNull [] rotation) {
         double _x = x - pivot[0];
         double _y = y - pivot[1];
         double _z = z - pivot[2];
@@ -469,4 +483,122 @@ public class StaticEntityModelMojang implements StaticEntityModel {
 
         tessellator.addVertexWithUV(_x + pivot[0], _y + pivot[1], _z + pivot[2], u, v);
     }
+
+    public static class TessellatorEntity {
+        private static final Logger LOGGER = LogUtils.getLogger();
+        private static final int VERT_SIZE = 5 * Float.BYTES + 3;
+        public ByteBuffer data;
+
+        public boolean drawing;
+
+        public byte normalX = 0;
+        public byte normalY = -128;
+        public byte normalZ = 0;
+
+        public final int vao;
+        public final int vbo;
+
+        public int vertexCount = 0;
+        private int quadVertCount = 0;
+
+        public TessellatorEntity(int capacity) {
+            this.data = BufferUtils.createByteBuffer(capacity);
+            this.vao = GL41.glGenVertexArrays();
+            this.vbo = GL41.glGenBuffers();
+
+            GL41.glBindVertexArray(this.vao);
+            GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+
+            GL41.glVertexAttribPointer(0, 3, GL41.GL_FLOAT, false, VERT_SIZE, 0);
+            GL41.glVertexAttrib4f(1, 1f, 1f, 1f, 1f);
+            GL41.glVertexAttribPointer(2, 2, GL41.GL_FLOAT, false, VERT_SIZE, Float.BYTES * 3);
+            GL41.glVertexAttrib2f(3, 15.5f/16f, 15.5f/16f);
+            GL41.glVertexAttribPointer(4, 3, GL41.GL_BYTE, true, VERT_SIZE, Float.BYTES * 5);
+
+            GL41.glEnableVertexAttribArray(0);
+            GL41.glEnableVertexAttribArray(2);
+            GL41.glEnableVertexAttribArray(4);
+        }
+
+        public void startDrawingQuads() {
+            if(this.drawing) {
+                this.drawing = false;
+                throw new IllegalStateException("Entity Tessellator already drawing!");
+            }
+
+            this.normalX = 0;
+            this.normalY = -128;
+            this.normalZ = 0;
+
+            this.vertexCount = 0;
+            this.quadVertCount = 0;
+
+            this.drawing = true;
+
+            this.data.clear();
+        }
+
+        public void addVertexWithUV(double x, double y, double z, double u, double v) {
+            if(!this.drawing) {
+                throw new IllegalStateException("Entity Tessellator already drawing!");
+            }
+            checkCanFit(64);
+
+            this.data.putFloat((float) x).putFloat((float) y).putFloat((float) z);
+            this.data.putFloat((float) u).putFloat((float) v);
+            this.data.put(this.normalX).put(this.normalY).put(this.normalZ);
+
+            this.vertexCount++;
+
+            if (Tessellator.QUAD_EMULATION && this.quadVertCount % 4 == 2) {
+                checkCanFit(128);
+                this.data.put(this.data.position(), this.data, this.data.position() - VERT_SIZE * 3, VERT_SIZE);
+                this.data.put(this.data.position() + VERT_SIZE, this.data, this.data.position() - VERT_SIZE, VERT_SIZE);
+                this.data.position(this.data.position() + VERT_SIZE * 2);
+                this.vertexCount += 2;
+            }
+
+            this.quadVertCount++;
+        }
+
+        public void checkCanFit(int size) {
+            if(this.data.capacity() < this.data.position() + size) {
+                int newSize = this.data.capacity() * 2;
+
+                LOGGER.info("Expanding {} Buffer ({} -> {})", "Entity Tessellator", this.data.capacity(), newSize);
+
+                ByteBuffer newBuffer = BufferUtils.createByteBuffer(newSize);
+                this.data.flip();
+                newBuffer.put(this.data);
+                this.data = newBuffer;
+            }
+        }
+
+        public void setNormal(double x, double y, double z) {
+            if(!this.drawing) {
+                throw new IllegalStateException("Entity Tessellator already drawing!");
+            }
+
+            this.normalX = (byte) (x * 127.0);
+            this.normalY = (byte) (y * 127.0);
+            this.normalZ = (byte) (z * 127.0);
+        }
+
+        public void draw() {
+            if(!this.drawing) {
+                throw new IllegalStateException("Entity Tessellator already drawing!");
+            }
+
+            this.drawing = false;
+
+            if (this.vertexCount == 0) return;
+
+            GL41.glBindVertexArray(this.vao);
+            GL41.glVertexAttrib2f(3, GLRenderer.getLightmapBlock(), GLRenderer.getLightmapSky());
+            GL41.glBindBuffer(GL41.GL_ARRAY_BUFFER, this.vbo);
+            GL41.glBufferData(GL41.GL_ARRAY_BUFFER, this.data.flip(), GL41.GL_STREAM_DRAW);
+            GL41.glDrawArrays(Tessellator.QUAD_EMULATION ? DrawMode.TRIANGLES.cap : DrawMode.QUADS.cap, 0, this.vertexCount);
+            GL41.glBindVertexArray(0);
+        }
+    }
 }
diff --git a/game/client/src/main/resources/assets/minecraft/textures/colormap/stars/default.png b/game/client/src/main/resources/assets/minecraft/textures/colormap/stars/default.png
index c31b5d772..a190b4504 100644
Binary files a/game/client/src/main/resources/assets/minecraft/textures/colormap/stars/default.png and b/game/client/src/main/resources/assets/minecraft/textures/colormap/stars/default.png differ
diff --git a/game/client/src/main/resources/shaders/base.fsh b/game/client/src/main/resources/shaders/base.fsh
deleted file mode 100644
index ff17fe1b6..000000000
--- a/game/client/src/main/resources/shaders/base.fsh
+++ /dev/null
@@ -1,81 +0,0 @@
-#version 120
-
-uniform sampler2D colortex0;
-uniform sampler2D depthtex0;
-
-uniform float gamma;
-
-uniform int cbCorrectionMode;
-
-uniform float width;
-uniform float height;
-
-varying vec2 texcoord;
-
-vec3 adjustGamma(vec3 color, float value)
-{
-	return pow(color, vec3(1.0 - value + 0.5));
-}
-
-vec3 cbCorrection(vec3 tex)
-{
-    int mode = cbCorrectionMode;
-    if (mode < 1 || mode > 4) return tex;
-	
-	if(mode == 4) //Grayscale
-	{
-		return vec3((tex.r + tex.g + tex.b) / 3.0f);
-	}
-	
-    float L = (17.8824 * tex.r) + (43.5161 * tex.g) + (4.11935 * tex.b);
-    float M = (3.45565 * tex.r) + (27.1554 * tex.g) + (3.86714 * tex.b);
-    float S = (0.0299566 * tex.r) + (0.184309 * tex.g) + (1.46709 * tex.b);
-
-	float l, m, s;
-	if (mode == 1) //Protanopia
-	{
-		l = 0.0 * L + 2.02344 * M + -2.52581 * S;
-		m = 0.0 * L + 1.0 * M + 0.0 * S;
-		s = 0.0 * L + 0.0 * M + 1.0 * S;
-	}
-
-	if (mode == 2) //Deuteranopia
-	{
-		l = 1.0 * L + 0.0 * M + 0.0 * S;
-    	m = 0.494207 * L + 0.0 * M + 1.24827 * S;
-    	s = 0.0 * L + 0.0 * M + 1.0 * S;
-	}
-
-	if (mode == 3) //Tritanopia
-	{
-		l = 1.0 * L + 0.0 * M + 0.0 * S;
-    	m = 0.0 * L + 1.0 * M + 0.0 * S;
-    	s = -0.395913 * L + 0.801109 * M + 0.0 * S;
-	}
-
-	vec3 error;
-    error.r = (0.0809444479 * l) + (-0.130504409 * m) + (0.116721066 * s);
-    error.g = (-0.0102485335 * l) + (0.0540193266 * m) + (-0.113614708 * s);
-    error.b = (-0.000365296938 * l) + (-0.00412161469 * m) + (0.693511405 * s);
-    vec3 diff = tex - error;
-    vec3 correction;
-    correction.r = 0.0;
-	correction.g =  (diff.r * 0.7) + (diff.g * 1.0);
-	correction.b =  (diff.r * 0.7) + (diff.b * 1.0);
-	correction = tex + correction;
-
-	return correction;
-}
-
-void main()
-{
-	vec3 color = vec3(0.0);
-
-	color = texture2D(colortex0, texcoord.xy).rgb;
-
-	color = cbCorrection(color);
-	
-	color = adjustGamma(color, gamma);
-	
-	gl_FragColor = vec4(color, 1.0);
-}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/base.vsh b/game/client/src/main/resources/shaders/base.vsh
deleted file mode 100644
index 9c7ba53f5..000000000
--- a/game/client/src/main/resources/shaders/base.vsh
+++ /dev/null
@@ -1,9 +0,0 @@
-#version 120
-
-varying vec2 texcoord;
-
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
-}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/clouds.fsh b/game/client/src/main/resources/shaders/clouds.fsh
index b246f1317..00746bf35 100644
--- a/game/client/src/main/resources/shaders/clouds.fsh
+++ b/game/client/src/main/resources/shaders/clouds.fsh
@@ -1,23 +1,30 @@
-#version 120
+#version 410 core
 
 #define FOG
 #define RADIAL_FOG
 
-uniform sampler2D texture;
-
 uniform int isEyeInLiquid;
 
-#ifdef RADIAL_FOG
-uniform mat4 gbufferProjectionInverse;
+uniform mat4 projectionInv;
 uniform float viewWidth;
 uniform float viewHeight;
-#endif
 
-varying vec2 texcoord;
-varying vec4 color;
+in vec4 Color;
+in vec2 TexCoord;
+
+out vec4 FragColor;
+
+uniform vec4 ufogColor;
+uniform int ufogMode;
+uniform float ufogStart;
+uniform float ufogEnd;
+uniform float ufogDensity;
+
+uniform sampler2D texture0;
+uniform sampler2D texture1;
 
 void main() {
-	vec4 tex = texture2D(texture, texcoord);
+	vec4 tex = texture(texture0, TexCoord);
 	
 	// Alpha test
 	if(tex.a < 0.1f) {
@@ -29,30 +36,22 @@ void main() {
 		discard;
 	}
 	
-	vec4 col = color;
-	
-	#ifdef FOG
+	vec4 col = Color;
+
 	float fogStrength = 0.0f;
-	
-	#ifndef RADIAL_FOG
-	fogStrength = (gl_FogFragCoord - gl_Fog.start) * gl_Fog.scale;
-	#endif
-	
-	#ifdef RADIAL_FOG
-	vec4 fragPos = gbufferProjectionInverse * vec4((gl_FragCoord.xy / vec2(viewWidth, viewHeight)) * 2.0f - 1.0f, gl_FragCoord.z * 2.0f - 1.0f, 1.0f);
+
+	vec4 fragPos = projectionInv * vec4((gl_FragCoord.xy / vec2(viewWidth, viewHeight)) * 2.0f - 1.0f, gl_FragCoord.z * 2.0f - 1.0f, 1.0f);
 	fragPos /= fragPos.w;
 	
 	float dist = length(fragPos.xyz);
-	float end = gl_Fog.end;
-	float start = gl_Fog.start / gl_Fog.end;
-	
+	float end = (ufogEnd * 1.5f);
+	float start = ufogStart / (ufogEnd * 1.5f);
+
 	fogStrength = dist / end;
-	fogStrength -= (start);
+	fogStrength -= start;
 	fogStrength /= (1.0f - start);
 	fogStrength = clamp(fogStrength, 0.0f, 1.0f);
-	#endif
 	col.a *= 1.0f - fogStrength;
-	#endif
 	
-	gl_FragData[0] = tex * col;
+	FragColor = tex * col;
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/clouds.vsh b/game/client/src/main/resources/shaders/clouds.vsh
index 0a5f716c5..ec9b57fd0 100644
--- a/game/client/src/main/resources/shaders/clouds.vsh
+++ b/game/client/src/main/resources/shaders/clouds.vsh
@@ -1,12 +1,20 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec3 aPos;
+layout (location = 1) in vec4 aColor;
+layout (location = 2) in vec2 aUV;
+//layout (location = 3) in vec2 aLightmap;
+//layout (location = 4) in vec3 aNormal;
 
-varying vec2 texcoord;
-varying vec4 color;
+out vec4 Color;
+out vec2 TexCoord;
+
+uniform mat4 model;
+uniform mat4 view;
+uniform mat4 projection;
 
 void main() {
-	texcoord = gl_MultiTexCoord0.xy;
-	color = gl_Color;
-	
-	gl_Position = ftransform();
-	gl_FogFragCoord = gl_Position.z;
+	TexCoord = aUV;
+	Color = aColor;
+
+	gl_Position = projection * view * model * vec4(aPos, 1);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/color.fsh b/game/client/src/main/resources/shaders/color.fsh
new file mode 100644
index 000000000..a0dabc0a1
--- /dev/null
+++ b/game/client/src/main/resources/shaders/color.fsh
@@ -0,0 +1,11 @@
+#version 410 core
+
+out vec4 FragColor;
+
+in vec4 Color;
+
+uniform vec4 ucolor;
+
+void main() {
+    FragColor = Color * ucolor;
+}
diff --git a/game/client/src/main/resources/shaders/color.vsh b/game/client/src/main/resources/shaders/color.vsh
new file mode 100644
index 000000000..963b1691f
--- /dev/null
+++ b/game/client/src/main/resources/shaders/color.vsh
@@ -0,0 +1,14 @@
+#version 410 core
+layout (location = 0) in vec3 aPos;
+layout (location = 1) in vec4 aColor;
+
+out vec4 Color;
+
+uniform mat4 model;
+uniform mat4 view;
+uniform mat4 projection;
+
+void main() {
+    gl_Position = projection * view * model * vec4(aPos, 1);
+    Color = aColor;
+}
diff --git a/game/client/src/main/resources/shaders/color_world.fsh b/game/client/src/main/resources/shaders/color_world.fsh
new file mode 100644
index 000000000..a3c438d38
--- /dev/null
+++ b/game/client/src/main/resources/shaders/color_world.fsh
@@ -0,0 +1,60 @@
+#version 410 core
+
+out vec4 FragColor;
+
+in vec4 Color;
+in vec2 LightMapCoord;
+in float Distance;
+in vec3 Light;
+
+uniform vec4 ucolor;
+
+uniform vec4 ufogColor;
+uniform int ufogMode;
+uniform float ufogStart;
+uniform float ufogEnd;
+uniform float ufogDensity;
+
+uniform sampler2D texture1;
+
+// Taken from https://github.com/hughsk/glsl-fog
+float fogFactorLinear() {
+    return 1.0 - clamp(((ufogEnd - (Distance)) / (ufogEnd - ufogStart)), 0.0, 1.0);
+}
+
+float fogFactorExp() {
+    return 1.0 - clamp(exp(-ufogDensity * (Distance)), 0.0, 1.0);
+}
+
+float fogFactorExp2() {
+    float LOG2 = -1.442695;
+    float d = ufogDensity * (Distance);
+    return 1.0 - clamp(exp2(d * d * LOG2), 0.0, 1.0);
+}
+
+
+vec4 computeFog(vec4 color) {
+    float f = 0;
+    if (ufogMode == 0) { // Linear
+        f = fogFactorLinear();
+    }
+    else if (ufogMode == 1) { // EXP
+        f = fogFactorExp();
+    }
+    else if (ufogMode == 2) { // EXP2
+        f = fogFactorExp2();
+    }
+    return vec4(mix(color.rgb, ufogColor.rgb, f), color.a);
+}
+
+void main() {
+    vec4 lightColor = texture(texture1, LightMapCoord);
+
+    vec4 oColor = lightColor * Color * ucolor;
+    vec4 litColor = vec4(oColor.rgb * clamp(Light, 0, 1), oColor.a);
+
+    FragColor = computeFog(oColor);
+    if (FragColor.a < 0.1f) {
+        discard;
+    }
+}
diff --git a/game/client/src/main/resources/shaders/color_world.vsh b/game/client/src/main/resources/shaders/color_world.vsh
new file mode 100644
index 000000000..6eec498b0
--- /dev/null
+++ b/game/client/src/main/resources/shaders/color_world.vsh
@@ -0,0 +1,36 @@
+#version 410 core
+layout (location = 0) in vec3 aPos;
+layout (location = 1) in vec4 aColor;
+layout (location = 3) in vec2 aLightmap;
+layout (location = 4) in vec3 aNormal;
+
+out vec4 Color;
+out vec2 TexCoord;
+out vec2 LightMapCoord;
+out float Distance;
+out vec3 Light;
+
+uniform mat4 normalTransform;
+uniform vec4 lightModelAmbient;
+uniform vec4 lightSourcePosition[];
+uniform vec4 lightSourceDiffuse[];
+
+uniform mat4 model;
+uniform mat4 view;
+uniform mat4 projection;
+
+void main() {
+    vec4 p = vec4(aPos, 1);
+    gl_Position = projection * view * model * p;
+
+    Color = aColor;
+    LightMapCoord = aLightmap;
+
+    // Used for the radial fog in shader
+    Distance = length((view * model * p).xyz);
+
+    vec4 norm = normalize(normalTransform * model * vec4(aNormal, 0));
+    float dir1 = max(0.0f, dot(norm, lightSourcePosition[0]));
+    float dir2 = max(0.0f, dot(norm, lightSourcePosition[1]));
+    Light = (lightModelAmbient + lightSourceDiffuse[0] * (dir1 + dir2)).xyz;
+}
diff --git a/game/client/src/main/resources/shaders/font.fsh b/game/client/src/main/resources/shaders/font.fsh
new file mode 100644
index 000000000..969fa5cdb
--- /dev/null
+++ b/game/client/src/main/resources/shaders/font.fsh
@@ -0,0 +1,18 @@
+#version 410 core
+out vec4 FragColor;
+
+in vec4 Color;
+in vec2 TexCoord;
+in vec2 Lightmap;
+
+uniform vec4 ucolor;
+
+uniform sampler2D texture0;
+uniform sampler2D texture1;
+
+void main() {
+    FragColor = texture(texture0, TexCoord) * texture(texture1, Lightmap) * Color * ucolor;
+    if (FragColor.a < 0.1f) {
+        discard;
+    }
+}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/font.gsh b/game/client/src/main/resources/shaders/font.gsh
new file mode 100644
index 000000000..0cf0dc235
--- /dev/null
+++ b/game/client/src/main/resources/shaders/font.gsh
@@ -0,0 +1,43 @@
+#version 410 core
+layout (points) in;
+layout (triangle_strip, max_vertices = 4) out;
+
+in VS_OUT {
+    vec2 size;
+    float shift;
+    vec4 color;
+    vec2 uv;
+    vec2 uvSizes;
+    vec2 lightmap;
+} gs_in[];
+
+out vec4 Color;
+out vec2 TexCoord;
+out vec2 Lightmap;
+
+uniform mat4 model;
+uniform mat4 view;
+uniform mat4 projection;
+
+void main() {
+    Color = gs_in[0].color;
+    Lightmap = gs_in[0].lightmap;
+
+    TexCoord = gs_in[0].uv + vec2(0, gs_in[0].uvSizes.y);
+    gl_Position = projection * view * model * (gl_in[0].gl_Position + vec4(-gs_in[0].shift,  gs_in[0].size.y, 0.0, 0.0));
+    EmitVertex();
+
+    TexCoord = gs_in[0].uv + vec2(gs_in[0].uvSizes.x, gs_in[0].uvSizes.y);
+    gl_Position = projection * view * model * (gl_in[0].gl_Position + vec4(gs_in[0].size.x - gs_in[0].shift,  gs_in[0].size.y, 0.0, 0.0));
+    EmitVertex();
+
+    TexCoord = gs_in[0].uv + vec2(0, 0);
+    gl_Position = projection * view * model * (gl_in[0].gl_Position + vec4(gs_in[0].shift, 0, 0.0, 0.0));
+    EmitVertex();
+
+    TexCoord = gs_in[0].uv + vec2(gs_in[0].uvSizes.x, 0);
+    gl_Position = projection * view * model * (gl_in[0].gl_Position + vec4(gs_in[0].size.x + gs_in[0].shift, 0, 0.0, 0.0));
+    EmitVertex();
+
+    EndPrimitive();
+}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/font.vsh b/game/client/src/main/resources/shaders/font.vsh
new file mode 100644
index 000000000..3c9e8bb1a
--- /dev/null
+++ b/game/client/src/main/resources/shaders/font.vsh
@@ -0,0 +1,30 @@
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aSize;
+layout (location = 2) in float aShift;
+layout (location = 3) in vec4 aColor;
+layout (location = 4) in vec2 aUv;
+layout (location = 5) in vec2 aUvSizes;
+layout (location = 6) in vec2 aLightmap;
+
+out VS_OUT {
+    vec2 size;
+    float shift;
+    vec4 color;
+    vec2 uv;
+    vec2 uvSizes;
+    vec2 lightmap;
+} vs_out;
+
+uniform float uZ;
+
+void main() {
+    gl_Position = vec4(aPos, uZ, 1);
+
+    vs_out.size = aSize;
+    vs_out.shift = aShift;
+    vs_out.color = aColor;
+    vs_out.uv = aUv;
+    vs_out.uvSizes = aUvSizes;
+    vs_out.lightmap = aLightmap;
+}
diff --git a/game/client/src/main/resources/shaders/interface.fsh b/game/client/src/main/resources/shaders/interface.fsh
new file mode 100644
index 000000000..ded77c9ca
--- /dev/null
+++ b/game/client/src/main/resources/shaders/interface.fsh
@@ -0,0 +1,13 @@
+#version 410 core
+
+out vec4 FragColor;
+
+in vec4 Color;
+in vec2 TexCoord;
+
+uniform vec4 ucolor;
+uniform sampler2D texture0;
+
+void main() {
+    FragColor = texture(texture0, TexCoord) * Color * ucolor;
+}
diff --git a/game/client/src/main/resources/shaders/interface.vsh b/game/client/src/main/resources/shaders/interface.vsh
new file mode 100644
index 000000000..1df6d673c
--- /dev/null
+++ b/game/client/src/main/resources/shaders/interface.vsh
@@ -0,0 +1,18 @@
+#version 410 core
+layout (location = 0) in vec3 aPos;
+layout (location = 1) in vec4 aColor;
+layout (location = 2) in vec2 aUV;
+
+out vec4 Color;
+out vec2 TexCoord;
+
+uniform mat4 model;
+uniform mat4 view;
+uniform mat4 projection;
+
+void main() {
+    gl_Position = projection * view * model * vec4(aPos, 1);
+
+    TexCoord = aUV;
+    Color = aColor;
+}
diff --git a/game/client/src/main/resources/shaders/lines.fsh b/game/client/src/main/resources/shaders/lines.fsh
new file mode 100644
index 000000000..8b8fb3a78
--- /dev/null
+++ b/game/client/src/main/resources/shaders/lines.fsh
@@ -0,0 +1,12 @@
+#version 410 core
+out vec4 FragColor;
+
+in vec4 Color;
+uniform vec4 ucolor;
+
+void main() {
+    FragColor = Color * ucolor;
+    if (FragColor.a < 0.1f) {
+        discard;
+    }
+}
diff --git a/game/client/src/main/resources/shaders/lines.gsh b/game/client/src/main/resources/shaders/lines.gsh
new file mode 100644
index 000000000..811cb2e7a
--- /dev/null
+++ b/game/client/src/main/resources/shaders/lines.gsh
@@ -0,0 +1,40 @@
+#version 410 core
+layout (lines) in;
+layout (triangle_strip, max_vertices = 4) out;
+
+in VS_OUT {
+    vec4 color;
+} gs_in[];
+
+out vec4 Color;
+
+uniform float viewWidth;
+uniform float viewHeight;
+uniform float uLineWidth;
+
+void main()
+{
+    vec4 p1 = gl_in[0].gl_Position;
+    vec4 p2 = gl_in[1].gl_Position;
+
+    vec2 dir    = normalize((p2.xy/p2.w - p1.xy/p1.w) * vec2(viewWidth, viewHeight));
+    vec2 offset = vec2(-dir.y, dir.x) * uLineWidth / vec2(viewWidth, viewHeight);
+
+    Color = gs_in[0].color;
+    gl_Position = p1 + vec4(offset.xy * p1.w, 0.0, 0.0);
+    EmitVertex();
+
+    Color = gs_in[0].color;
+    gl_Position = p1 - vec4(offset.xy * p1.w, 0.0, 0.0);
+    EmitVertex();
+
+    Color = gs_in[1].color;
+    gl_Position = p2 + vec4(offset.xy * p2.w, 0.0, 0.0);
+    EmitVertex();
+
+    Color = gs_in[1].color;
+    gl_Position = p2 - vec4(offset.xy * p2.w, 0.0, 0.0);
+    EmitVertex();
+
+    EndPrimitive();
+}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/lines.vsh b/game/client/src/main/resources/shaders/lines.vsh
new file mode 100644
index 000000000..e88cd1228
--- /dev/null
+++ b/game/client/src/main/resources/shaders/lines.vsh
@@ -0,0 +1,18 @@
+#version 410 core
+layout (location = 0) in vec3 aPos;
+layout (location = 1) in vec4 aColor;
+
+
+out VS_OUT {
+    vec4 color;
+} vs_out;
+
+uniform mat4 model;
+uniform mat4 view;
+uniform mat4 projection;
+
+void main() {
+    gl_Position = projection * view * model * vec4(aPos, 1);
+
+    vs_out.color = aColor;
+}
diff --git a/game/client/src/main/resources/shaders/particle.fsh b/game/client/src/main/resources/shaders/particle.fsh
index 84c62fb8a..f7ffa5db6 100644
--- a/game/client/src/main/resources/shaders/particle.fsh
+++ b/game/client/src/main/resources/shaders/particle.fsh
@@ -5,10 +5,12 @@ in vec4 Color;
 in vec2 TexCoord;
 in vec2 Lightmap;
 
-uniform float partialTick;
 uniform sampler2D texture0;
 uniform sampler2D texture1;
 
 void main() {
     FragColor = texture(texture0, TexCoord) * texture(texture1, Lightmap) * Color;
+    if (FragColor.a < 0.1f) {
+        discard;
+    }
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/blur/post.fsh b/game/client/src/main/resources/shaders/photo/blur/post.fsh
index f4d556b12..f21919af8 100644
--- a/game/client/src/main/resources/shaders/photo/blur/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/blur/post.fsh
@@ -1,4 +1,6 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 
@@ -6,7 +8,6 @@ uniform float width;
 uniform float height;
 uniform float intensity;
 
-varying vec2 texcoord;
 
 vec3 getBlur(){
 	vec3 blur = vec3(0.0);
@@ -19,7 +20,7 @@ vec3 getBlur(){
 		for(int j=0; j < q; j++){
 			float strength = 1 - sin(length(vec2(i - qh, j - qh)) / qh);
 			
-			blur += texture2D(colortex0, texcoord + vec2(i - qh, j - qh) * pixel).rgb * strength;
+			blur += texture(colortex0, TexCoords + vec2(i - qh, j - qh) * pixel).rgb * strength;
 			
 			allStrengths += strength;
 		}
@@ -29,9 +30,9 @@ vec3 getBlur(){
 }
 
 void main(){
-	vec3 color = texture2D(colortex0, texcoord).rgb;
+	vec3 color = texture(colortex0, TexCoords).rgb;
 
-	float blurFactor = clamp(distance(texcoord, vec2(0.5)) * 1.0, 0.0, 1.0);
+	float blurFactor = clamp(distance(TexCoords, vec2(0.5)) * 1.0, 0.0, 1.0);
 	vec3 blur = getBlur();
 
 	//Apply Blur
@@ -44,5 +45,5 @@ void main(){
 	//Bloom
 	//color = color * 0.93 + clamp(pow(blur, vec3(2.0)), 0.0, 1.0) * 0.4;
 	
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/blur/post.vsh b/game/client/src/main/resources/shaders/photo/blur/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/blur/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/blur/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/distantblur/post.fsh b/game/client/src/main/resources/shaders/photo/distantblur/post.fsh
index e78f7a680..611e72dfe 100644
--- a/game/client/src/main/resources/shaders/photo/distantblur/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/distantblur/post.fsh
@@ -1,4 +1,6 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 uniform sampler2D depthtex0;
@@ -7,7 +9,6 @@ uniform float intensity;
 uniform float width;
 uniform float height;
 
-varying vec2 texcoord;
 
 vec3 getBlur(){
 	vec3 blur = vec3(0.0);
@@ -20,7 +21,7 @@ vec3 getBlur(){
 		for(int j=0; j < q; j++){
 			float strength = 1 - sin(length(vec2(i - qh, j - qh)) / qh);
 			
-			blur += texture2D(colortex0, texcoord + vec2(i - qh, j - qh) * pixel).rgb * strength;
+			blur += texture(colortex0, TexCoords + vec2(i - qh, j - qh) * pixel).rgb * strength;
 			
 			allStrengths += strength;
 		}
@@ -31,8 +32,8 @@ vec3 getBlur(){
 
 void main()
 {
-	vec3 color = texture2D(colortex0, texcoord).rgb;
-	float depth = texture2D(depthtex0, texcoord).r;
+	vec3 color = texture(colortex0, TexCoords).rgb;
+	float depth = texture(depthtex0, TexCoords).r;
 
 	depth = (depth - (0.45 + 0.1 * (1.0 - intensity))) * 20;
 
@@ -42,5 +43,5 @@ void main()
 	//color = vec3(depth);
 	//color = blur;
 	
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/distantblur/post.vsh b/game/client/src/main/resources/shaders/photo/distantblur/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/distantblur/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/distantblur/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/eerie/post.fsh b/game/client/src/main/resources/shaders/photo/eerie/post.fsh
index 6173bcd20..5889c6c91 100644
--- a/game/client/src/main/resources/shaders/photo/eerie/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/eerie/post.fsh
@@ -1,22 +1,22 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 
 uniform float intensity;
 
-varying vec2 texcoord;
-
 void main(){
-	vec3 color = texture2D(colortex0, texcoord).rgb;
+	vec3 color = texture(colortex0, TexCoords).rgb;
 	
 	float grayscale = (color.r + color.g + color.b) / 3.0;
 	
 	color = mix(color, vec3(grayscale), 0.5 * intensity);
 	
-	float vignette = length(vec2(texcoord - 0.5));
+	float vignette = length(vec2(TexCoords - 0.5));
 	vignette = clamp((vignette - 0.4) * 3, 0.0, 1.0);
 	
 	color = mix(color, vec3(0.0), vignette);
 	
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/eerie/post.vsh b/game/client/src/main/resources/shaders/photo/eerie/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/eerie/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/eerie/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/inverted/post.fsh b/game/client/src/main/resources/shaders/photo/inverted/post.fsh
index 57be58d11..15d45caa2 100644
--- a/game/client/src/main/resources/shaders/photo/inverted/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/inverted/post.fsh
@@ -1,15 +1,15 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 
 uniform float intensity;
 
-varying vec2 texcoord;
-
 void main(){
-	vec3 color = texture2D(colortex0, texcoord).rgb;
+	vec3 color = texture(colortex0, TexCoords).rgb;
 
 	color = mix(color, vec3(1.0 - color.r, 1.0 - color.g, 1.0 - color.b), intensity);
 
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/inverted/post.vsh b/game/client/src/main/resources/shaders/photo/inverted/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/inverted/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/inverted/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/outline/post.fsh b/game/client/src/main/resources/shaders/photo/outline/post.fsh
index 378dbf61f..63830932c 100644
--- a/game/client/src/main/resources/shaders/photo/outline/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/outline/post.fsh
@@ -1,4 +1,6 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 uniform sampler2D depthtex0;
@@ -7,27 +9,25 @@ uniform float width;
 uniform float height;
 uniform float intensity;
 
-varying vec2 texcoord;
-
 float getDepth(vec2 coord){
-	return texture2D(depthtex0, coord).r;
+	return texture(depthtex0, coord).r;
 }
 
 void main(){
-	vec3 color = texture2D(colortex0, texcoord).rgb;
+	vec3 color = texture(colortex0, TexCoords).rgb;
 	
 	float outline = 0.0;
 	
 	float size = 4.0 * intensity;
 	
-	outline += clamp(getDepth(texcoord) - getDepth(texcoord + vec2(size / width, 0)), 0.0, 1.0);
-	outline += clamp(getDepth(texcoord) - getDepth(texcoord - vec2(size / width, 0)), 0.0, 1.0);
-	outline += clamp(getDepth(texcoord) - getDepth(texcoord + vec2(0, size / height)), 0.0, 1.0);
-	outline += clamp(getDepth(texcoord) - getDepth(texcoord - vec2(0, size / height)), 0.0, 1.0);
+	outline += clamp(getDepth(TexCoords) - getDepth(TexCoords + vec2(size / width, 0)), 0.0, 1.0);
+	outline += clamp(getDepth(TexCoords) - getDepth(TexCoords - vec2(size / width, 0)), 0.0, 1.0);
+	outline += clamp(getDepth(TexCoords) - getDepth(TexCoords + vec2(0, size / height)), 0.0, 1.0);
+	outline += clamp(getDepth(TexCoords) - getDepth(TexCoords - vec2(0, size / height)), 0.0, 1.0);
 	
 	outline = 1.0 - clamp(outline * 512, 0.0, 1.0);
 	
 	color *= outline;
 	
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/outline/post.vsh b/game/client/src/main/resources/shaders/photo/outline/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/outline/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/outline/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/outline2/post.fsh b/game/client/src/main/resources/shaders/photo/outline2/post.fsh
index 24d23552f..0c2f76a45 100644
--- a/game/client/src/main/resources/shaders/photo/outline2/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/outline2/post.fsh
@@ -1,4 +1,6 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D depthtex0;
 
@@ -6,10 +8,8 @@ uniform float width;
 uniform float height;
 uniform float intensity;
 
-varying vec2 texcoord;
-
 float getDepth(vec2 coord){
-	return texture2D(depthtex0, coord).r;
+	return texture(depthtex0, coord).r;
 }
 
 void main(){
@@ -17,12 +17,12 @@ void main(){
 	
 	float size = 4.0 * intensity;
 	
-	outline += clamp(getDepth(texcoord) - getDepth(texcoord + vec2(size / width, 0)), 0.0, 1.0);
-	outline += clamp(getDepth(texcoord) - getDepth(texcoord - vec2(size / width, 0)), 0.0, 1.0);
-	outline += clamp(getDepth(texcoord) - getDepth(texcoord + vec2(0, size / height)), 0.0, 1.0);
-	outline += clamp(getDepth(texcoord) - getDepth(texcoord - vec2(0, size / height)), 0.0, 1.0);
+	outline += clamp(getDepth(TexCoords) - getDepth(TexCoords + vec2(size / width, 0)), 0.0, 1.0);
+	outline += clamp(getDepth(TexCoords) - getDepth(TexCoords - vec2(size / width, 0)), 0.0, 1.0);
+	outline += clamp(getDepth(TexCoords) - getDepth(TexCoords + vec2(0, size / height)), 0.0, 1.0);
+	outline += clamp(getDepth(TexCoords) - getDepth(TexCoords - vec2(0, size / height)), 0.0, 1.0);
 	
 	outline = 1.0 - clamp(outline * 512, 0.0, 1.0);
 	
-	gl_FragColor = vec4(vec3(outline), 1.0);
+	FragColor = vec4(vec3(outline), 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/outline2/post.vsh b/game/client/src/main/resources/shaders/photo/outline2/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/outline2/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/outline2/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/sepia/post.fsh b/game/client/src/main/resources/shaders/photo/sepia/post.fsh
index 7a581ef57..048cc98ba 100644
--- a/game/client/src/main/resources/shaders/photo/sepia/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/sepia/post.fsh
@@ -1,11 +1,11 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 
 uniform float intensity;
 
-varying vec2 texcoord;
-
 vec3 toSepia(vec3 color)
 {
 	color.r = color.r * 0.393 + color.g * 0.769 + color.b * 0.189;
@@ -17,10 +17,10 @@ vec3 toSepia(vec3 color)
 
 void main()
 {
-	vec3 color = texture2D(colortex0, texcoord).rgb;
+	vec3 color = texture(colortex0, TexCoords).rgb;
 	vec3 sepia = toSepia(color);
 
 	color = mix(color, sepia, intensity);
 
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/sepia/post.vsh b/game/client/src/main/resources/shaders/photo/sepia/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/sepia/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/sepia/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/silhouette/post.fsh b/game/client/src/main/resources/shaders/photo/silhouette/post.fsh
index ef0bcffdc..a739d1a83 100644
--- a/game/client/src/main/resources/shaders/photo/silhouette/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/silhouette/post.fsh
@@ -1,20 +1,20 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 uniform sampler2D depthtex0;
 
 uniform float intensity;
 
-varying vec2 texcoord;
-
 void main()
 {
-	vec3 color = texture2D(colortex0, texcoord).rgb;
-	float depth = texture2D(depthtex0, texcoord).r;
+	vec3 color = texture(colortex0, TexCoords).rgb;
+	float depth = texture(depthtex0, TexCoords).r;
 
 	depth = (depth - 0.45) * 10;
 
 	color = mix(color, vec3(depth), intensity);
 
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/silhouette/post.vsh b/game/client/src/main/resources/shaders/photo/silhouette/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/silhouette/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/silhouette/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/tiltshift/post.fsh b/game/client/src/main/resources/shaders/photo/tiltshift/post.fsh
index b0ecd9e97..e119bccc7 100644
--- a/game/client/src/main/resources/shaders/photo/tiltshift/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/tiltshift/post.fsh
@@ -1,4 +1,6 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 uniform sampler2D depthtex0;
@@ -7,23 +9,21 @@ uniform float width;
 uniform float height;
 uniform float intensity;
 
-varying vec2 texcoord;
-
 vec3 getBlur(float r){
 	float x, y, xx, yy, rr = r * r, dx, dy, w, w0;
 	w0 = 0.3780 / pow(r, 1.975);
 	vec2 p;
 	vec4 col = vec4(0.0, 0.0, 0.0, 0.0);
-	for (dx = 1.0 / width, x = -r, p.x = (texcoord.x) + (x * dx); x <= r; x++, p.x += dx)
+	for (dx = 1.0 / width, x = -r, p.x = (TexCoords.x) + (x * dx); x <= r; x++, p.x += dx)
 	{
 		xx = x * x;
-		for (dy = 1.0 / height, y = -r, p.y = (texcoord.y) + (y * dy); y <= r; y++, p.y += dy)
+		for (dy = 1.0 / height, y = -r, p.y = (TexCoords.y) + (y * dy); y <= r; y++, p.y += dy)
 		{
 			yy = y * y;
 			if (xx + yy <= rr)
 			{
 				w = w0 * exp((-xx - yy) / (2.0 * rr));
-				col += texture2D(colortex0, p) * w;
+				col += texture(colortex0, p) * w;
 			}
 		}
 	}
@@ -32,9 +32,9 @@ vec3 getBlur(float r){
 
 void main()
 {
-	vec3 color = texture2D(colortex0, texcoord).rgb;
+	vec3 color = texture(colortex0, TexCoords).rgb;
 
-	float blurFactor = clamp(distance(texcoord, vec2(0.5)) * 4 * intensity, 0.0, 1.0);
+	float blurFactor = clamp(distance(TexCoords, vec2(0.5)) * 4 * intensity, 0.0, 1.0);
 	vec3 blur = getBlur(blurFactor * 15);
 
 	//Apply Blur
@@ -46,5 +46,5 @@ void main()
 	//Bloom
 	//color = color * 0.93 + clamp(pow(blur, vec3(2.0)), 0.0, 1.0) * 0.4;
 	
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/tiltshift/post.vsh b/game/client/src/main/resources/shaders/photo/tiltshift/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/tiltshift/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/tiltshift/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/vignette/post.fsh b/game/client/src/main/resources/shaders/photo/vignette/post.fsh
index 9188eb8fe..7ae618a54 100644
--- a/game/client/src/main/resources/shaders/photo/vignette/post.fsh
+++ b/game/client/src/main/resources/shaders/photo/vignette/post.fsh
@@ -1,17 +1,17 @@
-#version 120
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 uniform float intensity;
 
-varying vec2 texcoord;
-
 void main(){
-	vec3 color = texture2D(colortex0, texcoord).rgb;
+	vec3 color = texture(colortex0, TexCoords).rgb;
 	
-	float vignette = length(vec2(texcoord - 0.5)) * intensity;
+	float vignette = length(vec2(TexCoords - 0.5)) * intensity;
 	vignette = clamp((vignette - 0.3) * 3, 0.0, 1.0);
 	
 	color = mix(color, vec3(0.0), vignette);
 	
-	gl_FragColor = vec4(color, 1.0);
+	FragColor = vec4(color, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/photo/vignette/post.vsh b/game/client/src/main/resources/shaders/photo/vignette/post.vsh
index 9c7ba53f5..c95c4842f 100644
--- a/game/client/src/main/resources/shaders/photo/vignette/post.vsh
+++ b/game/client/src/main/resources/shaders/photo/vignette/post.vsh
@@ -1,9 +1,11 @@
-#version 120
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
 
-varying vec2 texcoord;
+out vec2 TexCoords;
 
-void main(){
-	gl_Position = ftransform();
-	
-	texcoord = gl_MultiTexCoord0.xy;
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/post.vsh b/game/client/src/main/resources/shaders/post.vsh
deleted file mode 100644
index 5650d067e..000000000
--- a/game/client/src/main/resources/shaders/post.vsh
+++ /dev/null
@@ -1,9 +0,0 @@
-#version 120
-
-varying vec2 texcoord;
-
-void main(){
-    gl_Position = ftransform();
-
-    texcoord = gl_MultiTexCoord0.xy;
-}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/post/base.fsh b/game/client/src/main/resources/shaders/post/base.fsh
new file mode 100644
index 000000000..1f1cfc31a
--- /dev/null
+++ b/game/client/src/main/resources/shaders/post/base.fsh
@@ -0,0 +1,82 @@
+#version 410
+out vec4 FragColor;
+in vec2 TexCoords;
+
+uniform sampler2D colortex0;
+uniform sampler2D depthtex0;
+
+uniform float gamma;
+
+uniform int cbCorrectionMode;
+
+uniform float width;
+uniform float height;
+
+
+vec3 adjustGamma(vec3 color, float value)
+{
+    return pow(color, vec3(1.0 - value + 0.5));
+}
+
+vec3 cbCorrection(vec3 tex)
+{
+    int mode = cbCorrectionMode;
+    if (mode < 1 || mode > 4) return tex;
+
+    if (mode == 4)//Grayscale
+    {
+        return vec3((tex.r + tex.g + tex.b) / 3.0f);
+    }
+
+    float L = (17.8824 * tex.r) + (43.5161 * tex.g) + (4.11935 * tex.b);
+    float M = (3.45565 * tex.r) + (27.1554 * tex.g) + (3.86714 * tex.b);
+    float S = (0.0299566 * tex.r) + (0.184309 * tex.g) + (1.46709 * tex.b);
+
+    float l, m, s;
+    if (mode == 1)//Protanopia
+    {
+        l = 0.0 * L + 2.02344 * M + -2.52581 * S;
+        m = 0.0 * L + 1.0 * M + 0.0 * S;
+        s = 0.0 * L + 0.0 * M + 1.0 * S;
+    }
+
+    if (mode == 2)//Deuteranopia
+    {
+        l = 1.0 * L + 0.0 * M + 0.0 * S;
+        m = 0.494207 * L + 0.0 * M + 1.24827 * S;
+        s = 0.0 * L + 0.0 * M + 1.0 * S;
+    }
+
+    if (mode == 3)//Tritanopia
+    {
+        l = 1.0 * L + 0.0 * M + 0.0 * S;
+        m = 0.0 * L + 1.0 * M + 0.0 * S;
+        s = -0.395913 * L + 0.801109 * M + 0.0 * S;
+    }
+
+    vec3 error;
+    error.r = (0.0809444479 * l) + (-0.130504409 * m) + (0.116721066 * s);
+    error.g = (-0.0102485335 * l) + (0.0540193266 * m) + (-0.113614708 * s);
+    error.b = (-0.000365296938 * l) + (-0.00412161469 * m) + (0.693511405 * s);
+    vec3 diff = tex - error;
+    vec3 correction;
+    correction.r = 0.0;
+    correction.g =  (diff.r * 0.7) + (diff.g * 1.0);
+    correction.b =  (diff.r * 0.7) + (diff.b * 1.0);
+    correction = tex + correction;
+
+    return correction;
+}
+
+void main()
+{
+    vec3 color = vec3(0.0);
+
+    color = texture(colortex0, TexCoords).rgb;
+
+    color = cbCorrection(color);
+
+    color = adjustGamma(color, gamma);
+
+    FragColor = vec4(color, 1.0);
+}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/post/base.vsh b/game/client/src/main/resources/shaders/post/base.vsh
new file mode 100644
index 000000000..c95c4842f
--- /dev/null
+++ b/game/client/src/main/resources/shaders/post/base.vsh
@@ -0,0 +1,11 @@
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
+
+out vec2 TexCoords;
+
+void main()
+{
+	TexCoords = aTexCoords;
+	gl_Position = vec4(aPos, 0.0, 1.0);
+}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/post.fsh b/game/client/src/main/resources/shaders/post/post.fsh
similarity index 79%
rename from game/client/src/main/resources/shaders/post.fsh
rename to game/client/src/main/resources/shaders/post/post.fsh
index 6b9aa03e7..180f9656c 100644
--- a/game/client/src/main/resources/shaders/post.fsh
+++ b/game/client/src/main/resources/shaders/post/post.fsh
@@ -1,4 +1,8 @@
-#version 120
+#version 410
+
+out vec4 FragColor;
+
+in vec2 TexCoords;
 
 uniform sampler2D colortex0;
 uniform sampler2D depthtex0;
@@ -23,8 +27,6 @@ uniform float width;
 uniform float height;
 uniform float frameTimeCounter;
 
-varying vec2 texcoord;
-
 #define PI 3.14159
 
 // FXAA defines
@@ -35,11 +37,11 @@ float FXAA_SPAN_MAX = 8.0f * fxaa;
 vec4 applyFXAA(vec2 fragCoord, sampler2D tex, vec2 uViewportSize) {
     vec4 color;
     vec2 inverseVP = vec2(1.0 / uViewportSize.x, 1.0 / uViewportSize.y);
-    vec3 rgbNW = texture2D(tex, (fragCoord + vec2(-1.0, -1.0)) * inverseVP).xyz;
-    vec3 rgbNE = texture2D(tex, (fragCoord + vec2(1.0, -1.0)) * inverseVP).xyz;
-    vec3 rgbSW = texture2D(tex, (fragCoord + vec2(-1.0, 1.0)) * inverseVP).xyz;
-    vec3 rgbSE = texture2D(tex, (fragCoord + vec2(1.0, 1.0)) * inverseVP).xyz;
-    vec3 rgbM  = texture2D(tex, fragCoord  * inverseVP).xyz;
+    vec3 rgbNW = texture(tex, (fragCoord + vec2(-1.0, -1.0)) * inverseVP).xyz;
+    vec3 rgbNE = texture(tex, (fragCoord + vec2(1.0, -1.0)) * inverseVP).xyz;
+    vec3 rgbSW = texture(tex, (fragCoord + vec2(-1.0, 1.0)) * inverseVP).xyz;
+    vec3 rgbSE = texture(tex, (fragCoord + vec2(1.0, 1.0)) * inverseVP).xyz;
+    vec3 rgbM  = texture(tex, fragCoord  * inverseVP).xyz;
     vec3 luma = vec3(0.299, 0.587, 0.114);
     float lumaNW = dot(rgbNW, luma);
     float lumaNE = dot(rgbNE, luma);
@@ -62,11 +64,11 @@ vec4 applyFXAA(vec2 fragCoord, sampler2D tex, vec2 uViewportSize) {
     dir * rcpDirMin)) * inverseVP;
 
     vec3 rgbA = 0.5 * (
-    texture2D(tex, fragCoord * inverseVP + dir * (1.0 / 3.0 - 0.5)).xyz +
-    texture2D(tex, fragCoord * inverseVP + dir * (2.0 / 3.0 - 0.5)).xyz);
+    texture(tex, fragCoord * inverseVP + dir * (1.0 / 3.0 - 0.5)).xyz +
+    texture(tex, fragCoord * inverseVP + dir * (2.0 / 3.0 - 0.5)).xyz);
     vec3 rgbB = rgbA * 0.5 + 0.25 * (
-    texture2D(tex, fragCoord * inverseVP + dir * -0.5).xyz +
-    texture2D(tex, fragCoord * inverseVP + dir * 0.5).xyz);
+    texture(tex, fragCoord * inverseVP + dir * -0.5).xyz +
+    texture(tex, fragCoord * inverseVP + dir * 0.5).xyz);
 
     float lumaB = dot(rgbB, luma);
     if ((lumaB < lumaMin) || (lumaB > lumaMax))
@@ -115,7 +117,7 @@ void Bloom(inout vec3 color) {
 			
 			float strength = dist;
 			
-			blur += pow(texture2D(colortex0, texcoord.xy + offset).rgb, vec3(2.2f)) * strength;
+			blur += pow(texture(colortex0, TexCoords + offset).rgb, vec3(2.2f)) * strength;
 			allStrengths += strength;
 		}
 	}
@@ -127,7 +129,7 @@ void Bloom(inout vec3 color) {
 }
 
 void HeatHaze(inout vec2 coord, float amount) {
-	float depth = texture2D(depthtex0, coord.xy).r;
+	float depth = texture(depthtex0, coord.xy).r;
 	float strength = pow(depth, 500);
 	strength = (strength - 0.16) * 2.0f;
 	strength = clamp(strength, 0.0f, 1.0f) * amount;
@@ -153,22 +155,22 @@ vec3 colorEffects(vec3 tex) {
 
 void main() {
     vec3 color = vec3(0.0);
-	vec2 coord = texcoord;
-	
+	vec2 coord = TexCoords;
+
 	if(heatHaze > 0) {
 		HeatHaze(coord, heatHaze);
 	}
-	
+
     if (fxaa > 0.01) {
         color = applyFXAA(vec2(coord.x * width, coord.y * height), colortex0, vec2(width, height)).rgb;
     } else {
-        color = texture2D(colortex0, coord.xy).rgb;
+        color = texture(colortex0, coord.xy).rgb;
     }
-	
+
 	if(bloom > 0) {
 		Bloom(color);
 	}
-	
+
     // Perform color correction
     color = adjustBrightness(color, brightness);
     color = adjustContrast(color, contrast);
@@ -176,6 +178,10 @@ void main() {
     color = adjustSaturation(color, saturation);
     color = adjustColor(color, rMod, gMod, bMod);
     color = colorEffects(color);
-	
-    gl_FragColor = vec4(color, 1.0);
+
+    FragColor = vec4(color, 1.0);
+
+//    float depth = texture(depthtex0, TexCoords).r;
+//    depth = pow(depth, 1000);
+//    FragColor = vec4(depth, depth, depth, 1.0);
 }
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/post/post.vsh b/game/client/src/main/resources/shaders/post/post.vsh
new file mode 100644
index 000000000..1ae551a3a
--- /dev/null
+++ b/game/client/src/main/resources/shaders/post/post.vsh
@@ -0,0 +1,11 @@
+#version 410 core
+layout (location = 0) in vec2 aPos;
+layout (location = 1) in vec2 aTexCoords;
+
+out vec2 TexCoords;
+
+void main()
+{
+    TexCoords = aTexCoords;
+    gl_Position = vec4(aPos, 0.0, 1.0);
+}
\ No newline at end of file
diff --git a/game/client/src/main/resources/shaders/showdepth.fsh b/game/client/src/main/resources/shaders/post/showdepth.fsh
similarity index 76%
rename from game/client/src/main/resources/shaders/showdepth.fsh
rename to game/client/src/main/resources/shaders/post/showdepth.fsh
index 1b8d1ff11..bc1360925 100644
--- a/game/client/src/main/resources/shaders/showdepth.fsh
+++ b/game/client/src/main/resources/shaders/post/showdepth.fsh
@@ -5,7 +5,7 @@ uniform sampler2D depthtex0;
 varying vec2 texcoord;
 
 void main(){
-	float depth = texture2D(depthtex0, texcoord).r;
+	float depth = texture(depthtex0, texcoord).r;
 	
 	depth = pow(depth, 1000);
 	
diff --git a/game/client/src/main/resources/shaders/showdepth.vsh b/game/client/src/main/resources/shaders/post/showdepth.vsh
similarity index 100%
rename from game/client/src/main/resources/shaders/showdepth.vsh
rename to game/client/src/main/resources/shaders/post/showdepth.vsh
diff --git a/game/client/src/main/resources/shaders/world.fsh b/game/client/src/main/resources/shaders/world.fsh
new file mode 100644
index 000000000..9d9f5081b
--- /dev/null
+++ b/game/client/src/main/resources/shaders/world.fsh
@@ -0,0 +1,66 @@
+#version 410 core
+
+out vec4 FragColor;
+
+in vec4 Color;
+in vec2 TexCoord;
+in vec2 LightMapCoord;
+in float Distance;
+in vec3 Light;
+
+uniform vec4 ucolor;
+
+uniform vec4 ufogColor;
+uniform int ufogMode;
+uniform float ufogStart;
+uniform float ufogEnd;
+uniform float ufogDensity;
+
+uniform sampler2D texture0;
+uniform sampler2D texture1;
+
+// Taken from https://github.com/hughsk/glsl-fog
+float fogFactorLinear() {
+    return 1.0 - clamp(((ufogEnd - (Distance)) / (ufogEnd - ufogStart)), 0.0, 1.0);
+}
+
+float fogFactorExp() {
+    return 1.0 - clamp(exp(-ufogDensity * (Distance)), 0.0, 1.0);
+}
+
+float fogFactorExp2() {
+    float LOG2 = -1.442695;
+    float d = ufogDensity * (Distance);
+    return 1.0 - clamp(exp2(d * d * LOG2), 0.0, 1.0);
+}
+
+
+vec4 computeFog(vec4 color) {
+    float f = 0;
+    if (ufogMode == 0) { // Linear
+        f = fogFactorLinear();
+    }
+    else if (ufogMode == 1) { // EXP
+        f = fogFactorExp();
+    }
+    else if (ufogMode == 2) { // EXP2
+        f = fogFactorExp2();
+    }
+    return vec4(mix(color.rgb, ufogColor.rgb, f), color.a);
+}
+
+void main() {
+    vec4 lightColor = texture(texture1, LightMapCoord);
+    vec4 texColor = texture(texture0, TexCoord);
+
+    vec4 oColor = texColor * lightColor * Color * ucolor;
+    vec4 litColor = vec4(oColor.rgb * clamp(Light, 0, 1), oColor.a);
+
+    vec4 fColor = computeFog(litColor);
+
+
+    FragColor = fColor;
+    if (FragColor.a < 0.1f) {
+        discard;
+    }
+}
diff --git a/game/client/src/main/resources/shaders/world.vsh b/game/client/src/main/resources/shaders/world.vsh
new file mode 100644
index 000000000..97d6d3f8e
--- /dev/null
+++ b/game/client/src/main/resources/shaders/world.vsh
@@ -0,0 +1,38 @@
+#version 410 core
+layout (location = 0) in vec3 aPos;
+layout (location = 1) in vec4 aColor;
+layout (location = 2) in vec2 aUV;
+layout (location = 3) in vec2 aLightmap;
+layout (location = 4) in vec3 aNormal;
+
+out vec4 Color;
+out vec2 TexCoord;
+out vec2 LightMapCoord;
+out float Distance;
+out vec3 Light;
+
+uniform mat4 normalTransform;
+uniform vec4 lightModelAmbient;
+uniform vec4 lightSourcePosition[];
+uniform vec4 lightSourceDiffuse[];
+
+uniform mat4 model;
+uniform mat4 view;
+uniform mat4 projection;
+
+void main() {
+    vec4 p = vec4(aPos, 1);
+    gl_Position = projection * view * model * p;
+
+    TexCoord = aUV;
+    Color = aColor;
+    LightMapCoord = aLightmap;
+
+    // Used for the radial fog in shader
+    Distance = length((view * model * p).xyz);
+
+    vec4 norm = normalize(normalTransform * model * vec4(aNormal, 0));
+    float dir1 = max(0.0f, dot(norm, lightSourcePosition[0]));
+    float dir2 = max(0.0f, dot(norm, lightSourcePosition[1]));
+    Light = (lightModelAmbient + lightSourceDiffuse[0] * (dir1 + dir2)).xyz;
+}
diff --git a/game/core/src/main/java/net/minecraft/core/block/BlockLogicPortal.java b/game/core/src/main/java/net/minecraft/core/block/BlockLogicPortal.java
index 7e529741b..e9be8f585 100644
--- a/game/core/src/main/java/net/minecraft/core/block/BlockLogicPortal.java
+++ b/game/core/src/main/java/net/minecraft/core/block/BlockLogicPortal.java
@@ -227,7 +227,7 @@ public class BlockLogicPortal extends BlockLogicTransparent implements IPainted
             }
         }
 
-        return new Bounds(axis, new TilePos(tilePos), maxBoundA, maxBoundY);
+        return new Bounds(axis, new TilePos(p), maxBoundA, maxBoundY);
     }
 
     public boolean tryToCreatePortal(@NotNull World world, @NotNull TilePosc tilePos, @Nullable DyeColor color) {
@@ -240,7 +240,7 @@ public class BlockLogicPortal extends BlockLogicTransparent implements IPainted
         world.noNeighborUpdate = true;
         switch (bounds.axis) {
             case X: {
-                TilePos p = new TilePos(0, 0, 0);
+                TilePos p = new TilePos();
                 for (int ra = 1; ra < bounds.maxBoundA; ra++) {
                     for (int ry = 1; ry < bounds.maxBoundB; ry++) {
                         p.x = bounds.pos.x + ra;
@@ -260,7 +260,7 @@ public class BlockLogicPortal extends BlockLogicTransparent implements IPainted
                 break;
             }
             case Z: {
-                TilePos p = new TilePos(0, 0, 0);
+                TilePos p = new TilePos();
                 for (int ra = 1; ra < bounds.maxBoundA; ra++) {
                     for (int ry = 1; ry < bounds.maxBoundB; ry++) {
                         p.x = bounds.pos.x;
diff --git a/game/core/src/main/java/net/minecraft/core/entity/Entity.java b/game/core/src/main/java/net/minecraft/core/entity/Entity.java
index b59005a58..058afc505 100644
--- a/game/core/src/main/java/net/minecraft/core/entity/Entity.java
+++ b/game/core/src/main/java/net/minecraft/core/entity/Entity.java
@@ -10,10 +10,12 @@ import net.minecraft.core.entity.animal.MobPig;
 import net.minecraft.core.entity.vehicle.EntityBoat;
 import net.minecraft.core.block.piston.BlockLogicPistonHead;
 import net.minecraft.core.util.collection.NamespaceID;
+import net.minecraft.core.util.helper.Direction;
 import net.minecraft.core.util.helper.DyeColor;
 import net.minecraft.core.world.Dimension;
 import net.minecraft.core.world.ICarriable;
 import net.minecraft.core.world.pos.TilePos;
+import net.minecraft.core.world.pos.TilePosc;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 
@@ -1312,65 +1314,49 @@ public abstract class Entity
     public void killed(Mob mob) {
     }
 
-    protected boolean checkInTile(double d, double d1, double d2) {
-        int i = MathHelper.floor(d);
-        int j = MathHelper.floor(d1);
-        int k = MathHelper.floor(d2);
-        double d3 = d - (double) i;
-        double d4 = d1 - (double) j;
-        double d5 = d2 - (double) k;
-        if (this.world.isBlockNormalCube(i, j, k)) {
-            boolean flag = !this.world.isBlockNormalCube(i - 1, j, k);
-            boolean flag1 = !this.world.isBlockNormalCube(i + 1, j, k);
-            boolean flag2 = !this.world.isBlockNormalCube(i, j - 1, k);
-            boolean flag3 = !this.world.isBlockNormalCube(i, j + 1, k);
-            boolean flag4 = !this.world.isBlockNormalCube(i, j, k - 1);
-            boolean flag5 = !this.world.isBlockNormalCube(i, j, k + 1);
-            byte byte0 = -1;
-            double d6 = 9999D;
-            if (flag && d3 < d6) {
-                d6 = d3;
-                byte0 = 0;
+    protected boolean checkAndPushInTile(double x, double y, double z) {
+        TilePosc tilePos = new TilePos(x, y, z);
+        TilePos queryPos = new TilePos();
+        double depthX = x - (double) tilePos.x();
+        double depthY = y - (double) tilePos.y();
+        double depthZ = z - (double) tilePos.z();
+        if (this.world.isBlockNormalCube(tilePos)) {
+            Direction direction = Direction.NONE;
+            double minDepth = Double.MAX_VALUE;
+            if (depthX < minDepth && !this.world.isBlockNormalCube(tilePos.west(queryPos))) {
+                minDepth = depthX;
+                direction = Direction.WEST;
             }
-            if (flag1 && 1.0D - d3 < d6) {
-                d6 = 1.0D - d3;
-                byte0 = 1;
+            if (1.0D - depthX < minDepth && !this.world.isBlockNormalCube(tilePos.east(queryPos))) {
+                minDepth = 1.0D - depthX;
+                direction = Direction.EAST;
             }
-            if (flag2 && d4 < d6) {
-                d6 = d4;
-                byte0 = 2;
+            if (depthY < minDepth && !this.world.isBlockNormalCube(tilePos.down(queryPos))) {
+                minDepth = depthY;
+                direction = Direction.DOWN;
             }
-            if (flag3 && 1.0D - d4 < d6) {
-                d6 = 1.0D - d4;
-                byte0 = 3;
+            if (1.0D - depthY < minDepth && !this.world.isBlockNormalCube(tilePos.up(queryPos))) {
+                minDepth = 1.0D - depthY;
+                direction = Direction.UP;
             }
-            if (flag4 && d5 < d6) {
-                d6 = d5;
-                byte0 = 4;
+            if (depthZ < minDepth && !this.world.isBlockNormalCube(tilePos.north(queryPos))) {
+                minDepth = depthZ;
+                direction = Direction.NORTH;
             }
-            if (flag5 && 1.0D - d5 < d6) {
-                double d7 = 1.0D - d5;
-                byte0 = 5;
+            if (1.0D - depthZ < minDepth && !this.world.isBlockNormalCube(tilePos.south(queryPos))) {
+//                minDepth = 1.0D - depthZ;
+                direction = Direction.SOUTH;
             }
-            float f = this.random.nextFloat() * 0.2F + 0.1F;
-            if (byte0 == 0) {
-                this.xd = -f;
-            }
-            if (byte0 == 1) {
-                this.xd = f;
-            }
-            if (byte0 == 2) {
-                this.yd = -f;
-            }
-            if (byte0 == 3) {
-                this.yd = f;
-            }
-            if (byte0 == 4) {
-                this.zd = -f;
-            }
-            if (byte0 == 5) {
-                this.zd = f;
+            float pushOut = this.random.nextFloat() * 0.2F + 0.1F;
+            switch (direction) {
+                case WEST -> this.xd = -pushOut;
+                case EAST -> this.xd = pushOut;
+                case DOWN -> this.yd = -pushOut;
+                case UP -> this.yd = pushOut;
+                case NORTH -> this.zd = -pushOut;
+                case SOUTH -> this.zd = pushOut;
             }
+            return true;
         }
         return false;
     }
diff --git a/game/core/src/main/java/net/minecraft/core/entity/EntityItem.java b/game/core/src/main/java/net/minecraft/core/entity/EntityItem.java
index c28403b42..6837107e2 100644
--- a/game/core/src/main/java/net/minecraft/core/entity/EntityItem.java
+++ b/game/core/src/main/java/net/minecraft/core/entity/EntityItem.java
@@ -102,7 +102,7 @@ public class EntityItem extends Entity
             this.world.playSoundAtEntity(null, this, "random.fizz", 0.4F, 2.0F + this.random.nextFloat() * 0.4F);
         }
 
-        checkInTile(this.x, (this.bb.minY + this.bb.maxY) / 2D, this.z);
+        checkAndPushInTile(this.x, (this.bb.minY + this.bb.maxY) / 2D, this.z);
         move(this.xd, this.yd, this.zd);
         
         if(!this.world.isClientSide) {
diff --git a/game/core/src/main/java/net/minecraft/core/item/ItemBed.java b/game/core/src/main/java/net/minecraft/core/item/ItemBed.java
index 341ec886f..4cf988695 100644
--- a/game/core/src/main/java/net/minecraft/core/item/ItemBed.java
+++ b/game/core/src/main/java/net/minecraft/core/item/ItemBed.java
@@ -24,7 +24,7 @@ public class ItemBed extends Item {
             pos = pos.add(side.getDirection(), new TilePos());
         }
         Direction dir = player == null ? Direction.NORTH : player.getHorizontalPlacementDirection(null).getOpposite();
-        TilePos pos2 = pos.add(dir, new TilePos());
+        TilePos pos2 = pos.sub(dir, new TilePos());
         if (world.isAirBlock(pos) && world.isAirBlock(pos2) && world.canPlaceOnSurfaceOfBlock(pos.down(new TilePos())) && world.canPlaceOnSurfaceOfBlock(pos2.down(new TilePos()))) {
             if (world.canBlockIdBePlacedAt(Blocks.BED.id(), pos, false, side) && selfStack.consumeItem(player)) {
                 world.playBlockSoundEffect(player, pos.x() + 0.5F, pos.y() + 0.5F, pos.z() + 0.5F, Blocks.BED, EnumBlockSoundEffectType.PLACE);
diff --git a/game/core/src/main/java/net/minecraft/core/util/collection/NamespaceID.java b/game/core/src/main/java/net/minecraft/core/util/collection/NamespaceID.java
index 31532ba9d..01e0b0fa7 100644
--- a/game/core/src/main/java/net/minecraft/core/util/collection/NamespaceID.java
+++ b/game/core/src/main/java/net/minecraft/core/util/collection/NamespaceID.java
@@ -64,11 +64,11 @@ public final class NamespaceID implements Comparable<NamespaceID>, CharSequence,
     private @Nullable String namespace;
     private @Nullable String value;
 
-    NamespaceID(final @NotNull String formattedKey) throws HardIllegalArgumentException {
+    public NamespaceID(final @NotNull String formattedKey) throws HardIllegalArgumentException {
         set(formattedKey);
     }
 
-    NamespaceID(final @NotNull String namespace, final @NotNull String value) {
+    public NamespaceID(final @NotNull String namespace, final @NotNull String value) {
         set(namespace, value);
     }
 
diff --git a/game/core/src/main/java/net/minecraft/core/util/debug/Debug.java b/game/core/src/main/java/net/minecraft/core/util/debug/Debug.java
index eccfb43ec..5abdf0960 100644
--- a/game/core/src/main/java/net/minecraft/core/util/debug/Debug.java
+++ b/game/core/src/main/java/net/minecraft/core/util/debug/Debug.java
@@ -1,10 +1,10 @@
 package net.minecraft.core.util.debug;
 
 import com.mojang.logging.LogUtils;
+import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
+import it.unimi.dsi.fastutil.objects.ObjectArrayList;
 import org.slf4j.Logger;
 
-import java.util.ArrayList;
-import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
 
@@ -90,8 +90,8 @@ public class Debug {
 		
 		public final String name;
 		public Profiler parent;
-		public Map<String, Profiler> profilers = new HashMap<>();
-		public List<Profiler> allProfilers = new ArrayList<>();
+		public Map<String, Profiler> profilers = new Object2ObjectOpenHashMap<>();
+		public List<Profiler> allProfilers = new ObjectArrayList<>();
 		public long startTime = -1;
 		public long time = 0;
 		
@@ -104,15 +104,15 @@ public class Debug {
 			Profiler profiler = this.profilers.get(name);
 			if(profiler == null) {
 				profiler = new Profiler(name, this);
-				profilers.put(name, profiler);
-				allProfilers.add(profiler);
+                this.profilers.put(name, profiler);
+                this.allProfilers.add(profiler);
 			}
 			return profiler;
 		}
 		
 		@Override
 		public int hashCode() {
-			return name.hashCode();
+			return this.name.hashCode();
 		}
 		
 	}
diff --git a/game/core/src/main/java/net/minecraft/core/util/helper/MathHelper.java b/game/core/src/main/java/net/minecraft/core/util/helper/MathHelper.java
index 473408139..8813b5145 100644
--- a/game/core/src/main/java/net/minecraft/core/util/helper/MathHelper.java
+++ b/game/core/src/main/java/net/minecraft/core/util/helper/MathHelper.java
@@ -14,12 +14,12 @@ public class MathHelper {
     public MathHelper() {
     }
 
-    public static float sin(float f) {
-        return SIN_TABLE[(int) (f * 10430.38F) & 0xffff];
+    public static float sin(float deg) {
+        return SIN_TABLE[(int) (deg * 10430.38F) & 0xffff];
     }
 
-    public static float cos(float f) {
-        return SIN_TABLE[(int) (f * 10430.38F + 16384F) & 0xffff];
+    public static float cos(float deg) {
+        return SIN_TABLE[(int) (deg * 10430.38F + 16384F) & 0xffff];
     }
 
     public static float sqrt_float(float f) {
@@ -73,18 +73,15 @@ public class MathHelper {
     }
 
     public static double clamp(double value, double min, double max) {
-        if (value > max) return max;
-        return Math.max(value, min);
+        return org.joml.Math.clamp(min, max, value);
     }
 
     public static float clamp(float value, float min, float max) {
-        if (value > max) return max;
-        return Math.max(value, min);
+        return org.joml.Math.clamp(min, max, value);
     }
 
     public static int clamp(int value, int min, int max) {
-        if (value > max) return max;
-        return Math.max(value, min);
+        return org.joml.Math.clamp(min, max, value);
     }
 
     public static byte clamp(byte value, byte min, byte max) {
@@ -93,11 +90,11 @@ public class MathHelper {
     }
 
     public static float lerp(float a, float b, float amount) {
-        return a + ((b - a) * amount);
+        return org.joml.Math.lerp(a, b, amount);
     }
 
     public static double lerp(double a, double b, double amount) {
-        return a + ((b - a) * amount);
+        return org.joml.Math.lerp(a, b, amount);
     }
 
     public static float unlerp(float a, float b, float value) {
diff --git a/game/core/src/main/java/net/minecraft/core/world/BlocksContainer.java b/game/core/src/main/java/net/minecraft/core/world/BlocksContainer.java
index 295b1be1a..03670e0ce 100644
--- a/game/core/src/main/java/net/minecraft/core/world/BlocksContainer.java
+++ b/game/core/src/main/java/net/minecraft/core/world/BlocksContainer.java
@@ -22,6 +22,7 @@ public class BlocksContainer implements MutableWorldSource {
     public final @NotNull World world;
     private final @NotNull Map<@NotNull TilePos, @NotNull BlockEntry> blockEntryMap = new HashMap<>();
     private @Nullable Entity lightRefEntity = null;
+    public float partialTick = 1f;
 
     public BlocksContainer(final @NotNull World world) {
         this.world = world;
@@ -119,7 +120,7 @@ public class BlocksContainer implements MutableWorldSource {
             return entry.id;
         }
 
-        return this.world.getBlockId(tilePos);
+        return 0;
     }
 
     @Override
@@ -134,13 +135,13 @@ public class BlocksContainer implements MutableWorldSource {
             return entry.tileEntity;
         }
 
-        return this.world.getTileEntity(tilePos);
+        return null;
     }
 
     @Override
     public float getBrightness(final @NotNull TilePosc tilePos, final int lightEmission) {
         if (this.lightRefEntity != null) {
-            return this.lightRefEntity.getBrightness(1.0f);
+            return this.lightRefEntity.getBrightness(this.partialTick);
         }
 
         return this.world.getBrightness(tilePos, lightEmission);
@@ -149,7 +150,7 @@ public class BlocksContainer implements MutableWorldSource {
     @Override
     public int getLightmapCoord(final @NotNull TilePosc tilePos, final int lightEmission) {
         if (this.lightRefEntity != null) {
-            return this.lightRefEntity.getLightmap(1.0f);
+            return this.lightRefEntity.getLightmap(this.partialTick);
         }
 
         return this.world.getLightmapCoord(tilePos, lightEmission);
@@ -172,7 +173,7 @@ public class BlocksContainer implements MutableWorldSource {
             return entry.data;
         }
 
-        return this.world.getBlockData(tilePos);
+        return 0;
     }
 
     @Override
diff --git a/game/core/src/main/java/net/minecraft/core/world/World.java b/game/core/src/main/java/net/minecraft/core/world/World.java
index b1373963b..20b7e44e6 100644
--- a/game/core/src/main/java/net/minecraft/core/world/World.java
+++ b/game/core/src/main/java/net/minecraft/core/world/World.java
@@ -866,7 +866,7 @@ public class World implements MutableWorldSource {
         if (tilePos.y() < 0) {
             return 0;
         }
-        return this.getChunk(tilePos).getRawBrightness(new ChunkTilePos(new TilePos(tilePos.x(), Math.min(tilePos.y(), this.getHeightBlocks() - 1), tilePos.z())), this.skyDarken);
+        return this.getChunk(tilePos).getRawBrightness(new ChunkTilePos(tilePos.x(), Math.min(tilePos.y(), this.getHeightBlocks() - 1), tilePos.z()), this.skyDarken);
     }
 
     public boolean canLoadedBlockSeeSky(final @NotNull TilePosc tilePos) {
@@ -1416,7 +1416,7 @@ public class World implements MutableWorldSource {
         if (f2 > 1.0F) {
             f2 = 1.0F;
         }
-        return f2 * f2 * 0.5F;
+        return f2 * f2;
     }
 
     @Deprecated
diff --git a/game/core/src/main/java/net/minecraft/core/world/biome/Biome.java b/game/core/src/main/java/net/minecraft/core/world/biome/Biome.java
index ad5ca9ffa..572aa93be 100644
--- a/game/core/src/main/java/net/minecraft/core/world/biome/Biome.java
+++ b/game/core/src/main/java/net/minecraft/core/world/biome/Biome.java
@@ -33,6 +33,7 @@ public class Biome
     protected @NotNull List<@NotNull SpawnListEntry> spawnableWaterCreatureList = new ArrayList<>();
     protected @NotNull List<@NotNull SpawnListEntry> spawnableAmbientCreatureList = new ArrayList<>();
     private boolean hasSurfaceSnow = false;
+    private boolean hasSurfaceIce = false;
     
     public Biome(String key)
     {
@@ -102,12 +103,21 @@ public class Biome
     	return hasSurfaceSnow;
     }
 
+    public boolean hasSurfaceIce() {
+        return this.hasSurfaceIce;
+    }
+
     public Biome setSurfaceSnow()
     {
     	hasSurfaceSnow = true;
     	return this;
     }
 
+    public Biome setSurfaceIce() {
+        this.hasSurfaceIce = true;
+        return this;
+    }
+
     public Biome setBlockedWeathers(Weather... blocked)
     {
     	this.blockedWeathers = blocked;
diff --git a/game/core/src/main/java/net/minecraft/core/world/biome/Biomes.java b/game/core/src/main/java/net/minecraft/core/world/biome/Biomes.java
index 9e2c8d5b2..8fd5abe0a 100644
--- a/game/core/src/main/java/net/minecraft/core/world/biome/Biomes.java
+++ b/game/core/src/main/java/net/minecraft/core/world/biome/Biomes.java
@@ -18,12 +18,12 @@ public class Biomes
     public static final Biome OVERWORLD_GRASSLANDS = register("minecraft:overworld.grasslands", new Biome("overworld.grasslands").setColor(0xf0f048).setBlockedWeathers(Weathers.OVERWORLD_SNOW));
     public static final Biome OVERWORLD_OUTBACK = register("minecraft:overworld.outback", new BiomeOutback("overworld.outback").setColor(0xd95e20).setBlockedWeathers(Weathers.OVERWORLD_SNOW).setTopBlock(Blocks.DIRT_SCORCHED.id()).setFillerBlock(Blocks.DIRT_SCORCHED.id()));
     public static final Biome OVERWORLD_SHRUBLAND = register("minecraft:overworld.shrubland", new BiomeShrubland("overworld.shrubland").setColor(0xbaba38));
-    public static final Biome OVERWORLD_TAIGA = register("minecraft:overworld.taiga", new BiomeTaiga("overworld.taiga").setColor(0x8abcff).setSurfaceSnow());
+    public static final Biome OVERWORLD_TAIGA = register("minecraft:overworld.taiga", new BiomeTaiga("overworld.taiga").setColor(0x8abcff).setSurfaceSnow().setSurfaceIce());
     public static final Biome OVERWORLD_BOREAL_FOREST = register("minecraft:overworld.boreal_forest", new BiomeBorealForest("overworld.boreal_forest").setColor(0x148564));
     public static final Biome OVERWORLD_DESERT = register("minecraft:overworld.desert", new BiomeDesert("overworld.desert").setColor(0xEDE26F).setBlockedWeathers(Weathers.OVERWORLD_RAIN, Weathers.OVERWORLD_SNOW, Weathers.OVERWORLD_STORM).setTopBlock(Blocks.SAND.id()).setFillerBlock(Blocks.SAND.id()));
     public static final Biome OVERWORLD_PLAINS = register("minecraft:overworld.plains", new BiomePlains("overworld.plains").setColor(0xA3C649));
     public static final Biome OVERWORLD_GLACIER = register("minecraft:overworld.glacier", new Biome("overworld.glacier").setColor(0xcbf6ff).setSurfaceSnow().setTopBlock(Blocks.BLOCK_SNOW.id()).setFillerBlock(Blocks.BLOCK_SNOW.id()));
-    public static final Biome OVERWORLD_TUNDRA = register("minecraft:overworld.tundra", new Biome("overworld.tundra").setColor(0x57e0ff).setSurfaceSnow());
+    public static final Biome OVERWORLD_TUNDRA = register("minecraft:overworld.tundra", new Biome("overworld.tundra").setColor(0x57e0ff).setSurfaceSnow().setSurfaceIce());
     public static final Biome OVERWORLD_MEADOW = register("minecraft:overworld.meadow", new BiomeBorealForest("overworld.meadow").setColor(0x8c8c22));
     public static final Biome DRIFT_DRIFT = register("minecraft:drift.drift", new BiomeDrift("drift.drift").setColor(0x8080FF).setBlockedWeathers(Weathers.OVERWORLD_RAIN, Weathers.OVERWORLD_SNOW, Weathers.OVERWORLD_STORM, Weathers.OVERWORLD_FOG));
     public static final Biome OVERWORLD_BIRCH_FOREST = register("minecraft:overworld.birch_forest", new BiomeBirchForest("overworld.birch_forest").setColor(0x4bcb5e));
@@ -46,10 +46,10 @@ public class Biomes
     public static final Biome OVERWORLD_LEGACY_FOREST = register("minecraft:overworld.legacy.forest", new BiomeForestLegacy("overworld.legacy.forest").setColor(0x056621));
     public static final Biome OVERWORLD_LEGACY_SAVANNA = register("minecraft:overworld.legacy.savanna", new BiomeDesertLegacy("overworld.legacy.savanna").setColor(0xd9e023).setBlockedWeathers(Weathers.OVERWORLD_SNOW));
     public static final Biome OVERWORLD_LEGACY_SHRUBLAND = register("minecraft:overworld.legacy.shrubland", new Biome("overworld.legacy.shrubland").setColor(0xa1ad20));
-    public static final Biome OVERWORLD_LEGACY_TAIGA = register("minecraft:overworld.legacy.taiga", new BiomeTaigaLegacy("overworld.legacy.taiga").setColor(0x2eb153).setSurfaceSnow());
+    public static final Biome OVERWORLD_LEGACY_TAIGA = register("minecraft:overworld.legacy.taiga", new BiomeTaigaLegacy("overworld.legacy.taiga").setColor(0x2eb153).setSurfaceSnow().setSurfaceIce());
     public static final Biome OVERWORLD_LEGACY_DESERT = register("minecraft:overworld.legacy.desert", new BiomeDesertLegacy("overworld.legacy.desert").setColor(0xfa9418).setBlockedWeathers(Weathers.OVERWORLD_RAIN, Weathers.OVERWORLD_SNOW, Weathers.OVERWORLD_STORM).setTopBlock(Blocks.SAND.id()).setFillerBlock(Blocks.SAND.id()));
     public static final Biome OVERWORLD_LEGACY_PLAINS = register("minecraft:overworld.legacy.plains", new BiomeDesertLegacy("overworld.legacy.plains").setColor(0xffd910));
-    public static final Biome OVERWORLD_LEGACY_TUNDRA = register("minecraft:overworld.legacy.tundra", new Biome("overworld.legacy.tundra").setColor(0x57ebf9).setSurfaceSnow());
+    public static final Biome OVERWORLD_LEGACY_TUNDRA = register("minecraft:overworld.legacy.tundra", new Biome("overworld.legacy.tundra").setColor(0x57ebf9).setSurfaceSnow().setSurfaceIce());
 
     public static Biome register(String key, Biome biome)
     {
diff --git a/game/core/src/main/java/net/minecraft/core/world/chunk/provider/ChunkProviderThreaded.java b/game/core/src/main/java/net/minecraft/core/world/chunk/provider/ChunkProviderThreaded.java
index 7696e8930..00f8aaf2f 100644
--- a/game/core/src/main/java/net/minecraft/core/world/chunk/provider/ChunkProviderThreaded.java
+++ b/game/core/src/main/java/net/minecraft/core/world/chunk/provider/ChunkProviderThreaded.java
@@ -195,12 +195,14 @@ public class ChunkProviderThreaded implements IChunkProvider {
         }
 
         synchronized (this.loadedChunks) {
+            int count = 0;
             var itr = this.loadedChunks.entrySet().iterator();
             while (itr.hasNext()) {
                 var entry = itr.next();
                 ChunkPos pos = entry.getKey();
                 Chunk chunk = entry.getValue();
                 if (!isChunkValid(pos)) {
+                    count++;
                     saveChunk(chunk);
                     chunk.onUnload();
                     itr.remove();
@@ -208,6 +210,7 @@ public class ChunkProviderThreaded implements IChunkProvider {
                         this.lastQueriedChunkPos = MIN_POS;
                         this.lastQueriedChunk = this.empty;
                     }
+                    if (count > 4) break;
                 }
             }
         }
diff --git a/game/core/src/main/java/net/minecraft/core/world/data/SynchedEntityData.java b/game/core/src/main/java/net/minecraft/core/world/data/SynchedEntityData.java
index 07c3243ab..f765aa206 100644
--- a/game/core/src/main/java/net/minecraft/core/world/data/SynchedEntityData.java
+++ b/game/core/src/main/java/net/minecraft/core/world/data/SynchedEntityData.java
@@ -3,8 +3,10 @@ package net.minecraft.core.world.data;
 import com.mojang.nbt.tags.CompoundTag;
 import it.unimi.dsi.fastutil.ints.Int2ObjectArrayMap;
 import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
+import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap;
 import it.unimi.dsi.fastutil.objects.Object2IntArrayMap;
 import it.unimi.dsi.fastutil.objects.Object2IntMap;
+import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap;
 import net.minecraft.core.item.ItemStack;
 import net.minecraft.core.net.packet.Packet;
 import net.minecraft.core.world.chunk.ChunkCoordinates;
@@ -39,8 +41,8 @@ public class SynchedEntityData
     public static final int MAX_STRING_SIZE = 1024;
 
     public static final int END_MARKER = 0xFF;
-    private static final Object2IntMap<Class<?>> DATA_TYPES = new Object2IntArrayMap<>();
-    private final Int2ObjectMap<@NotNull DataItem<?>> itemsById = new Int2ObjectArrayMap<>();
+    private static final Object2IntMap<Class<?>> DATA_TYPES = new Object2IntOpenHashMap<>();
+    private final Int2ObjectMap<@NotNull DataItem<?>> itemsById = new Int2ObjectOpenHashMap<>();
     private boolean isDirty = true;
 
     /**
diff --git a/game/core/src/main/java/net/minecraft/core/world/generate/IceFloeLargeFeature.java b/game/core/src/main/java/net/minecraft/core/world/generate/IceFloeLargeFeature.java
new file mode 100644
index 000000000..b1c7abc79
--- /dev/null
+++ b/game/core/src/main/java/net/minecraft/core/world/generate/IceFloeLargeFeature.java
@@ -0,0 +1,79 @@
+package net.minecraft.core.world.generate;
+
+import net.minecraft.core.block.Block;
+import net.minecraft.core.block.Blocks;
+import net.minecraft.core.util.helper.MathHelper;
+import net.minecraft.core.world.World;
+import net.minecraft.core.world.biome.Biome;
+import net.minecraft.core.world.biome.Biomes;
+import net.minecraft.core.world.chunk.Chunk;
+import net.minecraft.core.world.generate.chunk.ChunkGeneratorResult;
+import net.minecraft.core.world.noise.PerlinNoise;
+import net.minecraft.core.world.noise.WorleyNoise;
+import net.minecraft.core.world.pos.TilePos;
+import net.minecraft.core.world.type.WorldType;
+import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
+import org.joml.Vector2f;
+
+import java.util.Random;
+
+public class IceFloeLargeFeature
+    extends LargeFeature {
+    private @Nullable PerlinNoise perlinNoise = null;
+    private @Nullable PerlinNoise heightPerlinNoise = null;
+    private @Nullable World lastWorld = null;
+
+    @Override
+    protected void doGeneration(@NotNull final World world, @NotNull final Random random, final int chunkX, final int chunkZ, final int baseChunkX, final int baseChunkZ, @NotNull final ChunkGeneratorResult result) {
+        if (this.perlinNoise == null || this.heightPerlinNoise == null || this.lastWorld != world) {
+            this.perlinNoise = new PerlinNoise(world.getRandomSeed(), 4);
+            this.heightPerlinNoise = new PerlinNoise(world.getRandomSeed(), 8);
+            this.lastWorld = world;
+        }
+
+        final @NotNull WorldType worldType = world.getWorldType();
+        final int oceanY = worldType.getMinY() + worldType.getOceanY();
+
+        final @NotNull TilePos tilePos = new TilePos();
+        final @NotNull Vector2f vec = new Vector2f();
+        final @NotNull WorleyNoise.Result worley = new WorleyNoise.Result();
+
+        for (int x = 0; x < Chunk.CHUNK_SIZE_X; x++) {
+            for (int z = 0; z < Chunk.CHUNK_SIZE_Z; z++) {
+                tilePos.set(Chunk.CHUNK_SIZE_X * baseChunkX + x, oceanY, Chunk.CHUNK_SIZE_Z * baseChunkZ + z);
+                final @NotNull Biome biome = world.getBlockBiome(tilePos);
+                if (biome == Biomes.OVERWORLD_GLACIER) {
+                    vec.x = baseChunkX + ((float) x / (float) Chunk.CHUNK_SIZE_X);
+                    vec.y = baseChunkZ + ((float) z / (float) Chunk.CHUNK_SIZE_Z);
+                    WorleyNoise.getWorleyDistance2d(vec, worley);
+                    final float scale = 10.0f;
+                    final float lineWidth = (float) (this.perlinNoise.get((baseChunkX * Chunk.CHUNK_SIZE_X + x) / scale, (baseChunkZ * Chunk.CHUNK_SIZE_Z + z) / scale) / 2.0 + 0.5);
+                    if (MathHelper.unsignedMod(worley.index, 15) != 0) {
+                        if (worley.distance > 0.9f + lineWidth * 0.05f) {
+                            continue;
+                        }
+                        for (int y = oceanY - 3; y < oceanY; y++) {
+                            this.trySetBlock(result, x, y, z, Blocks.PERMAICE.id());
+                        }
+                        for (int y = oceanY; y < oceanY + 1; y++) {
+                            this.trySetBlock(result, x, y, z, Blocks.BLOCK_SNOW.id());
+                        }
+                    }
+                }
+            }
+        }
+    }
+
+    private void trySetBlock(final @NotNull ChunkGeneratorResult result, final int x, final int y, final int z, final int id) {
+        final int current = result.getBlock(x, y, z);
+        if (current == Blocks.FLUID_WATER_STILL.id() || current == 0) {
+            result.setBlock(x, y, z, id);
+        }
+    }
+
+    @Override
+    public int getRadiusChunk() {
+        return 0;
+    }
+}
diff --git a/game/core/src/main/java/net/minecraft/core/world/generate/LargeFeature.java b/game/core/src/main/java/net/minecraft/core/world/generate/LargeFeature.java
index 05722cd35..8577dbddf 100644
--- a/game/core/src/main/java/net/minecraft/core/world/generate/LargeFeature.java
+++ b/game/core/src/main/java/net/minecraft/core/world/generate/LargeFeature.java
@@ -6,11 +6,11 @@ import org.jetbrains.annotations.NotNull;
 
 import java.util.Random;
 
-public class LargeFeature {
+public abstract class LargeFeature {
     public LargeFeature() {
     }
 
-    public void generate(@NotNull World world, int baseChunkX, int baseChunkZ, @NotNull ChunkGeneratorResult result) {
+    public final void generate(@NotNull World world, int baseChunkX, int baseChunkZ, @NotNull ChunkGeneratorResult result) {
         int radius = getRadiusChunk();
         Random rand = new Random(world.getRandomSeed());
         long randX = (rand.nextLong() / 2L) * 2L + 1L;
@@ -24,8 +24,7 @@ public class LargeFeature {
         }
     }
 
-    protected void doGeneration(@NotNull World world, @NotNull Random random, int chunkX, int chunkZ, int baseChunkX, int baseChunkZ, @NotNull ChunkGeneratorResult result) {
-    }
+    protected abstract void doGeneration(@NotNull World world, @NotNull Random random, int chunkX, int chunkZ, int baseChunkX, int baseChunkZ, @NotNull ChunkGeneratorResult result);
 
     public int getRadiusChunk() {
         return 8;
diff --git a/game/core/src/main/java/net/minecraft/core/world/generate/RetroCavesLargeFeature.java b/game/core/src/main/java/net/minecraft/core/world/generate/RetroCavesLargeFeature.java
index 1344d5d89..28b8e7d3b 100644
--- a/game/core/src/main/java/net/minecraft/core/world/generate/RetroCavesLargeFeature.java
+++ b/game/core/src/main/java/net/minecraft/core/world/generate/RetroCavesLargeFeature.java
@@ -25,21 +25,6 @@ public class RetroCavesLargeFeature extends LargeFeature {
         this.maxY = maxY;
     }
 
-    @Override
-    public void generate(@NotNull World world, int baseChunkX, int baseChunkZ, @NotNull ChunkGeneratorResult result) {
-        int radius = getRadiusChunk();
-        Random rand = new Random(world.getRandomSeed());
-        long randX = (rand.nextLong() / 2L) * 2L + 1L;
-        long randZ = (rand.nextLong() / 2L) * 2L + 1L;
-        for (int chunkX = baseChunkX - radius; chunkX <= baseChunkX + radius; chunkX++) {
-            for (int chunkZ = baseChunkZ - radius; chunkZ <= baseChunkZ + radius; chunkZ++) {
-                rand.setSeed((long) chunkX * randX + (long) chunkZ * randZ ^ world.getRandomSeed());
-                doGeneration(world, rand, chunkX, chunkZ, baseChunkX, baseChunkZ, result);
-            }
-
-        }
-    }
-
     protected void generateHubRoom(@NotNull World world, @NotNull Random random, int baseChunkX, int baseChunkZ, @NotNull ChunkGeneratorResult result, double blockX, double blockY, double blockZ) {
         generateCave(world, random, baseChunkX, baseChunkZ, result, blockX, blockY, blockZ, 1.0F + random.nextFloat() * 6F, 0.0F, 0.0F, -1, -1, 0.5D);
     }
diff --git a/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/ChunkDecoratorOverworld.java b/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/ChunkDecoratorOverworld.java
index 58afeae82..16fbdd278 100644
--- a/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/ChunkDecoratorOverworld.java
+++ b/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/ChunkDecoratorOverworld.java
@@ -101,7 +101,7 @@ public class ChunkDecoratorOverworld
             lakeChance = 0;
         if (lakeChance != 0 && rand.nextInt(lakeChance) == 0) {
             int fluid = Blocks.FLUID_WATER_STILL.id();
-            if (biome.hasSurfaceSnow()) {
+            if (biome.hasSurfaceIce()) {
                 fluid = Blocks.ICE.id();
             }
             int i1 = x + rand.nextInt(16) + 8;
@@ -608,7 +608,7 @@ public class ChunkDecoratorOverworld
                         this.world.setBlockWithNotify(dx, dy, dz, Blocks.LAYER_SNOW.id());
                     }
                 }
-                if ((localBiome.hasSurfaceSnow() || this.world.worldType == WorldTypes.OVERWORLD_WINTER) && (this.world.getBlockId(dx, oceanY - 1, dz) == Blocks.FLUID_WATER_STILL.id() || this.world.getBlockId(dx, oceanY - 1, dz) == Blocks.FLUID_WATER_FLOWING.id())) {
+                if ((localBiome.hasSurfaceIce() || this.world.worldType == WorldTypes.OVERWORLD_WINTER) && (this.world.getBlockId(dx, oceanY - 1, dz) == Blocks.FLUID_WATER_STILL.id() || this.world.getBlockId(dx, oceanY - 1, dz) == Blocks.FLUID_WATER_FLOWING.id())) {
                     this.world.setBlockWithNotify(dx, oceanY - 1, dz, Blocks.ICE.id());
                 }
 
diff --git a/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/ChunkGeneratorOverworld.java b/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/ChunkGeneratorOverworld.java
index 8d2e7df5c..1394b695d 100644
--- a/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/ChunkGeneratorOverworld.java
+++ b/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/ChunkGeneratorOverworld.java
@@ -2,6 +2,7 @@ package net.minecraft.core.world.generate.chunk.perlin.overworld;
 
 import net.minecraft.core.world.World;
 import net.minecraft.core.world.generate.CavesLargeFeature;
+import net.minecraft.core.world.generate.IceFloeLargeFeature;
 import net.minecraft.core.world.generate.LargeFeature;
 import net.minecraft.core.world.generate.chunk.perlin.ChunkGeneratorPerlin;
 import org.jetbrains.annotations.NotNull;
@@ -9,6 +10,6 @@ import org.jetbrains.annotations.NotNull;
 public class ChunkGeneratorOverworld
     extends ChunkGeneratorPerlin {
     public ChunkGeneratorOverworld(@NotNull World world) {
-        super(world, new ChunkDecoratorOverworld(world), new TerrainGeneratorOverworld(world), new SurfaceGeneratorOverworld(world), new LargeFeature[]{new CavesLargeFeature()});
+        super(world, new ChunkDecoratorOverworld(world), new TerrainGeneratorOverworld(world), new SurfaceGeneratorOverworld(world), new LargeFeature[]{new CavesLargeFeature(), new IceFloeLargeFeature() });
     }
 }
diff --git a/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/TerrainGeneratorOverworld.java b/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/TerrainGeneratorOverworld.java
index 2c651ab62..62f3b3300 100644
--- a/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/TerrainGeneratorOverworld.java
+++ b/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/TerrainGeneratorOverworld.java
@@ -2,9 +2,11 @@ package net.minecraft.core.world.generate.chunk.perlin.overworld;
 
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.world.World;
+import net.minecraft.core.world.biome.Biomes;
 import net.minecraft.core.world.chunk.Chunk;
 import net.minecraft.core.world.generate.chunk.perlin.DensityGenerator;
 import net.minecraft.core.world.generate.chunk.perlin.TerrainGeneratorLerp;
+import net.minecraft.core.world.pos.ChunkTilePos;
 import net.minecraft.core.world.type.WorldType;
 import org.jetbrains.annotations.NotNull;
 
diff --git a/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/b173/ChunkDecoratorOverworldB173.java b/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/b173/ChunkDecoratorOverworldB173.java
index 5f0bb0b67..343f4fafb 100644
--- a/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/b173/ChunkDecoratorOverworldB173.java
+++ b/game/core/src/main/java/net/minecraft/core/world/generate/chunk/perlin/overworld/b173/ChunkDecoratorOverworldB173.java
@@ -306,7 +306,7 @@ public class ChunkDecoratorOverworldB173
                         this.world.setBlockWithNotify(xx, yy, zz, Blocks.LAYER_SNOW.id());
                     }
                 }
-                if (localBiome.hasSurfaceSnow() && (this.world.getBlockId(xx, oceanY - 1, zz) == Blocks.FLUID_WATER_STILL.id() || this.world.getBlockId(xx, oceanY - 1, zz) == Blocks.FLUID_WATER_FLOWING.id())) {
+                if (localBiome.hasSurfaceIce() && (this.world.getBlockId(xx, oceanY - 1, zz) == Blocks.FLUID_WATER_STILL.id() || this.world.getBlockId(xx, oceanY - 1, zz) == Blocks.FLUID_WATER_FLOWING.id())) {
                     this.world.setBlockWithNotify(xx, oceanY - 1, zz, Blocks.ICE.id());
                 }
             }
diff --git a/game/core/src/main/java/net/minecraft/core/world/noise/WorleyNoise.java b/game/core/src/main/java/net/minecraft/core/world/noise/WorleyNoise.java
new file mode 100644
index 000000000..073ab4987
--- /dev/null
+++ b/game/core/src/main/java/net/minecraft/core/world/noise/WorleyNoise.java
@@ -0,0 +1,173 @@
+package net.minecraft.core.world.noise;
+
+import net.minecraft.core.util.helper.MathHelper;
+import org.jetbrains.annotations.NotNull;
+import org.joml.Vector2f;
+import org.joml.Vector2fc;
+import org.joml.Vector3f;
+import org.joml.Vector3fc;
+
+// NOTE: code shamelessly stolen from https://www.shadertoy.com/view/MslGD8,
+// https://www.reddit.com/r/proceduralgeneration/comments/4u0s1i/infinite_worleycellularvoroni_noise/,
+// and https://www.shadertoy.com/view/ldl3W8
+public final class WorleyNoise {
+    public static class Result {
+        public float distance;
+        public int index;
+    }
+    private WorleyNoise() { }
+
+    private static final @NotNull Vector2fc HASH_CONST_2D_A = new Vector2f(127.1f, 311.7f);
+    private static final @NotNull Vector2fc HASH_CONST_2D_B = new Vector2f(269.5f, 183.3f);
+    private static final @NotNull Vector3fc HASH_CONST_3D_A = new Vector3f(127.1f, 311.7f, 74.7f);
+    private static final @NotNull Vector3fc HASH_CONST_3D_B = new Vector3f(269.5f ,183.3f ,246.1f);
+    private static final @NotNull Vector3fc HASH_CONST_3D_C = new Vector3f(113.5f, 271.9f, 124.6f);
+    private static final float HASH_CONST_MULT = 18.5453f;
+
+    public static void getWorleyDistance2d(final @NotNull Vector2fc xy, final @NotNull Result result) {
+        final @NotNull Vector2fc ip = xy.floor(new Vector2f()); // nearest gridpoint
+        final @NotNull Vector2fc fp = xy.sub(ip, new Vector2f()); // fractional distance from gridpoint
+
+        final @NotNull Vector2f mg = new Vector2f();
+        final @NotNull Vector2f mr = new Vector2f();
+        float md = 8.0f;
+        int index = 0;
+
+        final @NotNull Vector2f g = new Vector2f();
+        final @NotNull Vector2f o = new Vector2f();
+        final @NotNull Vector2f r = new Vector2f();
+        final @NotNull Vector2f pos = new Vector2f();
+
+        // First pass - regular voronoi
+        for (int i = -1; i <= 1; i++) {
+            for (int j = -1; j <= 1; j++) {
+                g.set(i, j);
+                hash(ip.add(g, pos), o); // o gives the offset of the gridpoint to use for lookup
+                g.add(o, r).sub(fp); // r gives distance to the point of interest in either direction
+                final float d = r.dot(r); // distance to gridpoint
+                if (d < md) { // check if this is the closest point
+                    md = d; // if it is, save the distance
+                    mr.set(r);
+                    mg.set(g);
+                    index = (int) (o.x * 10.0f) + (int) (o.y * 10.0f);
+                }
+            }
+        }
+
+        // Second pass - distance to borders
+        md = 8.0f;
+        for (int i = -2; i <= 2; i++) {
+            for (int j = -2; j <= 2; j++) {
+                g.set(mg).add(i, j);
+                ip.add(g, pos);
+                hash(ip.add(g, pos), o);
+                g.add(o, r).sub(fp); // r gives distance to the point of interest in either direction
+                pos.set(mr).sub(r);
+                if (pos.dot(pos) > 0.00001f) {
+                    g.set(mr).add(r).mul(0.5f);
+                    o.set(r).sub(mr).normalize();
+                    md = Math.min(md, g.dot(o));
+                }
+            }
+        }
+
+        result.distance = 1.0f - md;
+        result.index = index;
+    }
+
+    public static void getWorleyDistance3d(final @NotNull Vector3fc xyz, final @NotNull Result result) {
+        final @NotNull Vector3fc ip = xyz.floor(new Vector3f());
+        final @NotNull Vector3fc fp = xyz.sub(ip, new Vector3f());
+
+        final @NotNull Vector3f mg = new Vector3f();
+        final @NotNull Vector3f mr = new Vector3f();
+        float md = 8.0f;
+        int index = 0;
+
+        final @NotNull Vector3f g = new Vector3f();
+        final @NotNull Vector3f o = new Vector3f();
+        final @NotNull Vector3f r = new Vector3f();
+        final @NotNull Vector3f pos = new Vector3f();
+
+        // First pass - regular voronoi
+        for (int i = -1; i <= 1; i++) {
+            for (int j = -1; j <= 1; j++) {
+                for (int k = -1; k <= 1; k++) {
+                    g.set(i, j, k);
+                    hash(ip.add(g, pos), o); // o gives the offset of the gridpoint to use for lookup
+                    g.add(o, r).sub(fp); // r gives distance to the point of interest in either direction
+                    final float d = r.dot(r); // distance to gridpoint
+                    if (d < md) { // check if this is the closest point
+                        md = d; // if it is, save the distance
+                        mr.set(r);
+                        mg.set(g);
+                        index = (int) (o.x * 10.0f) + (int) (o.y * 10.0f) + (int) (o.z * 10.0f);
+                    }
+                }
+            }
+        }
+
+        // Second pass - distance to borders
+        md = 8.0f;
+        for (int i = -2; i <= 2; i++) {
+            for (int j = -2; j <= 2; j++) {
+                for (int k = -2; k <= 2; k++) {
+                    g.set(mg).add(i, j, k);
+                    ip.add(g, pos);
+                    hash(ip.add(g, pos), o);
+                    g.add(o, r).sub(fp); // r gives distance to the point of interest in either direction
+                    pos.set(mr).sub(r);
+                    if (pos.dot(pos) > 0.00001f) {
+                        g.set(mr).add(r).mul(0.5f);
+                        o.set(r).sub(mr).normalize();
+                        md = Math.min(md, g.dot(o));
+                    }
+                }
+            }
+        }
+
+        result.distance = 1.0f - md;
+        result.index = index;
+    }
+
+    private static void hash(final @NotNull Vector2fc p, final @NotNull Vector2f out) {
+        out.x = p.dot(HASH_CONST_2D_A);
+        out.y = p.dot(HASH_CONST_2D_B);
+
+        sin(out, out);
+        out.mul(HASH_CONST_MULT, out);
+        fract(out, out);
+    }
+
+    private static void hash(final @NotNull Vector3fc p, final @NotNull Vector3f out) {
+        out.x = p.dot(HASH_CONST_3D_A);
+        out.y = p.dot(HASH_CONST_3D_B);
+        out.z = p.dot(HASH_CONST_3D_C);
+
+        sin(out, out);
+        out.mul(HASH_CONST_MULT, out);
+        fract(out, out);
+    }
+
+    private static void sin(final @NotNull Vector2fc p, final @NotNull Vector2f out) {
+        out.x = (float) Math.sin(p.x());
+        out.y = (float) Math.sin(p.y());
+    }
+
+    private static void sin(final @NotNull Vector3fc p, final @NotNull Vector3f out) {
+        out.x = (float) Math.sin(p.x());
+        out.y = (float) Math.sin(p.y());
+        out.z = (float) Math.sin(p.z());
+    }
+
+    private static void fract(final @NotNull Vector2fc p, final @NotNull Vector2f out) {
+        out.x = p.x() - MathHelper.floor_float(p.x());
+        out.y = p.y() - MathHelper.floor_float(p.y());
+    }
+
+    private static void fract(final @NotNull Vector3fc p, final @NotNull Vector3f out) {
+        out.x = p.x() - MathHelper.floor_float(p.x());
+        out.y = p.y() - MathHelper.floor_float(p.y());
+        out.z = p.z() - MathHelper.floor_float(p.z());
+    }
+}
diff --git a/game/core/src/main/java/net/minecraft/core/world/pos/TilePos.java b/game/core/src/main/java/net/minecraft/core/world/pos/TilePos.java
index b6b2f5a2e..9822b05e3 100644
--- a/game/core/src/main/java/net/minecraft/core/world/pos/TilePos.java
+++ b/game/core/src/main/java/net/minecraft/core/world/pos/TilePos.java
@@ -249,7 +249,7 @@ public final class TilePos implements Externalizable, Cloneable, TilePosc {
                 this.y >= 0 &&
                 this.z >= World.MIN_BLOCK_Z &&
                 this.x <= World.MAX_BLOCK_X &&
-                this.y < source.getHeightBlocks() &&
+                this.y <= source.getHeightBlocks() &&
                 this.z <= World.MAX_BLOCK_Z;
     }
 
diff --git a/game/core/src/main/java/net/minecraft/core/world/type/overworld/WorldTypeOverworld.java b/game/core/src/main/java/net/minecraft/core/world/type/overworld/WorldTypeOverworld.java
index 04e0c4070..f203f4580 100644
--- a/game/core/src/main/java/net/minecraft/core/world/type/overworld/WorldTypeOverworld.java
+++ b/game/core/src/main/java/net/minecraft/core/world/type/overworld/WorldTypeOverworld.java
@@ -3,8 +3,10 @@ package net.minecraft.core.world.type.overworld;
 import net.minecraft.core.block.Blocks;
 import net.minecraft.core.util.helper.MathHelper;
 import net.minecraft.core.world.World;
+import net.minecraft.core.world.biome.Biomes;
 import net.minecraft.core.world.biome.provider.BiomeProvider;
 import net.minecraft.core.world.biome.provider.BiomeProviderOverworld;
+import net.minecraft.core.world.biome.provider.BiomeProviderSingleBiome;
 import net.minecraft.core.world.config.season.SeasonConfig;
 import net.minecraft.core.world.generate.chunk.ChunkGenerator;
 import net.minecraft.core.world.generate.chunk.perlin.overworld.ChunkGeneratorOverworld;
diff --git a/util/logging/src/main/java/com/mojang/logging/LogUtils.java b/util/logging/src/main/java/com/mojang/logging/LogUtils.java
index 44820a5ec..9e203f004 100644
--- a/util/logging/src/main/java/com/mojang/logging/LogUtils.java
+++ b/util/logging/src/main/java/com/mojang/logging/LogUtils.java
@@ -21,7 +21,7 @@ public class LogUtils
 {
     public static final String FATAL_MARKER_ID = "FATAL";
     public static final Marker FATAL_MARKER = MarkerFactory.getMarker(FATAL_MARKER_ID);
-//    private static final StackWalker STACK_WALKER = StackWalker.getInstance(StackWalker.Option.RETAIN_CLASS_REFERENCE);
+    private static final StackWalker STACK_WALKER = StackWalker.getInstance(StackWalker.Option.RETAIN_CLASS_REFERENCE);
     
     public static boolean isLoggerActive() {
         final LoggerContext loggerContext = LogManager.getContext();
@@ -72,19 +72,8 @@ public class LogUtils
         return new CategorizedLogger(LoggerFactory.getLogger(getCallerClass().getSimpleName()));
     }
 
-    private static Class<?> getCallerClass() { // Hacky way to replace the STACK_WALKER since STACK_WALKER uses java 9 language features
-        try {
-            StackTraceElement[] stElements = Thread.currentThread().getStackTrace();
-            for (int i=1; i<stElements.length; i++) {
-                StackTraceElement ste = stElements[i];
-                if (!ste.getClassName().equals(LogUtils.class.getName()) && ste.getClassName().indexOf("java.lang.Thread")!=0) {
-                    return Class.forName(ste.getClassName());
-                }
-            }
-        } catch (ClassNotFoundException notFoundException) {
-            System.err.print("Could not find calling class!");
-        }
-        return LogUtils.class;
+    private static Class<?> getCallerClass() {
+        return STACK_WALKER.getCallerClass();
     }
 
 }
