commit 1632c87ccbc294e93484cdb54b1a28dbd9fa23bd Author: rtm516 Date: Sun Jun 21 11:42:57 2020 +0100 Initial Commit diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..f8740e1 --- /dev/null +++ b/.gitignore @@ -0,0 +1,226 @@ + +# Created by https://www.gitignore.io/api/git,java,maven,eclipse,netbeans,jetbrains+all +# Edit at https://www.gitignore.io/?templates=git,java,maven,eclipse,netbeans,jetbrains+all + +### Eclipse ### +.metadata +bin/ +tmp/ +*.tmp +*.bak +*.swp +*~.nib +local.properties +.settings/ +.loadpath +.recommenders + +# External tool builders +.externalToolBuilders/ + +# Locally stored "Eclipse launch configurations" +*.launch + +# PyDev specific (Python IDE for Eclipse) +*.pydevproject + +# CDT-specific (C/C++ Development Tooling) +.cproject + +# CDT- autotools +.autotools + +# Java annotation processor (APT) +.factorypath + +# PDT-specific (PHP Development Tools) +.buildpath + +# sbteclipse plugin +.target + +# Tern plugin +.tern-project + +# TeXlipse plugin +.texlipse + +# STS (Spring Tool Suite) +.springBeans + +# Code Recommenders +.recommenders/ + +# Annotation Processing +.apt_generated/ + +# Scala IDE specific (Scala & Java development for Eclipse) +.cache-main +.scala_dependencies +.worksheet + +### Eclipse Patch ### +# Eclipse Core +.project + +# JDT-specific (Eclipse Java Development Tools) +.classpath + +# Annotation Processing +.apt_generated + +.sts4-cache/ + +### Git ### +# Created by git for backups. To disable backups in Git: +# $ git config --global mergetool.keepBackup false +*.orig + +# Created by git when using merge tools for conflicts +*.BACKUP.* +*.BASE.* +*.LOCAL.* +*.REMOTE.* +*_BACKUP_*.txt +*_BASE_*.txt +*_LOCAL_*.txt +*_REMOTE_*.txt + +### Java ### +# Compiled class file +*.class + +# Log file +*.log + +# BlueJ files +*.ctxt + +# Mobile Tools for Java (J2ME) +.mtj.tmp/ + +# Package Files # +*.jar +*.war +*.nar +*.ear +*.zip +*.tar.gz +*.rar + +# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml +hs_err_pid* + +### JetBrains+all ### +# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio and WebStorm +# Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839 + +# User-specific stuff +.idea/**/workspace.xml +.idea/**/tasks.xml +.idea/**/usage.statistics.xml +.idea/**/dictionaries +.idea/**/shelf + +# Generated files +.idea/**/contentModel.xml + +# Sensitive or high-churn files +.idea/**/dataSources/ +.idea/**/dataSources.ids +.idea/**/dataSources.local.xml +.idea/**/sqlDataSources.xml +.idea/**/dynamic.xml +.idea/**/uiDesigner.xml +.idea/**/dbnavigator.xml + +# Gradle +.idea/**/gradle.xml +.idea/**/libraries + +# Gradle and Maven with auto-import +# When using Gradle or Maven with auto-import, you should exclude module files, +# since they will be recreated, and may cause churn. Uncomment if using +# auto-import. +# .idea/modules.xml +# .idea/*.iml +# .idea/modules +# *.iml +# *.ipr + +# CMake +cmake-build-*/ + +# Mongo Explorer plugin +.idea/**/mongoSettings.xml + +# File-based project format +*.iws + +# IntelliJ +out/ + +# mpeltonen/sbt-idea plugin +.idea_modules/ + +# JIRA plugin +atlassian-ide-plugin.xml + +# Cursive Clojure plugin +.idea/replstate.xml + +# Crashlytics plugin (for Android Studio and IntelliJ) +com_crashlytics_export_strings.xml +crashlytics.properties +crashlytics-build.properties +fabric.properties + +# Editor-based Rest Client +.idea/httpRequests + +# Android studio 3.1+ serialized cache file +.idea/caches/build_file_checksums.ser + +### JetBrains+all Patch ### +# Ignores the whole .idea folder and all .iml files +# See https://github.com/joeblau/gitignore.io/issues/186 and https://github.com/joeblau/gitignore.io/issues/360 + +#.idea/ + +# Reason: https://github.com/joeblau/gitignore.io/issues/186#issuecomment-249601023 + +*.iml +modules.xml +.idea/misc.xml +*.ipr + +# Sonarlint plugin +.idea/sonarlint + +### Maven ### +target/ +pom.xml.tag +pom.xml.releaseBackup +pom.xml.versionsBackup +pom.xml.next +release.properties +dependency-reduced-pom.xml +buildNumber.properties +.mvn/timing.properties +.mvn/wrapper/maven-wrapper.jar + +### NetBeans ### +**/nbproject/private/ +**/nbproject/Makefile-*.mk +**/nbproject/Package-*.bash +build/ +nbbuild/ +dist/ +nbdist/ +.nb-gradle/ + +# End of https://www.gitignore.io/api/git,java,maven,eclipse,netbeans,jetbrains+all + +# Copyright header files +.idea/* +!.idea/copyright/ diff --git a/.idea/copyright/Geyser.xml b/.idea/copyright/Geyser.xml new file mode 100644 index 0000000..efe4e1e --- /dev/null +++ b/.idea/copyright/Geyser.xml @@ -0,0 +1,6 @@ + + + + \ No newline at end of file diff --git a/.idea/copyright/profiles_settings.xml b/.idea/copyright/profiles_settings.xml new file mode 100644 index 0000000..09299b8 --- /dev/null +++ b/.idea/copyright/profiles_settings.xml @@ -0,0 +1,7 @@ + + + + + + + \ No newline at end of file diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..acd4af1 --- /dev/null +++ b/LICENSE @@ -0,0 +1,21 @@ +The MIT License + +Copyright (c) 2019-2020 GeyserMC. http://geysermc.org + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. \ No newline at end of file diff --git a/README.md b/README.md new file mode 100644 index 0000000..eb88b18 --- /dev/null +++ b/README.md @@ -0,0 +1,29 @@ +# GeyserConnect + +[![forthebadge made-with-java](https://ForTheBadge.com/images/badges/made-with-java.svg)](https://java.com/) + +[![License: MIT](https://img.shields.io/badge/license-MIT-blue.svg)](LICENSE) +[![Build Status](https://ci.nukkitx.com/job/GeyserMC/job/GeyserConnect/job/master/badge/icon)](https://ci.nukkitx.com/job/GeyserMC/job/GeyserConnect/job/master/) +[![Discord](https://img.shields.io/discord/613163671870242838.svg?color=%237289da&label=discord)](http://discord.geysermc.org/) +[![HitCount](http://hits.dwyl.io/GeyserMC/GeyserConnect.svg)](http://hits.dwyl.io/GeyserMC/GeyserConnect) + +GeyserConnect is an easy way for Bedrock Edition clients to connect to any Java Edition servers without having to run anything. + +## What is GeyserConnect? +GeyserConnect is a server that Minecraft: Bedrock Edition clients can connect to that allows for a list of Minecraft: Java Edition servers to be displayed and accessed through 1 public Geyser instance. It is effectively a combination of [BedrockConnect](https://github.com/Pugmatt/BedrockConnect) and [Geyser](https://github.com/GeyserMC/Geyser). + +**Please note, this project is still a work in progress and should not be used on production. Expect bugs!** + +## TODO +- [x] Auto start Geyser instance +- [x] Transfer player to Geyser instance and connect to correct server +- [x] Server list + - [x] View + - [x] Add + - [x] Remove + - [x] Edit +- [x] Stop Geyser server after its idle for a while +- [x] Config file +- [x] Fix server images not loading straight away on Win10 +- [x] Per server online/offline mode +- [x] Add option to add a bedrock server diff --git a/pom.xml b/pom.xml new file mode 100644 index 0000000..984ebb4 --- /dev/null +++ b/pom.xml @@ -0,0 +1,67 @@ + + + + + 4.0.0 + + org.geysermc + packconverter + 1.0-SNAPSHOT + + PackConverter + Converts java edition resource packs into bedrock edition resource packs. + https://geysermc.org + + + PackConverter + UTF-8 + UTF-8 + 1.8 + 1.8 + + + + + org.projectlombok + lombok + 1.18.4 + provided + + + com.fasterxml.jackson.core + jackson-databind + 2.9.8 + + + com.twelvemonkeys.imageio + imageio-tga + 3.5 + + + \ No newline at end of file diff --git a/src/main/java/org/geysermc/packconverter/Main.java b/src/main/java/org/geysermc/packconverter/Main.java new file mode 100644 index 0000000..3ca8568 --- /dev/null +++ b/src/main/java/org/geysermc/packconverter/Main.java @@ -0,0 +1,203 @@ +/* + * Copyright (c) 2019-2020 GeyserMC. http://geysermc.org + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + * + * @author GeyserMC + * @link https://github.com/GeyserMC/PackConverter + * + */ + +package org.geysermc.packconverter; + +import com.fasterxml.jackson.core.JsonParser; +import com.fasterxml.jackson.core.util.DefaultPrettyPrinter; +import com.fasterxml.jackson.databind.ObjectMapper; +import com.fasterxml.jackson.databind.ObjectWriter; + +import javax.imageio.ImageIO; +import java.awt.*; +import java.awt.image.BufferedImage; +import java.awt.image.RescaleOp; +import java.io.*; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; +import java.util.*; +import java.util.regex.Matcher; +import java.util.regex.Pattern; +import java.util.zip.ZipEntry; +import java.util.zip.ZipFile; + +public class Main { + private static final String packname = "Faithful-1.15"; + private static final ObjectMapper OBJECT_MAPPER = new ObjectMapper().enable(JsonParser.Feature.ALLOW_COMMENTS); + + public static void main(String[] args) { + File inFile = new File(packname + ".zip"); + File outFile = new File(packname + ".mcpack"); + File outDir = new File(packname + "_mcpack/"); + + //if (inFile.exists() && !outFile.exists()) { + if (true) { + try { + // Open zip + ZipFile zipFile = new ZipFile(inFile); + + // Read mapping json + Map pathMappings = OBJECT_MAPPER.readValue(Main.class.getClassLoader().getResourceAsStream("paths.json"), Map.class); + Map fileMappings = OBJECT_MAPPER.readValue(Main.class.getClassLoader().getResourceAsStream("files.json"), Map.class); + + // pack.mcmeta match + Pattern metaPattern = Pattern.compile("(.*)/pack.mcmeta"); + String metaPath = ""; + String metaDesc = ""; + + // Regex match files over + ZipEntry entry; + final Enumeration entries = zipFile.entries(); + while (entries.hasMoreElements()) { + entry = entry = entries.nextElement(); + if (metaPath.equals("")) { + Matcher m = metaPattern.matcher(entry.getName()); + if (m.find()) { + metaPath = m.group(1); + metaDesc = OBJECT_MAPPER.readTree(zipFile.getInputStream(entry)).get("pack").get("description").asText(); + + continue; + } + } + + String curName = entry.getName(); + String newName = entry.getName(); + for (Map.Entry mapping : pathMappings.entrySet()) { + newName = curName.replaceAll(mapping.getKey(), mapping.getValue()); + if (newName != curName) { + break; + } + } + + Path newNamePath = Paths.get(newName); + for (Map.Entry mapping : fileMappings.entrySet()) { + String filename = newNamePath.getFileName().toString(); + if (filename.matches(mapping.getKey())) { + newNamePath = newNamePath.getParent().resolve(filename.replaceAll(mapping.getKey(), mapping.getValue())); + newName = newNamePath.toString(); + break; + } + } + + if (newName != curName) { + System.out.format("%s => %s\n", curName, newName); + + File newFile = outDir.toPath().resolve(newName).toFile(); + newFile.getParentFile().mkdirs(); + + InputStream fileStream = zipFile.getInputStream(entry); + FileOutputStream outStream = new FileOutputStream(newFile); + + byte[] buf = new byte[fileStream.available()]; + int length; + while ((length = fileStream.read(buf)) != -1) { + outStream.write(buf, 0, length); + } + + outStream.flush(); + outStream.close(); + } + } + + // Some fancy TGA trickery + //fixGrass(outDir.toPath().resolve(metaPath)); + + // Build manifest.json + ResourcePackManifest.Header header = new ResourcePackManifest.Header(); + header.setName(packname); + header.setDescription(metaDesc); + header.setUuid(UUID.randomUUID()); + header.setVersion(new int[] { 1, 0, 0}); + + ResourcePackManifest.Module module = new ResourcePackManifest.Module(); + module.setDescription(metaDesc); + module.setType("resources"); + module.setUuid(UUID.randomUUID()); + module.setVersion(new int[] { 1, 0, 0}); + + ResourcePackManifest manifest = new ResourcePackManifest(); + manifest.setFormatVersion(1); + manifest.setHeader(header); + Collection modules = new ArrayList(); + modules.add(module); + manifest.setModules(modules); + + ObjectWriter writer = OBJECT_MAPPER.writer(new DefaultPrettyPrinter()); + writer.writeValue(outDir.toPath().resolve(metaPath).resolve("manifest.json").toFile(), manifest); + + // Save + ZipUtils zipUtils = new ZipUtils(outDir); + zipUtils.generateFileList(); + zipUtils.zipIt(outFile.toString()); + + // Delete temp folder + //Files.delete(outDir.toPath()); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + + /** + * This is meant to write a dirt texture to a image with all alpha 0 + * then write the grass_side on top while preserving the RGB of the + * dirt texture, only seems to be possible with TGA and this doesnt work + * @param rootDir + */ + private static void fixGrass(Path rootDir) { + File grassSide = rootDir.resolve("textures/blocks/grass_side.png").toFile(); + File grassSideNew = rootDir.resolve("textures/blocks/grass_side.tga").toFile(); + File dirt = rootDir.resolve("textures/blocks/dirt.png").toFile(); + + if (grassSide.exists() && dirt.exists()) { + ImageIO.scanForPlugins(); + + try { + BufferedImage grassSideImg = ImageIO.read(grassSide); + BufferedImage dirtImg = ImageIO.read(dirt); + + BufferedImage newGrassSideImg = new BufferedImage(grassSideImg.getWidth(), grassSideImg.getHeight(), BufferedImage.TYPE_INT_ARGB); + Graphics2D g2 = newGrassSideImg.createGraphics(); + + float[] scales = { 1f, 1f, 1f, 0f }; + float[] offsets = new float[4]; + RescaleOp rop = new RescaleOp(scales, offsets, null); + g2.drawImage(dirtImg, rop, 0, 0); + + scales = new float[] { 1f, 1f, 1f, 1f }; + rop = new RescaleOp(scales, offsets, null); + g2.drawImage(grassSideImg, rop, 0, 0); + + g2.dispose(); + ImageIO.write(newGrassSideImg, "TGA", grassSideNew); + Files.delete(grassSide.toPath()); + } catch (IOException e) { + e.printStackTrace(); + } + } + } +} diff --git a/src/main/java/org/geysermc/packconverter/ResourcePackManifest.java b/src/main/java/org/geysermc/packconverter/ResourcePackManifest.java new file mode 100644 index 0000000..6648fa1 --- /dev/null +++ b/src/main/java/org/geysermc/packconverter/ResourcePackManifest.java @@ -0,0 +1,119 @@ +/* + * Copyright (c) 2019-2020 GeyserMC. http://geysermc.org + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + * + * @author GeyserMC + * @link https://github.com/GeyserMC/PackConverter + * + */ + +package org.geysermc.packconverter; + +import com.fasterxml.jackson.annotation.JsonInclude; +import com.fasterxml.jackson.annotation.JsonProperty; +import lombok.*; + +import java.util.Collection; +import java.util.Collections; +import java.util.UUID; + +/** + * author: NukkitX + * Nukkit Project + */ +@Setter +@Getter +@EqualsAndHashCode +@JsonInclude(JsonInclude.Include.NON_NULL) +public class ResourcePackManifest { + @JsonProperty("format_version") + private Integer formatVersion; + private Header header; + private Collection modules; + protected Collection dependencies; + + public Collection getModules() { + return Collections.unmodifiableCollection(modules); + } + + @Setter + @Getter + @ToString + @JsonInclude(JsonInclude.Include.NON_NULL) + public static class Header { + private String description; + private String name; + private UUID uuid; + private int[] version; + @JsonProperty("min_engine_version") + private int[] minimumSupportedMinecraftVersion; + } + + @Setter + @Getter + @ToString + @JsonInclude(JsonInclude.Include.NON_NULL) + public static class Module { + private String description; + private String type; + private UUID uuid; + private int[] version; + } + + @Setter + @Getter + @ToString + @JsonInclude(JsonInclude.Include.NON_NULL) + public static class Dependency { + private UUID uuid; + private int[] version; + } + + @Value + public static class Version { + private final int major; + private final int minor; + private final int patch; + + public static Version fromString(String ver) { + String[] split = ver.replace(']', ' ') + .replace('[', ' ') + .replaceAll(" ", "").split(","); + + return new Version(Integer.parseInt(split[0]), Integer.parseInt(split[1]), Integer.parseInt(split[2])); + } + + public static Version fromArray(int[] ver) { + return new Version(ver[0], ver[1], ver[2]); + } + + private Version(int major, int minor, int patch) { + this.major = major; + this.minor = minor; + this.patch = patch; + } + + + @Override + public String toString() { + return major + "." + minor + "." + patch; + } + } +} diff --git a/src/main/java/org/geysermc/packconverter/ZipUtils.java b/src/main/java/org/geysermc/packconverter/ZipUtils.java new file mode 100644 index 0000000..a89a2b7 --- /dev/null +++ b/src/main/java/org/geysermc/packconverter/ZipUtils.java @@ -0,0 +1,115 @@ +/* + * Copyright (c) 2019-2020 GeyserMC. http://geysermc.org + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + * + * @author GeyserMC + * @link https://github.com/GeyserMC/PackConverter + * + */ + +package org.geysermc.packconverter; + +import java.io.File; +import java.io.FileInputStream; +import java.io.FileOutputStream; +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; +import java.util.zip.ZipEntry; +import java.util.zip.ZipOutputStream; + +/** + * Adjusted ZipUtils class to better suit the usage + * From https://stackoverflow.com/a/15970455/5299903 + */ +public class ZipUtils { + + private final List fileList = new ArrayList<>(); + private final File sourceFolder; + + public ZipUtils(File sourceFolder) { + this.sourceFolder = sourceFolder; + } + + public void zipIt(String zipFile) { + byte[] buffer = new byte[1024]; + String source = sourceFolder.getName(); + FileOutputStream fos = null; + ZipOutputStream zos = null; + try { + fos = new FileOutputStream(zipFile); + zos = new ZipOutputStream(fos); + + System.out.println("Output to Zip : " + zipFile); + FileInputStream in = null; + + for (String file: this.fileList) { + System.out.println("File Added : " + file); + ZipEntry ze = new ZipEntry(file); + zos.putNextEntry(ze); + try { + in = new FileInputStream(sourceFolder + File.separator + file); + int len; + while ((len = in .read(buffer)) > 0) { + zos.write(buffer, 0, len); + } + } finally { + if (in != null) + in.close(); + } + } + + zos.closeEntry(); + System.out.println("Folder successfully compressed"); + + } catch (IOException ex) { + ex.printStackTrace(); + } finally { + try { + zos.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + + public void generateFileList() { + generateFileList(sourceFolder); + } + + + public void generateFileList(File node) { + // add file only + if (node.isFile()) { + fileList.add(generateZipEntry(node.getAbsolutePath())); + } + + if (node.isDirectory()) { + String[] subNote = node.list(); + for (String filename: subNote) { + generateFileList(new File(node, filename)); + } + } + } + + private String generateZipEntry(String file) { + return file.substring(sourceFolder.getAbsolutePath().length() + 1); + } +} diff --git a/src/main/resources/files.json b/src/main/resources/files.json new file mode 100644 index 0000000..a49425b --- /dev/null +++ b/src/main/resources/files.json @@ -0,0 +1,106 @@ +{ + /* Blocks */ + "grass_block_top.png": "grass_top.png", + "grass_block_side.png": "grass_side_carried.png", + //"grass_block_side_overlay.png": "grass_side.png", + "dark_oak_log.png": "log_big_oak.png", + "dark_oak_log_top.png": "log_big_oak_top.png", + "^(?!stripped_)([a-z_]+)_log.png": "log_$1.png", + "^(?!stripped_)([a-z_]+)_log_top.png": "log_$1_top.png", + "dark_oak_leaves.png": "leaves_big_oak.png", + "([a-z_]+)_leaves.png": "leaves_$1.png", + "dark_oak_sapling.png": "sapling_roofed_oak.png", + "([a-z_]+)_sapling.png": "sapling_$1.png", + "dark_oak_planks.png": "planks_big_oak.png", + "([a-z_]+)_planks.png": "planks_$1.png", + "oak_trapdoor.png": "trapdoor.png", + "mossy_cobblestone.png": "cobblestone_mossy.png", + "([a-z_]+)_wool.png": "wool_colored_$1.png", + "oak_door_top.png": "door_wood_upper.png", + "oak_door_bottom.png": "door_wood_lower.png", + "([a-z_]+)_door_top.png": "door_$1_upper.png", + "([a-z_]+)_door_bottom.png": "door_$1_lower.png", + "terracotta.png": "hardened_clay.png", + "([a-z_]+)_terracotta.png": "hardened_clay_stained_$1.png", + "([a-z_]+)_glazed_terracotta.png": "glazed_terracotta_$1.png", + "([a-z_]+)_stained_glass.png": "glass_$1.png", + "([a-z_]+)_stained_glass_top.png": "glass_pane_top_$1.png", + "grass.png": "tallgrass.png", + "([a-z_]+)_shulker_box.png": "shulker_top_$1.png", + "([a-z_]+)_concrete.png": "concrete_$1.png", + "([a-z_]+)_concrete_powder.png": "concrete_powder_$1.png", + "([a-z_]+)_stage([0-9]+).png": "$1_stage_$2.png", + "poppy.png": "flower_rose.png", + "azure_bluet.png": "flower_houstonia.png", + "pink_tulip.png": "flower_paeonia.png", + "([a-z_]+)_tulip.png": "flower_tulip_$1.png", + "(allium|blue_orchid|cornflower|dandelion|lily_of_the_valley|oxeye_daisy|wither_rose).png": "flower_$1.png", + "tall_grass_(top|bottom).png": "double_plant_grass_$1.png", + "large_fern_(top|bottom).png": "double_plant_fern_$1.png", + "lilac_(top|bottom).png": "double_plant_syringa_$1.png", + "rose_bush_(top|bottom).png": "double_plant_rose_$1.png", + "peony_(top|bottom).png": "double_plant_paeonia_$1.png", + "sunflower_(top|bottom|back|front).png": "double_plant_sunflower_$1.png", + "tall_seagrass_(top|bottom).png": "seagrass_doubletall_$1_a.png", + "farmland.png": "farmland_dry.png", + "farmland_moist.png": "farmland_wet.png", + "torch.png": "torch_on.png", + "sugar_cane.png": "reeds.png", + "kelp_plant.png": "kelp_a.png", + "kelp.png": "kelp_top.png", + "sandstone.png": "sandstone_normal.png", + "(granite|andesite|diorite).png": "stone_$1.png", + "polished_([a-z_]+).png": "stone_$1_smooth.png", + "([a-z_]+)_stem.png": "$1_stem_disconnected.png", + "attached_([a-z_]+)_stem.png": "$1_stem_connected.png", + "stonecutter_([a-z_]+).png": "stonecutter2_$1.png", + "cobweb.png": "web.png", + "([a-z_]+)_mushroom.png": "mushroom_$1.png", + "rail.png": "rail_normal.png", + "rail_corner.png": "rail_normal_turned.png", + "([a-z_]+)_rail.png": "rail_$1.png", + "([a-z_]+)_rail_on.png": "rail_$1_powered.png", + + /* Items */ + "([a-z_]+)_bucket.png": "bucket_$1.png", + "oak_(sign|boat).png": "$1.png", + "dark_oak_(sign|boat).png": "$1_darkoak.png", + "([a-z_]+)_(sign|boat).png": "$2_$1.png", + "([a-z_]+)_seeds.png": "seeds_$1.png", + "lapis_lazuli.png": "dye_powder_blue.png", + "([a-z_]+)_dye.png": "dye_powder_$1.png", + "(chicken|porkchop|beef|mutton|rabbit).png": "$1_raw.png", + "(pufferfish|salmon).png": "fish_$1_raw.png", + "cooked_(pufferfish|salmon).png": "fish_$1_cooked.png", + "cod.png": "fish_raw.png", + "cooked_cod.png": "fish_cooked.png", + "tropical_fish.png": "fish_clownfish_raw.png", + "pufferfish.png": "fish_pufferfish_raw.png", + "golden_(apple|carrot).png": "$1_golden.png", + "melon_slice.png": "melon.png", + "glistering_melon_slice.png": "melon_speckled.png", + "heart_of_the_sea.png": "heartofthesea_closed.png", + "nautilus_shell.png": "nautilus.png", + "fire_charge.png": "fireball.png", + "fermented_spider_eye.png": "spider_eye_fermented.png", + "dragon_breath.png": "dragons_breath.png", + "slime_ball.png": "slimeball.png", + "book.png": "book_normal.png", + "([a-z_]+)_book.png": "book_$1.png", + "redstone.png": "redstone_dust.png", + "minecart.png": "minecart_normal.png", + "([a-z_]+)_minecart.png": "minecart_$1.png", + "poisonous_potato.png": "potato_poisonous.png", + "firework_rocket.png": "fireworks.png", + "golden_([a-z_]+).png": "gold_$1.png", + "wooden_([a-z_]+).png": "wood_$1.png", + "bow.png": "bow_standby.png", + "map.png": "map_empty.png", + "totem_of_undying.png": "totem.png", + "glass_bottle.png": "potion_bottle_empty.png", + "lingering_potion.png": "potion_bottle_lingering_empty.png", + "baked_potato.png": "potato_baked.png", + "popped_chorus_fruit.png": "chorus_fruit_popped.png", + "oak_door.png": "door_wood.png", + "([a-z_]+)_door.png": "door_$1.png" +} \ No newline at end of file diff --git a/src/main/resources/paths.json b/src/main/resources/paths.json new file mode 100644 index 0000000..20d93ac --- /dev/null +++ b/src/main/resources/paths.json @@ -0,0 +1,7 @@ +{ + "\\/assets\\/minecraft\\/textures\\/block\\/([a-z0-9_]+)\\.png": "\\/textures\\/blocks\\/$1.png", + "\\/assets\\/minecraft\\/textures\\/item\\/([a-z0-9_]+)\\.png": "\\/textures\\/items\\/$1.png", + "\\/assets\\/minecraft\\/textures\\/entity\\/([a-z0-9_]+)\\.png": "\\/textures\\/entity\\/$1.png", + "\\/assets\\/minecraft\\/textures\\/entity\\/([a-z_]+)\\/([a-z0-9_]+)\\.png": "\\/textures\\/entity\\/$1\\/$2.png", + "(.*)\\/pack.png": "$1\\/pack_icon.png" +} \ No newline at end of file