再帰関数に変更。

level.datを読み込み可能に。
This commit is contained in:
mii
2020-09-27 02:14:54 +09:00
parent 67b6fdaefd
commit cf48402f43
70 changed files with 557 additions and 62 deletions

View File

@@ -1 +1 @@
D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\ByteConvertExtensionKt.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Converter.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\MainKt.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\SaveEditor.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\Data.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Byte.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Compound.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_End.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Int.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Long.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Short.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_String.class
D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\ByteConvertExtensionKt.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Converter.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\MainKt.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\SaveEditor.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\Data.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Byte.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Byte_Array.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Compound.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Double.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_End.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Float.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Int.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Int_Array.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_List.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Long.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_Short.class;D:\Git\SaveEditor\build\classes\kotlin\main\codes\mii\SaveEditor\Types\NBT_String.class

View File

@@ -1,2 +1,2 @@
73
60
135
117

View File

@@ -1 +1 @@
<EFBFBD>;<3B>)<29>)<29>)<29>"<22>!<21>!<21><17><1D><15><18><17><17><16><14><14><14><15><15><17><15><10><10><0F><13><12><0E><0E><0F><15><0F>
<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>!<EFBFBD><EFBFBD><EFBFBD>

View File

@@ -3,16 +3,22 @@ package codes.mii.SaveEditor
import codes.mii.SaveEditor.Types.*
import java.io.File
import java.io.IOException
import java.math.BigInteger
import java.nio.ByteBuffer
import java.nio.file.Files
import kotlin.experimental.and
class Converter {
@ExperimentalUnsignedTypes
fun convert(byte: ByteArray): NBT_Compound {
val result = NBT_Compound(0, "")
var result = NBT_Compound(0, "")
val byteSize = byte.size
var readingPosition = 0
try {
result = byteToCompound(byte, readingPosition).first
/*
while (byteSize > readingPosition) {
println(byte[readingPosition])
@@ -27,41 +33,142 @@ class Converter {
readingPosition += nameLength
}
when (nowByte) {
0.toByte() -> { // END
when (nowByte.toInt()) {
0 -> { // END
result.data.add(NBT_End())
readingPosition++
}
1.toByte() -> { // BYTE
1 -> { // BYTE
readingPosition++
result.data.add(NBT_Byte(nameLength.toByte(), name, byte[readingPosition]))
}
2.toByte(), 3.toByte(), 4.toByte() -> {
val n = when(nowByte) {
2, 3, 4 -> { // SHORT, INT, LONG
val n = when (nowByte) {
3.toByte() -> 4
4.toByte() -> 8
else -> 2
}
result.data.add(NBT_Short(nameLength.toByte(), name, readMultiByteHex(byte, readingPosition, n).toInt()))
result.data.add(
NBT_Short(
nameLength.toByte(),
name,
readMultiByteHex(byte, readingPosition, n).toInt()
)
)
readingPosition += n
}
8.toByte() -> { // STRING
readingPosition -= nameLength + 2
val res = byte.toNBT_String(readingPosition)
readingPosition += res.second
result.data.add(res.first)
5 -> { // FLOAT
result.data.add(
NBT_Float(
nameLength.toByte(),
name,
readMultiByteHex(byte, readingPosition, 4).toFloat()
)
)
readingPosition += 4
}
10.toByte() -> { // COMPOUND
6 -> { // DOUBLE
result.data.add(
NBT_Double(
nameLength.toByte(),
name,
0.0
)
)//readMultiByteHex(byte, readingPosition, 8)
readingPosition += 8
}
7 -> { // BYTE_ARRAY
val listLength = readMultiByteHex(byte, readingPosition, 4).toInt()
readingPosition += 4
val byteList: MutableList<Byte> = mutableListOf()
repeat(listLength) {
readingPosition++
byteList.add(byte[readingPosition])
}
result.data.add(NBT_Byte_Array(nameLength.toByte(), name, byteList))
}
8 -> { // STRING
val textLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
val text = byteToString(byte, readingPosition, textLength)
readingPosition += textLength
result.data.add(NBT_String(nameLength.toByte(), name, textLength.toByte(), text.toString()))
}
9 -> { // LIST
readingPosition++
val dataType = byte[readingPosition]
val dataLength = when (dataType.toInt()) {
0 -> 1
1 -> 1
2 -> 2
3 -> 4
4 -> 8
5 -> 4
6 -> 8
10 -> 4
else -> 0
}
val dataSize = readMultiByteHex(byte, readingPosition, 4).toInt()
readingPosition += 4
when (dataType.toInt()) {
7 -> {
repeat(dataSize) {
}
}
8 -> {
repeat(dataSize) {
val textLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
val text = byteToString(byte, readingPosition, textLength)
readingPosition += textLength
println(text)
}
}
11 -> {
repeat(dataSize) {
}
}
}
readingPosition += dataSize * dataLength
result.data.add(NBT_List(nameLength.toByte(), name, mutableListOf()))
}
10 -> { // COMPOUND
result.data.add(NBT_Compound(nameLength.toByte(), name))
}
11 -> { // INT_ARRAY
val listLength = readMultiByteHex(byte, readingPosition, 4).toInt()
readingPosition += 4
val byteList: MutableList<Int> = mutableListOf()
repeat(listLength) {
byteList.add(readMultiByteHex(byte, readingPosition, 4).toInt())
readingPosition += 4
}
result.data.add(NBT_Int_Array(nameLength.toByte(), name, byteList))
}
}
readingPosition++
}
*/
} catch (e: Exception) {
e.printStackTrace()
}
@@ -69,20 +176,357 @@ class Converter {
return result
}
fun byteToByte(byte: ByteArray, position: Int, disableName: Boolean = false): Pair<NBT_Byte, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
readingPosition++
val byteData = NBT_Byte(nameLength.toByte(), name, byte[readingPosition])
return byteData to readingPosition
}
@ExperimentalUnsignedTypes
fun byteToShort(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_Short, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val short = NBT_Short(nameLength.toByte(), name, readMultiByteHex(byte, readingPosition, 2).toInt())
readingPosition += 2
return short to readingPosition
}
fun byteToInt(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_Int, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val int = NBT_Int(nameLength.toByte(), name, readMultiByteHex(byte, readingPosition, 4).toInt())
readingPosition += 4
return int to readingPosition
}
fun byteToLong(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_Long, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val long = NBT_Long(nameLength.toByte(), name, readMultiByteHex(byte, readingPosition, 8))
readingPosition += 8
return long to readingPosition
}
fun byteToFloat(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_Float, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val float = NBT_Float(nameLength.toByte(), name, readMultiByteHex(byte, readingPosition, 4).toFloat())
readingPosition += 4
return float to readingPosition
}
fun byteToDouble(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_Double, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val double = NBT_Double(nameLength.toByte(), name, readMultiByteHex(byte, readingPosition, 8).toDouble())
readingPosition += 8
return double to readingPosition
}
fun byteToByteArray(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_Byte_Array, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val listLength = readMultiByteHex(byte, readingPosition, 4).toInt()
readingPosition += 4
val byteList: MutableList<Byte> = mutableListOf()
repeat(listLength) {
readingPosition++
byteList.add(byte[readingPosition])
}
return NBT_Byte_Array(nameLength.toByte(), name, byteList) to readingPosition
}
fun byteToString(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_String, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val textLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
val text = byteToString(byte, readingPosition, textLength)
readingPosition += textLength
return NBT_String(nameLength.toByte(), name, textLength.toByte(), text) to readingPosition
}
@ExperimentalUnsignedTypes
fun byteToList(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_List, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
readingPosition++
val list = NBT_List(nameLength.toByte(), name, mutableListOf())
val dataType = byte[readingPosition]
val listLength = readMultiByteHex(byte, readingPosition, 4).toInt()
readingPosition += 4
repeat(listLength) {
val (data, pos) = (when(dataType.toInt()) {
1 -> byteToByte(byte, readingPosition, true)
2 -> byteToShort(byte, readingPosition, true)
3 -> byteToInt(byte, readingPosition, true)
4 -> byteToLong(byte, readingPosition, true)
5 -> byteToFloat(byte, readingPosition, true)
6 -> byteToDouble(byte, readingPosition, true)
7 -> byteToByteArray(byte, readingPosition, true)
8 -> byteToString(byte, readingPosition, true)
9 -> byteToList(byte, readingPosition, true)
10 -> byteToCompound(byte, readingPosition, true)
else -> NBT_End() to readingPosition
})
list.data.add(data)
readingPosition = pos
}
return list to readingPosition
}
@ExperimentalUnsignedTypes
fun byteToIntArray(byte: ByteArray, position:Int, disableName: Boolean = false): Pair<NBT_Int_Array, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val listLength = readMultiByteHex(byte, readingPosition, 4).toInt()
readingPosition += 4
val intList: MutableList<Int> = mutableListOf()
repeat(listLength) {
intList.add(readMultiByteHex(byte, readingPosition, 4).toInt())
readingPosition += 4
}
return NBT_Int_Array(nameLength.toByte(), name, intList) to readingPosition
}
@ExperimentalUnsignedTypes
fun byteToCompound(byte: ByteArray, position: Int, disableName: Boolean = false): Pair<NBT_Compound, Int> {
var readingPosition = position
var nameLength = 0
var name = ""
val nowByte = byte[readingPosition]
if (!disableName) {
nameLength = readMultiByteHex(byte, readingPosition, 2).toInt()
readingPosition += 2
name = byteToString(byte, readingPosition, nameLength)
readingPosition += nameLength
}
val compound = NBT_Compound(nameLength.toByte(), name)
readingPosition++
while(byte[readingPosition] != 0.toByte()) {
println("Converting id ${byte[readingPosition]}, position $readingPosition")
when(byte[readingPosition].toInt()) {
1 -> {
val (data, pos) = byteToByte(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
2 -> {
val (data, pos) = byteToShort(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
3 -> {
val (data, pos) = byteToInt(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
4 -> {
val (data, pos) = byteToLong(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
5 -> { // FLOAT
val (data, pos) = byteToFloat(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
6 -> { // DOUBLE
val (data, pos) = byteToDouble(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
7 -> { // BYTE_ARRAY
val (data, pos) = byteToByteArray(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
8 -> { // STRING
val (data, pos) = byteToString(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
9 -> {
val (data, pos) = byteToList(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
10 -> {
val (data, pos) = byteToCompound(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
11 -> {
val (data, pos) = byteToIntArray(byte, readingPosition)
readingPosition = pos
compound.data.add(data)
}
}
readingPosition++
}
return compound to readingPosition
}
@ExperimentalUnsignedTypes
fun readMultiByteHex(byte: ByteArray, position: Int, count: Int): Long {
var readingPosition = position
val multiByteText = StringBuilder()
repeat(count) {
readingPosition++
val n = if (it != 1){
(byte[readingPosition].toUByte()).toString(16)
} else {
(byte[readingPosition]).toString(16)
}
multiByteText.append(if (n.length == 2) { n } else { "0$n" })
}
return multiByteText.toString().toLong(16)
println(byte.copyOfRange(position + 1, position + count + 1).joinToString())
println(BigInteger(byte.copyOfRange(position + 1, position + count + 1)).toString())
return BigInteger(byte.copyOfRange(position + 1, position + count + 1)).toLong()
}
private fun hexToAscii(hexStr: String): String? {

View File

@@ -9,57 +9,88 @@ class SaveEditor {
val converter: Converter = Converter()
fun showNBT(data: Data) {
when(data) {
is NBT_String -> {
println("STRING, Name: ${data.name}, Data: ${data.data}")
}
is NBT_End -> {
println("END")
}
is NBT_Byte -> {
println("BYTE, Name: ${data.name}, Data: ${data.data}")
}
is NBT_Compound -> {
println("COMPOUND, Name: ${data.name}")
data.data.forEach {
showNBT(it)
}
}
is NBT_Int -> {
println("INT, Name: ${data.name}, Data: ${data.data}")
}
is NBT_Short -> {
println("SHORT, Name: ${data.name}, Data: ${data.data}")
}
is NBT_Long -> {
println("LONG, Name: ${data.name}, Data: ${data.data}")
}
is NBT_Float -> {
println("FLOAT, Name: ${data.name}, Data: ${data.data}")
}
is NBT_Double -> {
println("DOUBLE, Name: ${data.name}, Data: ${data.data}")
}
is NBT_Byte_Array -> {
println("BYTE_ARRAY, Name: ${data.name}, Data: ${data.data.joinToString() }}")
}
is NBT_Int_Array -> {
println("BYTE_ARRAY, Name: ${data.name}, Data: ${data.data.joinToString() }")
}
is NBT_List -> {
println("LIST, Name: ${data.name}")
data.data.forEach {
showNBT(it)
}
}
else -> {
println("UNKNOWN, ${data::class.java}")
}
}
}
fun start(args: Array<String>) {
println("NBT Editor.")
if (args.count() >= 1) {
val bytes = converter.convertFile(File(args[0]))
/*
val inp = StringBuilder()
bytes?.forEach {
val n = it.toString(16)
inp.append(if (n.length == 1) { "0$n " } else { "$n " })
}
println("input: $inp")
*/
println("Converting...")
val result = converter.convert(bytes!!)
println("Converted.\n\nresult\n")
result.data.forEach {
when(it) {
is NBT_String -> {
println("STRING, Name: ${it.name}, Data: ${it.data}")
}
is NBT_End -> {
println("END")
}
is NBT_Byte -> {
println("BYTE, Name: ${it.name}, Data: ${it.data}")
}
is NBT_Compound -> {
println("COMPOUND, Name: ${it.name}")
}
is NBT_Int -> {
println("INT, Name: ${it.name}, Data: ${it.data}")
}
is NBT_Short -> {
println("SHORT, Name: ${it.name}, Data: ${it.data}")
}
is NBT_Long -> {
println("LONG, Name: ${it.name}, Data: ${it.data}")
}
else -> {
println("UNKNOWN, ${it::class.java}")
}
}
showNBT(it)
}
}
}

View File

@@ -0,0 +1,5 @@
package codes.mii.SaveEditor.Types
class NBT_Byte_Array(override val nameLength: Byte, override val name: String, val data: MutableList<Byte>) : Data {
override val typeByte: Byte = 7
}

View File

@@ -0,0 +1,5 @@
package codes.mii.SaveEditor.Types
class NBT_Double(override val nameLength: Byte, override val name: String, val data: Double) : Data {
override val typeByte: Byte = 6
}

View File

@@ -0,0 +1,5 @@
package codes.mii.SaveEditor.Types
class NBT_Float(override val nameLength: Byte, override val name: String, val data: Float) : Data {
override val typeByte: Byte = 5
}

View File

@@ -1,5 +1,5 @@
package codes.mii.SaveEditor.Types
class NBT_Int_Array(override val nameLength: Byte, override val name: String) : Data {
class NBT_Int_Array(override val nameLength: Byte, override val name: String, val data: MutableList<Int>) : Data {
override val typeByte: Byte = 11
}

View File

@@ -0,0 +1,5 @@
package codes.mii.SaveEditor.Types
class NBT_List(override val nameLength: Byte, override val name: String, val data: MutableList<Data>) : Data {
override val typeByte: Byte = 9
}