// 
// Decompiled by Procyon v0.6.0
// 

package com.hypixel.hytale.builtin.asseteditor;

import java.util.concurrent.ConcurrentHashMap;
import com.hypixel.hytale.server.core.asset.type.environment.config.Environment;
import com.hypixel.hytale.event.EventRegistry;
import com.hypixel.hytale.protocol.Vector2f;
import com.hypixel.hytale.server.core.asset.type.item.config.AssetIconProperties;
import com.hypixel.hytale.assetstore.map.BlockTypeAssetMap;
import com.hypixel.hytale.protocol.Vector3f;
import com.hypixel.hytale.assetstore.AssetStore;
import com.hypixel.hytale.assetstore.map.IndexedLookupTableAssetMap;
import java.time.Instant;
import com.hypixel.hytale.server.core.io.PacketHandler;
import com.hypixel.hytale.protocol.packets.world.UpdateEditorTimeOverride;
import com.hypixel.hytale.protocol.InstantData;
import com.hypixel.hytale.protocol.packets.asseteditor.AssetEditorUpdateSecondsPerGameDay;
import com.hypixel.hytale.server.core.modules.time.WorldTimeResource;
import com.hypixel.hytale.server.core.asset.type.weather.config.Weather;
import java.util.logging.Level;
import com.hypixel.hytale.logger.HytaleLogger;
import com.hypixel.hytale.server.core.modules.item.ItemModule;
import java.util.Set;
import com.hypixel.hytale.server.core.modules.i18n.I18nModule;
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
import com.hypixel.hytale.server.core.modules.entity.component.ModelComponent;
import com.hypixel.hytale.server.core.asset.type.item.config.ItemArmor;
import com.hypixel.hytale.server.core.inventory.ItemStack;
import com.hypixel.hytale.server.core.entity.entities.Player;
import com.hypixel.hytale.server.core.universe.world.World;
import com.hypixel.hytale.component.Store;
import com.hypixel.hytale.component.ComponentAccessor;
import com.hypixel.hytale.server.core.universe.world.PlayerUtil;
import com.hypixel.hytale.component.ComponentType;
import com.hypixel.hytale.server.core.modules.entity.player.PlayerSkinComponent;
import com.hypixel.hytale.component.Ref;
import com.hypixel.hytale.server.core.universe.world.storage.EntityStore;
import com.hypixel.hytale.assetstore.AssetUpdateQuery;
import com.hypixel.hytale.builtin.asseteditor.assettypehandler.AssetTypeHandler;
import java.nio.file.Path;
import java.util.Iterator;
import com.hypixel.hytale.protocol.Packet;
import com.hypixel.hytale.protocol.BlockType;
import com.hypixel.hytale.protocol.packets.asseteditor.AssetEditorUpdateModelPreview;
import com.hypixel.hytale.server.core.asset.type.model.config.Model;
import com.hypixel.hytale.builtin.asseteditor.assettypehandler.AssetStoreTypeHandler;
import javax.annotation.Nullable;
import com.hypixel.hytale.protocol.packets.asseteditor.AssetEditorPopupNotificationType;
import com.hypixel.hytale.server.core.universe.PlayerRef;
import javax.annotation.Nonnull;
import com.hypixel.hytale.builtin.asseteditor.event.AssetEditorClientDisconnectEvent;
import com.hypixel.hytale.builtin.asseteditor.event.AssetEditorSelectAssetEvent;
import com.hypixel.hytale.builtin.asseteditor.event.AssetEditorRequestDataSetEvent;
import com.hypixel.hytale.builtin.asseteditor.event.AssetEditorFetchAutoCompleteDataEvent;
import com.hypixel.hytale.builtin.asseteditor.event.AssetEditorAssetCreatedEvent;
import com.hypixel.hytale.builtin.asseteditor.event.AssetEditorUpdateWeatherPreviewLockEvent;
import com.hypixel.hytale.builtin.asseteditor.event.AssetEditorActivateButtonEvent;
import com.hypixel.hytale.server.core.asset.type.item.config.Item;
import com.hypixel.hytale.server.core.asset.type.model.config.ModelAsset;
import com.hypixel.hytale.assetstore.event.LoadedAssetsEvent;
import com.hypixel.hytale.protocol.packets.asseteditor.AssetEditorPreviewCameraSettings;
import java.util.UUID;
import java.util.Map;
import com.hypixel.hytale.protocol.packets.world.UpdateEditorWeatherOverride;
import com.hypixel.hytale.protocol.packets.world.ClearEditorTimeOverride;
import com.hypixel.hytale.server.core.Message;

@Deprecated
public class AssetSpecificFunctionality
{
    private static final Message NO_GAME_CLIENT_MESSAGE;
    private static final ClearEditorTimeOverride CLEAR_EDITOR_TIME_OVERRIDE_PACKET;
    private static final UpdateEditorWeatherOverride CLEAR_WEATHER_OVERRIDE_PACKET;
    private static final String MODEL_ASSET_ID;
    private static final String ITEM_ASSET_ID;
    private static final String WEATHER_ASSET_ID;
    private static final String ENVIRONMENT_ASSET_ID;
    private static final Map<UUID, PlayerPreviewData> activeWeatherPreviewMapping;
    private static final AssetEditorPreviewCameraSettings DEFAULT_PREVIEW_CAMERA_SETTINGS;
    
    public static void setup() {
        getEventRegistry().register(LoadedAssetsEvent.class, ModelAsset.class, AssetSpecificFunctionality::onModelAssetLoaded);
        getEventRegistry().register(LoadedAssetsEvent.class, Item.class, AssetSpecificFunctionality::onItemAssetLoaded);
        getEventRegistry().register(AssetEditorActivateButtonEvent.class, "EquipItem", AssetSpecificFunctionality::onEquipItem);
        getEventRegistry().register(AssetEditorActivateButtonEvent.class, "UseModel", AssetSpecificFunctionality::onUseModel);
        getEventRegistry().register(AssetEditorActivateButtonEvent.class, "ResetModel", AssetSpecificFunctionality::onResetModel);
        getEventRegistry().register(AssetEditorUpdateWeatherPreviewLockEvent.class, AssetSpecificFunctionality::onUpdateWeatherPreviewLockEvent);
        getEventRegistry().register(AssetEditorAssetCreatedEvent.class, AssetSpecificFunctionality.ITEM_ASSET_ID, AssetSpecificFunctionality::onItemAssetCreated);
        getEventRegistry().register(AssetEditorAssetCreatedEvent.class, AssetSpecificFunctionality.MODEL_ASSET_ID, AssetSpecificFunctionality::onModelAssetCreated);
        getEventRegistry().register(AssetEditorFetchAutoCompleteDataEvent.class, "BlockGroups", AssetSpecificFunctionality::onRequestBlockGroupsDataSet);
        getEventRegistry().register(AssetEditorFetchAutoCompleteDataEvent.class, "LocalizationKeys", AssetSpecificFunctionality::onRequestLocalizationKeyDataSet);
        getEventRegistry().register(AssetEditorRequestDataSetEvent.class, "ItemCategories", AssetSpecificFunctionality::onRequestItemCategoriesDataSet);
        getEventRegistry().registerGlobal(AssetEditorSelectAssetEvent.class, AssetSpecificFunctionality::onSelectAsset);
        getEventRegistry().registerGlobal(AssetEditorClientDisconnectEvent.class, AssetSpecificFunctionality::onClientDisconnected);
    }
    
    @Nullable
    private static PlayerRef tryGetPlayer(@Nonnull final EditorClient editorClient) {
        final PlayerRef playerRef = editorClient.tryGetPlayer();
        if (playerRef == null) {
            editorClient.sendPopupNotification(AssetEditorPopupNotificationType.Warning, AssetSpecificFunctionality.NO_GAME_CLIENT_MESSAGE);
            return null;
        }
        return playerRef;
    }
    
    private static void onModelAssetLoaded(@Nonnull final LoadedAssetsEvent<String, ModelAsset, ?> event) {
        if (event.isInitial()) {
            return;
        }
        final Map<EditorClient, AssetPath> clientOpenAssetPathMapping = AssetEditorPlugin.get().getClientOpenAssetPathMapping();
        if (clientOpenAssetPathMapping.isEmpty()) {
            return;
        }
        for (final ModelAsset modelAsset : event.getLoadedAssets().values()) {
            for (final Map.Entry<EditorClient, AssetPath> editor : clientOpenAssetPathMapping.entrySet()) {
                final Path path = editor.getValue().path();
                if (path.toString().isEmpty()) {
                    continue;
                }
                final AssetTypeHandler assetType = AssetEditorPlugin.get().getAssetTypeRegistry().getAssetTypeHandlerForPath(path);
                if (!(assetType instanceof AssetStoreTypeHandler)) {
                    continue;
                }
                if (!((AssetStoreTypeHandler)assetType).getAssetStore().getAssetClass().equals(ModelAsset.class)) {
                    continue;
                }
                final String id = ModelAsset.getAssetStore().decodeFilePathKey(path);
                if (!modelAsset.getId().equals(id)) {
                    continue;
                }
                final com.hypixel.hytale.protocol.Model modelPacket = Model.createUnitScaleModel(modelAsset).toPacket();
                final AssetEditorUpdateModelPreview packet = new AssetEditorUpdateModelPreview(editor.getValue().toPacket(), modelPacket, null, AssetSpecificFunctionality.DEFAULT_PREVIEW_CAMERA_SETTINGS);
                editor.getKey().getPacketHandler().write(packet);
            }
        }
    }
    
    private static void onItemAssetLoaded(@Nonnull final LoadedAssetsEvent<String, Item, ?> event) {
        if (event.isInitial()) {
            return;
        }
        final Map<EditorClient, AssetPath> clientOpenAssetPathMapping = AssetEditorPlugin.get().getClientOpenAssetPathMapping();
        if (clientOpenAssetPathMapping.isEmpty()) {
            return;
        }
        final AssetUpdateQuery.RebuildCache rebuildCache = event.getQuery().getRebuildCache();
        if (!rebuildCache.isBlockTextures() && !rebuildCache.isModelTextures() && !rebuildCache.isItemIcons() && !rebuildCache.isModels()) {
            return;
        }
        for (final Item item : event.getLoadedAssets().values()) {
            for (final Map.Entry<EditorClient, AssetPath> editor : clientOpenAssetPathMapping.entrySet()) {
                final Path path = editor.getValue().path();
                if (path.toString().isEmpty()) {
                    continue;
                }
                final AssetTypeHandler assetType = AssetEditorPlugin.get().getAssetTypeRegistry().getAssetTypeHandlerForPath(path);
                if (!(assetType instanceof AssetStoreTypeHandler)) {
                    continue;
                }
                if (!((AssetStoreTypeHandler)assetType).getAssetStore().getAssetClass().equals(Item.class)) {
                    continue;
                }
                final String id = Item.getAssetStore().decodeFilePathKey(path);
                if (!item.getId().equals(id)) {
                    continue;
                }
                final AssetEditorUpdateModelPreview packet = getModelPreviewPacketForItem(editor.getValue(), item);
                if (packet == null) {
                    continue;
                }
                editor.getKey().getPacketHandler().write(packet);
            }
        }
    }
    
    private static void onItemAssetCreated(@Nonnull final AssetEditorAssetCreatedEvent event) {
        if (!"EquipItem".equals(event.getButtonId())) {
            return;
        }
        equipItem(event.getAssetPath(), event.getEditorClient());
    }
    
    private static void onModelAssetCreated(@Nonnull final AssetEditorAssetCreatedEvent event) {
        if (!"UseModel".equals(event.getButtonId())) {
            return;
        }
        useModel(event.getAssetPath(), event.getEditorClient());
    }
    
    private static void onEquipItem(@Nonnull final AssetEditorActivateButtonEvent event) {
        final AssetPath currentAssetPath = AssetEditorPlugin.get().getOpenAssetPath(event.getEditorClient());
        if (currentAssetPath == null || currentAssetPath.path().toString().isEmpty()) {
            return;
        }
        equipItem(currentAssetPath.path(), event.getEditorClient());
    }
    
    private static void onUseModel(@Nonnull final AssetEditorActivateButtonEvent event) {
        final AssetPath currentAssetPath = AssetEditorPlugin.get().getOpenAssetPath(event.getEditorClient());
        if (currentAssetPath == null || currentAssetPath.path().toString().isEmpty()) {
            return;
        }
        useModel(currentAssetPath.path(), event.getEditorClient());
    }
    
    private static void onUpdateWeatherPreviewLockEvent(@Nonnull final AssetEditorUpdateWeatherPreviewLockEvent event) {
        final PlayerPreviewData currentPreviewSettings = AssetSpecificFunctionality.activeWeatherPreviewMapping.computeIfAbsent(event.getEditorClient().getUuid(), k -> new PlayerPreviewData());
        currentPreviewSettings.keepPreview = event.isLocked();
    }
    
    private static void onResetModel(@Nonnull final AssetEditorActivateButtonEvent event) {
        final EditorClient editorClient = event.getEditorClient();
        final PlayerRef playerRef = tryGetPlayer(editorClient);
        if (playerRef == null) {
            return;
        }
        final Ref<EntityStore> ref = playerRef.getReference();
        if (ref == null || !ref.isValid()) {
            return;
        }
        final Store<EntityStore> store = ref.getStore();
        final World world = store.getExternalData().getWorld();
        world.execute(() -> {
            if (!store.getArchetype(ref).contains(PlayerSkinComponent.getComponentType())) {
                final Message message = Message.translation("server.assetEditor.messages.model.noAuthSkinForPlayer").param("model", "Player");
                editorClient.sendPopupNotification(AssetEditorPopupNotificationType.Error, message);
            }
            else {
                PlayerUtil.resetPlayerModel(ref, store);
            }
        });
    }
    
    private static void equipItem(@Nonnull final Path assetPath, @Nonnull final EditorClient editorClient) {
        final PlayerRef playerRef = tryGetPlayer(editorClient);
        if (playerRef == null) {
            return;
        }
        final Player player = playerRef.getComponent(Player.getComponentType());
        final String key = Item.getAssetStore().decodeFilePathKey(assetPath);
        final Item item = Item.getAssetMap().getAsset(key);
        if (item == null) {
            editorClient.sendPopupNotification(AssetEditorPopupNotificationType.Error, Message.translation("server.assetEditor.messages.unknownItem").param("id", key.toString()));
            return;
        }
        final ItemArmor itemArmor = item.getArmor();
        if (itemArmor != null) {
            player.getInventory().getArmor().setItemStackForSlot((short)itemArmor.getArmorSlot().ordinal(), new ItemStack(key));
            return;
        }
        player.getInventory().getCombinedHotbarFirst().addItemStack(new ItemStack(key));
    }
    
    private static void useModel(@Nonnull final Path assetPath, @Nonnull final EditorClient editorClient) {
        final PlayerRef playerRef = tryGetPlayer(editorClient);
        if (playerRef == null) {
            return;
        }
        final Ref<EntityStore> ref = playerRef.getReference();
        if (ref == null || !ref.isValid()) {
            return;
        }
        final Store<EntityStore> store = ref.getStore();
        final World world = store.getExternalData().getWorld();
        world.execute(() -> {
            final String key = ModelAsset.getAssetStore().decodeFilePathKey(assetPath);
            final ModelAsset modelAsset = ModelAsset.getAssetMap().getAsset(key);
            if (modelAsset == null) {
                final Message unknownModelMessage = Message.translation("server.assetEditor.messages.unknownModel").param("id", key);
                editorClient.sendPopupNotification(AssetEditorPopupNotificationType.Error, unknownModelMessage);
            }
            else {
                final Model model = Model.createRandomScaleModel(modelAsset);
                store.putComponent(ref, ModelComponent.getComponentType(), new ModelComponent(model));
            }
        });
    }
    
    private static void onRequestLocalizationKeyDataSet(@Nonnull final AssetEditorFetchAutoCompleteDataEvent event) {
        final ObjectArrayList<String> results = new ObjectArrayList<String>();
        final String query = event.getQuery().toLowerCase();
        final Set<String> messageKeys = I18nModule.get().getMessages("en-US").keySet();
        for (final String key : messageKeys) {
            if (key.toLowerCase().startsWith(query)) {
                results.add(key);
            }
            if (results.size() >= 25) {
                break;
            }
        }
        event.setResults(results.toArray(String[]::new));
    }
    
    private static void onRequestBlockGroupsDataSet(@Nonnull final AssetEditorFetchAutoCompleteDataEvent event) {
        final ObjectArrayList<String> results = new ObjectArrayList<String>();
        final String query = event.getQuery().toLowerCase();
        for (final String group : com.hypixel.hytale.server.core.asset.type.blocktype.config.BlockType.getAssetMap().getGroups()) {
            if (group != null) {
                if (!group.trim().isEmpty()) {
                    if (query.isEmpty() || group.toLowerCase().contains(query)) {
                        results.add(group);
                    }
                }
            }
        }
        event.setResults(results.toArray(String[]::new));
    }
    
    private static void onRequestItemCategoriesDataSet(@Nonnull final AssetEditorRequestDataSetEvent event) {
        final ItemModule itemModule = ItemModule.get();
        if (itemModule.isDisabled()) {
            HytaleLogger.getLogger().at(Level.WARNING).log("Received ItemCategories dataset request but ItemModule is disabled!");
            return;
        }
        event.setResults(itemModule.getFlatItemCategoryList().toArray(String[]::new));
    }
    
    private static void onClientDisconnected(@Nonnull final AssetEditorClientDisconnectEvent event) {
        final AssetEditorPlugin plugin = AssetEditorPlugin.get();
        final EditorClient editorClient = event.getEditorClient();
        final PlayerRef player = editorClient.tryGetPlayer();
        final UUID uuid = editorClient.getUuid();
        final Set<EditorClient> editorClients = plugin.getEditorClients(uuid);
        if (editorClients == null || editorClients.size() == 1) {
            if (player != null) {
                player.getPacketHandler().write(AssetSpecificFunctionality.CLEAR_EDITOR_TIME_OVERRIDE_PACKET);
                player.getPacketHandler().write(AssetSpecificFunctionality.CLEAR_WEATHER_OVERRIDE_PACKET);
            }
            AssetSpecificFunctionality.activeWeatherPreviewMapping.remove(uuid);
            return;
        }
        final AssetPath openAssetPath = plugin.getOpenAssetPath(editorClient);
        if (openAssetPath == null || openAssetPath.equals(AssetPath.EMPTY_PATH)) {
            return;
        }
        final AssetTypeHandler assetType = plugin.getAssetTypeRegistry().getAssetTypeHandlerForPath(openAssetPath.path());
        if (assetType == null || !Weather.class.getSimpleName().equals(assetType.getConfig().id)) {
            return;
        }
        AssetSpecificFunctionality.activeWeatherPreviewMapping.remove(uuid);
        if (player != null) {
            player.getPacketHandler().write(new UpdateEditorWeatherOverride(0));
        }
    }
    
    static void resetTimeSettings(@Nonnull final EditorClient editorClient, @Nonnull final PlayerRef playerRef) {
        final Ref<EntityStore> ref = playerRef.getReference();
        if (ref == null || !ref.isValid()) {
            return;
        }
        final Store<EntityStore> store = ref.getStore();
        final World world = store.getExternalData().getWorld();
        final Player playerComponent = playerRef.getComponent(Player.getComponentType());
        assert playerComponent != null;
        final WorldTimeResource worldTimeResource = store.getResource(WorldTimeResource.getResourceType());
        final PacketHandler packetHandler = editorClient.getPacketHandler();
        final AssetEditorUpdateSecondsPerGameDay settingsPacket = new AssetEditorUpdateSecondsPerGameDay(world.getDaytimeDurationSeconds(), world.getNighttimeDurationSeconds());
        packetHandler.write(settingsPacket);
        final Instant gameTime = worldTimeResource.getGameTime();
        final UpdateEditorTimeOverride packet = new UpdateEditorTimeOverride(new InstantData(gameTime.getEpochSecond(), gameTime.getNano()), world.getWorldConfig().isGameTimePaused());
        packetHandler.write(packet);
        playerRef.getPacketHandler().write(AssetSpecificFunctionality.CLEAR_EDITOR_TIME_OVERRIDE_PACKET);
    }
    
    static void handleWeatherOrEnvironmentUnselected(@Nonnull final EditorClient editorClient, @Nonnull final Path assetPath, final boolean wasWeather) {
        final PlayerRef player = editorClient.tryGetPlayer();
        if (player == null) {
            return;
        }
        final PlayerPreviewData currentPreviewSettings = AssetSpecificFunctionality.activeWeatherPreviewMapping.computeIfAbsent(editorClient.getUuid(), k -> new PlayerPreviewData());
        if (currentPreviewSettings.keepPreview) {
            return;
        }
        resetTimeSettings(editorClient, player);
        if (wasWeather) {
            if (!assetPath.equals(currentPreviewSettings.weatherAssetPath)) {
                return;
            }
            currentPreviewSettings.weatherAssetPath = null;
            player.getPacketHandler().write(AssetSpecificFunctionality.CLEAR_WEATHER_OVERRIDE_PACKET);
        }
    }
    
    static void handleWeatherOrEnvironmentSelected(@Nonnull final EditorClient editorClient, @Nonnull final Path assetPath, final boolean isWeather) {
        final PlayerRef player = editorClient.tryGetPlayer();
        if (player == null) {
            return;
        }
        final PlayerPreviewData currentPreviewSettings = AssetSpecificFunctionality.activeWeatherPreviewMapping.computeIfAbsent(editorClient.getUuid(), k -> new PlayerPreviewData());
        if (!currentPreviewSettings.keepPreview) {
            resetTimeSettings(editorClient, player);
        }
        if (isWeather) {
            final AssetStore<String, Weather, IndexedLookupTableAssetMap<String, Weather>> assetStore = Weather.getAssetStore();
            final String key = assetStore.decodeFilePathKey(assetPath);
            final int weatherIndex = assetStore.getAssetMap().getIndex((Object)key);
            currentPreviewSettings.weatherAssetPath = assetPath;
            player.getPacketHandler().write(new UpdateEditorWeatherOverride(weatherIndex));
        }
    }
    
    private static void onSelectAsset(@Nonnull final AssetEditorSelectAssetEvent event) {
        final String assetType = event.getAssetType();
        if (AssetSpecificFunctionality.MODEL_ASSET_ID.equals(assetType)) {
            final String key = ModelAsset.getAssetStore().decodeFilePathKey(event.getAssetFilePath().path());
            final ModelAsset modelAsset = ModelAsset.getAssetMap().getAsset(key);
            if (modelAsset != null) {
                final com.hypixel.hytale.protocol.Model modelPacket = Model.createUnitScaleModel(modelAsset).toPacket();
                event.getEditorClient().getPacketHandler().write(new AssetEditorUpdateModelPreview(event.getAssetFilePath().toPacket(), modelPacket, null, AssetSpecificFunctionality.DEFAULT_PREVIEW_CAMERA_SETTINGS));
            }
        }
        if (AssetSpecificFunctionality.ITEM_ASSET_ID.equals(assetType)) {
            final AssetPath assetPath = event.getAssetFilePath();
            final String key2 = Item.getAssetStore().decodeFilePathKey(assetPath.path());
            final Item item = Item.getAssetMap().getAsset(key2);
            if (item != null) {
                final AssetEditorUpdateModelPreview packet = getModelPreviewPacketForItem(assetPath, item);
                if (packet != null) {
                    event.getEditorClient().getPacketHandler().write(packet);
                }
            }
        }
        final String previousAssetType = event.getPreviousAssetType();
        final boolean wasWeather = AssetSpecificFunctionality.WEATHER_ASSET_ID.equals(previousAssetType);
        if (wasWeather || AssetSpecificFunctionality.ENVIRONMENT_ASSET_ID.equals(previousAssetType)) {
            handleWeatherOrEnvironmentUnselected(event.getEditorClient(), event.getPreviousAssetFilePath().path(), wasWeather);
        }
        final boolean isWeather = AssetSpecificFunctionality.WEATHER_ASSET_ID.equals(assetType);
        if (isWeather || AssetSpecificFunctionality.ENVIRONMENT_ASSET_ID.equals(assetType)) {
            handleWeatherOrEnvironmentSelected(event.getEditorClient(), event.getAssetFilePath().path(), isWeather);
        }
    }
    
    public static AssetEditorUpdateModelPreview getModelPreviewPacketForItem(@Nonnull final AssetPath assetPath, @Nullable final Item item) {
        if (item == null) {
            return null;
        }
        AssetIconProperties iconProperties = item.getIconProperties();
        final AssetIconProperties defaultIconProperties = getDefaultItemIconProperties(item);
        if (iconProperties == null) {
            iconProperties = defaultIconProperties;
        }
        final AssetEditorPreviewCameraSettings camera = new AssetEditorPreviewCameraSettings();
        camera.modelScale = iconProperties.getScale() * item.getScale();
        final Vector2f translation = (iconProperties.getTranslation() != null) ? iconProperties.getTranslation() : defaultIconProperties.getTranslation();
        camera.cameraPosition = new Vector3f(-translation.x, -translation.y, 0.0f);
        final Vector3f rotation = (iconProperties.getRotation() != null) ? iconProperties.getRotation() : defaultIconProperties.getRotation();
        camera.cameraOrientation = new Vector3f((float)(-Math.toRadians(rotation.x)), (float)(-Math.toRadians(rotation.y)), (float)(-Math.toRadians(rotation.z)));
        if (item.getBlockId() != null) {
            final com.hypixel.hytale.server.core.asset.type.blocktype.config.BlockType blockType = com.hypixel.hytale.server.core.asset.type.blocktype.config.BlockType.getAssetStore().getAssetMap().getAsset(item.getBlockId());
            if (blockType != null) {
                final AssetEditorPreviewCameraSettings assetEditorPreviewCameraSettings = camera;
                assetEditorPreviewCameraSettings.modelScale *= blockType.getCustomModelScale();
                return new AssetEditorUpdateModelPreview(assetPath.toPacket(), null, blockType.toPacket(), camera);
            }
        }
        final com.hypixel.hytale.protocol.Model modelPacket = convertToModelPacket(item);
        return new AssetEditorUpdateModelPreview(assetPath.toPacket(), modelPacket, null, camera);
    }
    
    @Nonnull
    public static AssetIconProperties getDefaultItemIconProperties(@Nonnull final Item item) {
        if (item.getWeapon() != null) {
            return new AssetIconProperties(0.37f, new Vector2f(-24.6f, -24.6f), new Vector3f(45.0f, 90.0f, 0.0f));
        }
        if (item.getTool() != null) {
            return new AssetIconProperties(0.5f, new Vector2f(-17.4f, -12.0f), new Vector3f(45.0f, 270.0f, 0.0f));
        }
        if (item.getArmor() != null) {
            return switch (item.getArmor().getArmorSlot()) {
                default -> throw new MatchException(null, null);
                case Chest -> new AssetIconProperties(0.5f, new Vector2f(0.0f, -5.0f), new Vector3f(22.5f, 45.0f, 22.5f));
                case Head -> new AssetIconProperties(0.5f, new Vector2f(0.0f, -3.0f), new Vector3f(22.5f, 45.0f, 22.5f));
                case Legs -> new AssetIconProperties(0.5f, new Vector2f(0.0f, -25.8f), new Vector3f(22.5f, 45.0f, 22.5f));
                case Hands -> new AssetIconProperties(0.92f, new Vector2f(0.0f, -10.8f), new Vector3f(22.5f, 45.0f, 22.5f));
            };
        }
        return new AssetIconProperties(0.58823f, new Vector2f(0.0f, -13.5f), new Vector3f(22.5f, 45.0f, 22.5f));
    }
    
    @Nonnull
    public static com.hypixel.hytale.protocol.Model convertToModelPacket(@Nonnull final Item item) {
        final com.hypixel.hytale.protocol.Model packet = new com.hypixel.hytale.protocol.Model();
        packet.path = item.getModel();
        packet.texture = item.getTexture();
        return packet;
    }
    
    @Nonnull
    private static EventRegistry getEventRegistry() {
        return AssetEditorPlugin.get().getEventRegistry();
    }
    
    static {
        NO_GAME_CLIENT_MESSAGE = Message.translation("server.assetEditor.messages.noGameClient");
        CLEAR_EDITOR_TIME_OVERRIDE_PACKET = new ClearEditorTimeOverride();
        CLEAR_WEATHER_OVERRIDE_PACKET = new UpdateEditorWeatherOverride(0);
        MODEL_ASSET_ID = ModelAsset.class.getSimpleName();
        ITEM_ASSET_ID = Item.class.getSimpleName();
        WEATHER_ASSET_ID = Weather.class.getSimpleName();
        ENVIRONMENT_ASSET_ID = Environment.class.getSimpleName();
        activeWeatherPreviewMapping = new ConcurrentHashMap<UUID, PlayerPreviewData>();
        DEFAULT_PREVIEW_CAMERA_SETTINGS = new AssetEditorPreviewCameraSettings(0.25f, new Vector3f(0.0f, 75.0f, 0.0f), new Vector3f(0.0f, (float)Math.toRadians(45.0), 0.0f));
    }
    
    public static class PlayerPreviewData
    {
        @Nullable
        private Path weatherAssetPath;
        private boolean keepPreview;
    }
}
