general mindustry schematic tools
Diffstat (limited to 'pix2msch/core.py')
| -rw-r--r-- | pix2msch/core.py | 158 |
1 files changed, 158 insertions, 0 deletions
diff --git a/pix2msch/core.py b/pix2msch/core.py new file mode 100644 index 0000000..1b48d85 --- /dev/null +++ b/pix2msch/core.py @@ -0,0 +1,158 @@ +# modified from ado1928/pix2msch
+
+try:
+ import struct, zlib, os, base64
+ from PIL import Image
+except Exception as e:
+ print("You're missing a package!")
+ print()
+ print(e)
+ input()
+
+colorarray = [
+ 217, 157, 115,
+ 140, 127, 169,
+ 235, 238, 245,
+ 178, 198, 210,
+ 247, 203, 164,
+ 39, 39, 39,
+ 141, 161, 227,
+ 249, 163, 199,
+ 119, 119, 119,
+ 83, 86, 92,
+ 203,217, 127,
+ 244,186, 110,
+ 243, 233, 121,
+ 116, 87, 206,
+ 255, 121, 94,
+ 255, 170, 95
+ ]
+
+#convert array of ints into a list of tuples, then into a palette
+tuple_array = [tuple(colorarray[t*3:t*3+3]) for t in range(len(colorarray)//3)]
+palette = Image.new("P", (16, 16))
+palette.putpalette(colorarray*16)
+palette.load()
+
+def quantize(img, dither, transparency_treshold):
+ #invalid input checking
+ img = Image.open(img)
+ transparency_treshold = int(transparency_treshold)
+
+ #sphagetti
+ img = img.convert("RGBA") # image
+ imgq = img.convert("RGB") # fully opaque image
+ imgq = imgq._new(imgq.im.convert("P", 1 if dither else 0, palette.im)) #where the actual quantization happens
+
+ imgA = Image.new("RGBA", img.size)
+ pixels = imgA.load()
+ imgq = imgq.convert("RGB")
+
+ for y in range(img.size[1]):
+ for x in range(img.size[0]):
+ if img.getpixel((x, y))[3] >= transparency_treshold: #transparency treshold
+ pixels[x, y] = imgq.getpixel((x, y))
+ else:
+ pixels[x, y] = (0, 0, 0, 0)
+
+ # print("Quantization complete")
+
+ return imgA
+
+
+# imgfile - Path to the image
+# name - Name of the schematic
+# save_location - Save location, i guess
+# dither - Whether to use dithering (True or False, 1 or 0)
+# transparency_treshold - Below which alpha level to stop displaying (0-255), where 0 is show everything and 255 is show only fully opaque
+# mode - Either "path" or "clipboard". Whether to save the schematic as .msch or to copy it into clipboard
+
+def pix2msch(imgfile = None,
+ name = "schematic",
+ save_location = None,
+ dither = True,
+ transparency_treshold = 127,
+ mode = "path"
+ ): #sad face
+
+ tiles = []
+ #input checking
+ if mode == "path" and not(os.path.isdir(os.path.expandvars(save_location))):
+ print("not a path")
+ exit()
+
+ img = quantize(imgfile, dither, transparency_treshold)
+
+ img = img.rotate(-90, expand=True)
+
+ width, height = img.size
+ for y in range(height):
+ for x in range(width):
+ if img.getpixel((x, y))[3] > 1:
+ tiles.append((x, y, tuple_array.index(img.getpixel((x, y))[0:3])))
+
+ # print("Converted pixels into an array of tiles")
+
+ class ByteBuffer(): #so desparate i had to write my own byte buffer
+ def __init__(self, data=bytearray()):
+ self.data = data
+
+ def writeShort(self, int):
+ self.data += struct.pack(">H", int)
+
+ def writeUTF(self, str):
+ self.writeShort(len(str))
+ self.data += bytes(str.encode("UTF"))
+
+ def writeByte(self, int):
+ self.data += struct.pack("b", int)
+
+ def writeInt(self, int):
+ self.data += struct.pack(">i", int)
+
+ #write header and all of that stuff
+ data = ByteBuffer()
+
+ data.writeShort(height)
+ data.writeShort(width)
+
+ data.writeByte(1)
+
+ data.writeUTF("name")
+ data.writeUTF(name)
+
+ data.writeByte(1)
+
+ data.writeUTF("sorter")
+ data.writeInt(len(tiles))
+
+ # print("Header written")
+
+ for tile in tiles: #write tiles
+ data.writeByte(0)
+ data.writeShort(tile[1])
+ data.writeShort(tile[0])
+ data.writeInt(tile[2])
+ data.writeByte(0)
+
+ # print("Tile data written")
+
+
+ if mode == "path":
+ os.chdir(os.path.expandvars(save_location))
+ file = open(name + ".msch", "wb")
+ file.write(b"msch\x00"+zlib.compress(data.data))
+ file.close()
+
+ # print("Successfully saved {0} ".format(name + ".msch"))
+
+ else:
+ try:
+ import pyperclip
+ except ImportError:
+ print("To use this feature, you need to have the pyperclip module")
+ exit()
+ else:
+ pyperclip.copy(base64.standard_b64encode(b"msch\x00"+zlib.compress(data.data)).decode())
+ print("Schematic converted to base64, and put into clipboard")
+
|