Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import java.io.DataInput;
- import java.io.DataInputStream;
- import java.io.FileInputStream;
- import java.io.IOException;
- import java.math.BigInteger;
- import java.nio.ByteBuffer;
- import java.util.HexFormat;
- import java.util.Map;
- public class SBPrinter {
- public static void main (String[] args) {
- if (args.length < 1)
- System.out.println("Usage: java sbprinter [path]");
- else
- try {
- printSB(new DataInputStream(new FileInputStream(args[0])));
- } catch (IOException ioe) {
- System.out.println("crashed :(");
- }
- }
- public static void printSB (DataInput s) throws IOException {
- s.skipBytes(14);
- printObjectTable(s, "info");
- printObjectTable(s, "contents");
- }
- public static void printObjectTable (DataInput s, String name) throws IOException {
- System.out.printf("Object Table: %Ts\n", name);
- s.skipBytes(10);
- int len = s.readInt();
- for (int i = 0; i < len; i++) {
- int type = s.readUnsignedByte();
- if (type < 9 || type == 99) {
- System.out.printf(" --invalid object type: %Tx\n", Integer.valueOf(type));
- throw new RuntimeException();
- }
- if (type < 99)
- printFixedFormat(s, type, i);
- else
- printUserClass(s, type, i);
- }
- }
- public static void printFixedFormat (DataInput s, int type, int index) throws IOException {
- System.out.printf(" --Object %Td: ", Integer.valueOf(index));
- switch (type) {
- case 9:
- byte[] str9 = new byte[s.readInt()];
- s.readFully(str9);
- System.out.printf("String (%Ts)\n", new String(str9));
- break;
- case 10:
- byte[] str10 = new byte[s.readInt()];
- s.readFully(str10);
- System.out.printf("Symbol (%Ts)\n", new String(str10));
- break;
- case 11:
- byte[] str11 = new byte[s.readInt()];
- s.readFully(str11);
- System.out.printf("ByteArray\n --%Ts", toHexString(str11));
- break;
- case 12:
- short[] str12 = new short[s.readInt()];
- for (int i = 0; i < str12.length; i++)
- str12[i] = s.readShort();
- System.out.printf("SoundBuffer\n --%Ts", toHexString(str12));
- break;
- case 13:
- int[] str13 = new int[s.readInt()];
- for (int i = 0; i < str13.length; i++)
- str13[i] = s.readInt();
- System.out.printf("Bitmap\n --%Ts", toHexString(str13));
- break;
- case 14:
- byte[] str14 = new byte[s.readInt()];
- s.readFully(str14);
- System.out.printf("UTF8 (%Ts)\n", new String(str14));
- break;
- case 20:
- printArray(s, "Array");
- break;
- case 21:
- printArray(s, "OrderedCollection");
- break;
- case 22:
- printArray(s, "Set");
- break;
- case 23:
- printArray(s, "IdentitySet");
- break;
- case 24:
- printMap(s, "Dictionary");
- break;
- case 25:
- printMap(s, "IdentityDictionary");
- break;
- case 30:
- int scolor = s.readInt();
- HexFormat f31 = HexFormat.of();
- String str31 = "#" + f31.toHexDigits((short) ((scolor & 0x3FF00000) >> 20)) + f31.toHexDigits((short) ((scolor & 0x000FFC00) >> 10)) + f31.toHexDigits((short) (scolor & 0x000003FF));
- System.out.printf("Color (%Ts)\n", new String(str31));
- break;
- case 31:
- int tcolor = s.readInt();
- HexFormat f32 = HexFormat.of();
- String str32 = "#" + f32.toHexDigits((short) ((tcolor & 0x3FF00000) >> 20)) + f32.toHexDigits((short) ((tcolor & 0x000FFC00) >> 10)) + f32.toHexDigits((short) (tcolor & 0x000003FF)) + f32.toHexDigits((short) s.readByte());
- System.out.printf("TranslucentColor (%Ts)\n", new String(str32));
- break;
- case 32:
- System.out.printf("Point\n --x: ");
- printInline(s);
- System.out.printf("\n --y: ");
- printInline(s);
- System.out.println();
- break;
- case 33:
- System.out.printf("Rectangle\n --x: ");
- printInline(s);
- System.out.printf("\n --y: ");
- printInline(s);
- System.out.printf("\n --width (?): ");
- printInline(s);
- System.out.printf("\n --height (?): ");
- printInline(s);
- System.out.println();
- break;
- case 34:
- System.out.printf("Form\n --width: ");
- printInline(s);
- System.out.printf("\n --height: ");
- printInline(s);
- System.out.printf("\n --depth (?): ");
- printInline(s);
- System.out.printf("\n --privateOffset (?): ");
- printInline(s);
- System.out.printf("\n --bits: ");
- printInline(s);
- System.out.println();
- break;
- case 35:
- System.out.printf("ColorForm\n --width: ");
- printInline(s);
- System.out.printf("\n --height: ");
- printInline(s);
- System.out.printf("\n --depth (?): ");
- printInline(s);
- System.out.printf("\n --privateOffset (?): ");
- printInline(s);
- System.out.printf("\n --bits: ");
- printInline(s);
- System.out.printf("\n --colorMap (?): ");
- printInline(s);
- System.out.println();
- break;
- default:
- System.out.printf("invalid type");
- throw new RuntimeException();
- }
- }
- public static String toHexString (byte[] v) {
- if (v == null) return "null";
- StringBuilder b = new StringBuilder("[");
- HexFormat f = HexFormat.of();
- for (int i = 0; i < v.length; ++i) {
- if (i > 0) b.append(", ");
- b.append("0x");
- b.append(f.toHexDigits(v[i]));
- }
- b.append("]");
- return b.toString();
- }
- public static String toHexString (short[] v) {
- if (v == null) return "null";
- StringBuilder b = new StringBuilder("[");
- HexFormat f = HexFormat.of();
- for (int i = 0; i < v.length; ++i) {
- if (i > 0) b.append(", ");
- b.append("0x");
- b.append(f.toHexDigits(v[i]));
- }
- b.append("]");
- return b.toString();
- }
- public static String toHexString (int[] v) {
- if (v == null) return "null";
- StringBuilder b = new StringBuilder("[");
- HexFormat f = HexFormat.of();
- for (int i = 0; i < v.length; ++i) {
- if (i > 0) b.append(", ");
- b.append("0x");
- b.append(f.toHexDigits(v[i]));
- }
- b.append("]");
- return b.toString();
- }
- public static void printArray (DataInput s, String name) throws IOException {
- int len = s.readInt();
- if (len == 0) {
- System.out.printf("%Ts []\n", name);
- return;
- }
- System.out.printf("%Ts [", name);
- for (int i = 0; i < len; i++) {
- System.out.printf("\n ");
- printInline(s);
- }
- System.out.printf("\n ]\n");
- }
- public static void printMap (DataInput s, String name) throws IOException {
- int len = s.readInt();
- if (len == 0) {
- System.out.printf("%Ts {}\n", name);
- return;
- }
- System.out.printf("%Ts {", name);
- for (int i = 0; i < len; i++) {
- System.out.printf("\n ");
- printInline(s);
- System.out.printf(": ");
- printInline(s);
- }
- System.out.printf("\n }\n");
- }
- public static void printUserClass (DataInput s, int type, int index) throws IOException {
- System.out.printf(" --Object %1$Td: %2$Ts\n", Integer.valueOf(index), getUserClassName(type));
- System.out.printf(" --version: %Td\n", Integer.valueOf(s.readUnsignedByte()));
- int length = s.readUnsignedByte();
- System.out.printf(" --length: %Td", Integer.valueOf(length));
- String[] fieldNames = getUserClassFields(type);
- for (int i = 0; i < length; i++) {
- String fieldName = "$$" + i;
- if (i < fieldNames.length) fieldName = fieldNames[i];
- System.out.printf("\n --field %Ts: ", Integer.valueOf(i));
- printInline(s);
- }
- System.out.println();
- }
- public static void printInline (DataInput s) throws IOException {
- int type = s.readUnsignedByte();
- switch (type) {
- case 1:
- System.out.printf("nil");
- break;
- case 2:
- System.out.printf("true");
- break;
- case 3:
- System.out.printf("false");
- break;
- case 4:
- System.out.printf("SmallInteger (%Td)", Integer.valueOf(s.readInt()));
- break;
- case 5:
- System.out.printf("SmallInteger16 (%Td)", Integer.valueOf(s.readShort()));
- break;
- case 6:
- byte[] array6 = new byte[s.readUnsignedShort()];
- s.readFully(array6);
- System.out.printf("LargePositiveInteger (%Ts)", new BigInteger(1, array6));
- break;
- case 7:
- byte[] array7 = new byte[s.readUnsignedShort()];
- s.readFully(array7);
- System.out.printf("LargePositiveInteger (%Ts)", new BigInteger(-1, array7));
- break;
- case 8:
- System.out.printf("Float (%Tf)", Double.valueOf(s.readDouble()));
- break;
- case 99:
- byte[] array99 = new byte[s.readUnsignedShort()];
- s.readFully(array99);
- System.out.printf("Object Reference @%Td", ByteBuffer.allocate(4).put((byte) 0).put(array99).getInt());
- break;
- default:
- System.out.printf("illegal inline type (%Td)", type);
- throw new RuntimeException();
- }
- }
- public static final Map.Entry<String, String[]>[] USER_CLASS_FORMATS = new Map.Entry[] {
- Map.<String, String[]>entry("Morph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("BorderedMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor" }),
- Map.<String, String[]>entry("RectangleMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor" }),
- Map.<String, String[]>entry("EllipseMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor" }),
- Map.<String, String[]>entry("AlignmentMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor",
- "orientation", "centering", "hResizing", "vResizing", "inset" }),
- Map.<String, String[]>entry("StringMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "font with size", "emphasis",
- "contents" }),
- Map.<String, String[]>entry("UpdatingStringMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "font with size", "emphasis",
- "contents" }),
- Map.<String, String[]>entry("SimpleSliderMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor", "slider",
- "value", "setValueSelector", "sliderShadow", "sliderColor", "descending", "model", "target",
- "actionSelector", "arguments", "actWhen" }),
- Map.<String, String[]>entry("SimpleButtonMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor",
- "target", "actionSelector", "arguments", "actWhen" }),
- Map.<String, String[]>entry("SampledSound", new String[] {
- "envelopes", "scaledVol", "initialCount", "samples", "originalSaplingRate", "samplesSize",
- "scaledIncrement", "scaledInitialIndex" }),
- Map.<String, String[]>entry("ImageMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "form", "transparency" }),
- Map.<String, String[]>entry("SketchMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "originalForm", "rotationCenter",
- "rotationDegrees", "rotationStyle", "scalePoint", "offsetWhenRotated" }),
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- Map.<String, String[]>entry("SensorBoardMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("ScratchSpriteMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "objName", "vars", "blocksBin",
- "isClone", "media", "costume", "visibility", "scalePoint", "rotationDegrees", "rotationStyle",
- "volume", "tempoBPM", "draggable", "sceneStates", "lists" }),
- Map.<String, String[]>entry("ScratchStageMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "objName", "vars", "blocksBin",
- "isClone", "media", "costume", "zoom", "hPan", "vPan", "obsoleteSavedState", "sprites", "volume",
- "tempoBPM", "sceneStates", "lists" }),
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- null,
- Map.<String, String[]>entry("ChoiceArgMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("ColorArgMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("ExpressionArgMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- null,
- null,
- Map.<String, String[]>entry("SpriteArgMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- null,
- Map.<String, String[]>entry("BlockMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "isSpecialForm", "oldColor" }),
- Map.<String, String[]>entry("CommandBlockMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "isSpecialForm", "oldColor",
- "commandSpec", "argMorphs", "titleMorph", "reciever", "selector", "isReporter", "isTimed",
- "wantsName", "wantsPossesion" }),
- Map.<String, String[]>entry("CBlockMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- null,
- Map.<String, String[]>entry("HatBlockMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- null,
- Map.<String, String[]>entry("ScratchScriptsMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor" }),
- Map.<String, String[]>entry("ScratchSliderMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("AlignmentMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor",
- "orientation", "centering", "hResizing", "vResizing", "inset", "titleMorph", "readout", "readoutFrame",
- "scratchSlider", "watcher", "isSpriteSpecific", "$$19", "sliderMin", "sliderMax", "isLarge" }),
- null,
- Map.<String, String[]>entry("SetterBlockMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("EventHatMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- null,
- Map.<String, String[]>entry("VariableBlockMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "isSpecialForm", "oldColor",
- "commandSpec", "argMorphs", "titleMorph", "reciever", "selector", "isReporter", "isTimed",
- "wantsName", "wantsPossesion", "isBoolean" }),
- null,
- Map.<String, String[]>entry("ImageMedia", new String[] {
- "mediaName", "form", "rotationCenter", "textBox", "jpegBytes", "compositeForm" }),
- Map.<String, String[]>entry("MovieMedia", new String[] {
- "mediaName", "fileName", "fade", "fadeColor", "zoom", "hPan", "vPan", "msecsPerFrame", "currentFrame",
- "moviePlaying" }),
- Map.<String, String[]>entry("SoundMedia", new String[] {
- "mediaName", "originalSound", "volume", "balance", "compressedSampleRate", "compressedBitsPerSample",
- "compressedData" }),
- Map.<String, String[]>entry("KeyEventHatMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("BooleanArgMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("EventTitleMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("MouseClickEventHatMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("ExpressionArgMorphWithMenu", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("ReporterBlockMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("MultilineStringMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" }),
- Map.<String, String[]>entry("ToggleButton", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor",
- "target", "actionSelector", "arguments", "actWhen" }),
- Map.<String, String[]>entry("WatcherReadoutFrameMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor" }),
- Map.<String, String[]>entry("WatcherSliderMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor", "slider",
- "value", "setValueSelector", "sliderShadow", "sliderColor", "descending", "model", "target",
- "actionSelector", "arguments", "actWhen" }),
- Map.<String, String[]>entry("ScratchListMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties", "borderWidth", "borderColor",
- "listName", "cellMorphs", "target" }),
- Map.<String, String[]>entry("ScrollingStringMorph", new String[] {
- "bounds", "owner", "submorphs", "color", "flags", "properties" })
- };
- public static String getUserClassName (int type) {
- if (type < 100 || type > 176) return "UserClassType" + type;
- return USER_CLASS_FORMATS[type - 100].getKey();
- }
- public static String[] getUserClassFields (int type) {
- if (type < 100 || type > 176) return new String[0];
- return USER_CLASS_FORMATS[type - 100].getValue();
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment