88 lines
		
	
	
	
		
			2.7 KiB
		
	
	
	
		
			Java
		
	
	
	
	
	
			
		
		
	
	
			88 lines
		
	
	
	
		
			2.7 KiB
		
	
	
	
		
			Java
		
	
	
	
	
	
| package net.minecraft.client.gui.screens;
 | |
| 
 | |
| import com.google.common.hash.Hashing;
 | |
| import com.mojang.blaze3d.platform.NativeImage;
 | |
| import net.fabricmc.api.EnvType;
 | |
| import net.fabricmc.api.Environment;
 | |
| import net.minecraft.Util;
 | |
| import net.minecraft.client.renderer.texture.DynamicTexture;
 | |
| import net.minecraft.client.renderer.texture.TextureManager;
 | |
| import net.minecraft.resources.ResourceLocation;
 | |
| import org.jetbrains.annotations.Nullable;
 | |
| 
 | |
| @Environment(EnvType.CLIENT)
 | |
| public class FaviconTexture implements AutoCloseable {
 | |
| 	private static final ResourceLocation MISSING_LOCATION = ResourceLocation.withDefaultNamespace("textures/misc/unknown_server.png");
 | |
| 	private static final int WIDTH = 64;
 | |
| 	private static final int HEIGHT = 64;
 | |
| 	private final TextureManager textureManager;
 | |
| 	private final ResourceLocation textureLocation;
 | |
| 	@Nullable
 | |
| 	private DynamicTexture texture;
 | |
| 	private boolean closed;
 | |
| 
 | |
| 	private FaviconTexture(TextureManager textureManager, ResourceLocation textureLocation) {
 | |
| 		this.textureManager = textureManager;
 | |
| 		this.textureLocation = textureLocation;
 | |
| 	}
 | |
| 
 | |
| 	public static FaviconTexture forWorld(TextureManager textureManager, String worldName) {
 | |
| 		return new FaviconTexture(
 | |
| 			textureManager,
 | |
| 			ResourceLocation.withDefaultNamespace(
 | |
| 				"worlds/" + Util.sanitizeName(worldName, ResourceLocation::validPathChar) + "/" + Hashing.sha1().hashUnencodedChars(worldName) + "/icon"
 | |
| 			)
 | |
| 		);
 | |
| 	}
 | |
| 
 | |
| 	public static FaviconTexture forServer(TextureManager textureManager, String worldName) {
 | |
| 		return new FaviconTexture(textureManager, ResourceLocation.withDefaultNamespace("servers/" + Hashing.sha1().hashUnencodedChars(worldName) + "/icon"));
 | |
| 	}
 | |
| 
 | |
| 	public void upload(NativeImage image) {
 | |
| 		if (image.getWidth() == 64 && image.getHeight() == 64) {
 | |
| 			try {
 | |
| 				this.checkOpen();
 | |
| 				if (this.texture == null) {
 | |
| 					this.texture = new DynamicTexture(() -> "Favicon " + this.textureLocation, image);
 | |
| 				} else {
 | |
| 					this.texture.setPixels(image);
 | |
| 					this.texture.upload();
 | |
| 				}
 | |
| 
 | |
| 				this.textureManager.register(this.textureLocation, this.texture);
 | |
| 			} catch (Throwable var3) {
 | |
| 				image.close();
 | |
| 				this.clear();
 | |
| 				throw var3;
 | |
| 			}
 | |
| 		} else {
 | |
| 			image.close();
 | |
| 			throw new IllegalArgumentException("Icon must be 64x64, but was " + image.getWidth() + "x" + image.getHeight());
 | |
| 		}
 | |
| 	}
 | |
| 
 | |
| 	public void clear() {
 | |
| 		this.checkOpen();
 | |
| 		if (this.texture != null) {
 | |
| 			this.textureManager.release(this.textureLocation);
 | |
| 			this.texture.close();
 | |
| 			this.texture = null;
 | |
| 		}
 | |
| 	}
 | |
| 
 | |
| 	public ResourceLocation textureLocation() {
 | |
| 		return this.texture != null ? this.textureLocation : MISSING_LOCATION;
 | |
| 	}
 | |
| 
 | |
| 	public void close() {
 | |
| 		this.clear();
 | |
| 		this.closed = true;
 | |
| 	}
 | |
| 
 | |
| 	private void checkOpen() {
 | |
| 		if (this.closed) {
 | |
| 			throw new IllegalStateException("Icon already closed");
 | |
| 		}
 | |
| 	}
 | |
| }
 |