OSDN Git Service

[changed] SpriteSheetPacker to support texture filters, settings, default filtering...
authornathan.sweet <nathan.sweet@6c4fd544-2939-11df-bb46-9574ba5d0bfa>
Thu, 18 Nov 2010 23:21:06 +0000 (23:21 +0000)
committernathan.sweet <nathan.sweet@6c4fd544-2939-11df-bb46-9574ba5d0bfa>
Thu, 18 Nov 2010 23:21:06 +0000 (23:21 +0000)
extensions/image-packer/src/com/badlogic/gdx/imagepacker/SpriteSheetPacker.java
gdx/src/com/badlogic/gdx/graphics/SpriteSheet.java
gdx/src/com/badlogic/gdx/graphics/Texture.java
tests/gdx-tests-android/assets/data/pack
tests/gdx-tests-jogl/data/pack
tests/gdx-tests-lwjgl/data/pack

index 9e3e55b..3bd59f1 100644 (file)
@@ -14,44 +14,45 @@ import java.util.ArrayList;
 import java.util.Arrays;\r
 import java.util.Collections;\r
 import java.util.Comparator;\r
-import java.util.Iterator;\r
+import java.util.HashMap;\r
+import java.util.LinkedHashMap;\r
 import java.util.regex.Matcher;\r
 import java.util.regex.Pattern;\r
 \r
 import javax.imageio.ImageIO;\r
 \r
-import com.badlogic.gdx.scenes.scene2d.actions.RotateBy;\r
+import com.badlogic.gdx.graphics.Pixmap.Format;\r
+import com.badlogic.gdx.graphics.Texture.TextureFilter;\r
 import com.badlogic.gdx.utils.MathUtils;\r
 \r
 public class SpriteSheetPacker {\r
        static Pattern numberedImagePattern = Pattern.compile(".*?(\\d+)");\r
 \r
-       private ArrayList<Image> images = new ArrayList();\r
+       ArrayList<Image> images = new ArrayList();\r
        FileWriter writer;\r
        final File inputDir;\r
-       private int uncompressedSize, compressedSize;\r
-       final Direction direction;\r
+       int uncompressedSize, compressedSize;\r
        int xPadding, yPadding;\r
-       private final Filter filter;\r
-\r
-       // User configurable settings:\r
-       private int alphaThreshold = 11;\r
-       private boolean pot = true;\r
-       private int padding = 0;\r
-       private boolean debug = false;\r
-       private boolean rotate = true;\r
-       private int maxWidth = 1024;\r
-       private int maxHeight = 1024;\r
-\r
-       public SpriteSheetPacker (File inputDir, Filter filter, Direction direction, File outputDir, File packFile) throws IOException {\r
+       final Filter filter;\r
+       int minWidth, minHeight;\r
+       int maxWidth, maxHeight;\r
+       final Settings settings;\r
+\r
+       public SpriteSheetPacker (Settings settings, File inputDir, Filter filter, File outputDir, File packFile) throws IOException {\r
+               this.settings = settings;\r
                this.inputDir = inputDir;\r
                this.filter = filter;\r
-               this.direction = direction;\r
 \r
-               ArrayList<File> files = getFiles(inputDir, filter, direction);\r
-               if (files == null) return;\r
+               minWidth = filter.width != -1 ? filter.width : settings.minWidth;\r
+               minHeight = filter.height != -1 ? filter.height : settings.minHeight;\r
+               maxWidth = filter.width != -1 ? filter.width : settings.maxWidth;\r
+               maxHeight = filter.height != -1 ? filter.height : settings.maxHeight;\r
+               xPadding = images.size() > 1 && filter.direction != Direction.x && filter.direction != Direction.xy ? settings.padding : 0;\r
+               yPadding = images.size() > 1 && filter.direction != Direction.y && filter.direction != Direction.xy ? settings.padding : 0;\r
 \r
                // Collect and squeeze images.\r
+               File[] files = inputDir.listFiles(filter);\r
+               if (files == null) return;\r
                for (File file : files) {\r
                        if (file.isDirectory()) continue;\r
                        Image image = squeeze(file);\r
@@ -59,13 +60,16 @@ public class SpriteSheetPacker {
                }\r
                if (images.isEmpty()) return;\r
 \r
-               // Print image names.\r
                System.out.println(inputDir);\r
-               if (filter != rgba8888) System.out.println("Format: " + filter.name);\r
-               if (direction != null) System.out.println("Direction: " + direction);\r
-\r
-               xPadding = images.size() > 1 && direction != Direction.x && direction != Direction.xy ? padding : 0;\r
-               yPadding = images.size() > 1 && direction != Direction.y && direction != Direction.xy ? padding : 0;\r
+               if (filter.format != null)\r
+                       System.out.println("Format: " + filter.format);\r
+               else\r
+                       System.out.println("Format: " + settings.defaultFormat + " (default)");\r
+               if (filter.minFilter != null && filter.magFilter != null)\r
+                       System.out.println("Filter: " + filter.minFilter + ", " + filter.magFilter);\r
+               else\r
+                       System.out.println("Filter: " + settings.defaultFilterMin + ", " + settings.defaultFilterMag + " (default)");\r
+               if (filter.direction != Direction.none) System.out.println("Repeat: " + filter.direction);\r
 \r
                outputDir.mkdirs();\r
                String prefix = inputDir.getName();\r
@@ -90,8 +94,19 @@ public class SpriteSheetPacker {
                        outputFile = new File(outputDir, prefix + ++imageNumber + ".png");\r
 \r
                writer.write("\n" + prefix + imageNumber + ".png\n");\r
-               writer.write("repeat: " + direction + "\n");\r
-               writer.write("filter: Linear,Linear\n"); // BOZO\r
+               Format format;\r
+               if (filter.format != null) {\r
+                       writer.write("format: " + filter.format + "\n");\r
+                       format = filter.format;\r
+               } else {\r
+                       writer.write("format: " + settings.defaultFormat + "\n");\r
+                       format = settings.defaultFormat;\r
+               }\r
+               if (filter.minFilter == null || filter.magFilter == null)\r
+                       writer.write("filter: " + settings.defaultFilterMin + "," + settings.defaultFilterMag + "\n");\r
+               else\r
+                       writer.write("filter: " + filter.minFilter + "," + filter.magFilter + "\n");\r
+               writer.write("repeat: " + filter.direction + "\n");\r
 \r
                // Try reasonably hard to pack images into the smallest POT size.\r
                Comparator bestComparator = null;\r
@@ -99,7 +114,7 @@ public class SpriteSheetPacker {
                int bestWidth = 99999, bestHeight = 99999;\r
                int secondBestWidth = 99999, secondBestHeight = 99999;\r
                int bestUsedPixels = 0;\r
-               int width = 64, height = 64;\r
+               int width = minWidth, height = minHeight;\r
                int grownPixels = 0, grownPixels2 = 0;\r
                int i = 0, ii = 0;\r
                while (true) {\r
@@ -124,7 +139,7 @@ public class SpriteSheetPacker {
                                }\r
                        }\r
                        if (bestComparator != null) break;\r
-                       if (pot) {\r
+                       if (settings.pot) {\r
                                // 64,64 then 64,128 then 128,64 then 128,128 then 128,256 etc.\r
                                if (i % 3 == 0) {\r
                                        width *= 2;\r
@@ -174,12 +189,27 @@ public class SpriteSheetPacker {
                }\r
                width = bestWidth;\r
                height = bestHeight;\r
-               if (pot) {\r
+               if (settings.pot) {\r
                        width = MathUtils.nextPowerOfTwo(width);\r
                        height = MathUtils.nextPowerOfTwo(height);\r
                }\r
 \r
-               BufferedImage canvas = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);\r
+               int type;\r
+               switch (format) {\r
+               case RGBA8888:\r
+               case RGBA4444:\r
+                       type = BufferedImage.TYPE_INT_ARGB;\r
+                       break;\r
+               case RGB565:\r
+                       type = BufferedImage.TYPE_INT_RGB;\r
+                       break;\r
+               case Alpha:\r
+                       type = BufferedImage.TYPE_BYTE_GRAY;\r
+                       break;\r
+               default:\r
+                       throw new RuntimeException();\r
+               }\r
+               BufferedImage canvas = new BufferedImage(width, height, type);\r
                insert(canvas, images, bestWidth, bestHeight);\r
                System.out.println("Writing " + canvas.getWidth() + "x" + canvas.getHeight() + ": " + outputFile);\r
                ImageIO.write(canvas, "png", outputFile);\r
@@ -187,21 +217,21 @@ public class SpriteSheetPacker {
        }\r
 \r
        private int insert (BufferedImage canvas, ArrayList<Image> images, int width, int height) throws IOException {\r
-               if (debug && canvas != null) {\r
+               if (settings.debug && canvas != null) {\r
                        Graphics g = canvas.getGraphics();\r
                        g.setColor(Color.green);\r
                        g.drawRect(0, 0, width - 1, height - 1);\r
                }\r
                // Pretend image is larger so padding on right and bottom edges is ignored.\r
-               if (direction != Direction.x && direction != Direction.xy) width += xPadding;\r
-               if (direction != Direction.y && direction != Direction.xy) height += yPadding;\r
+               if (filter.direction != Direction.x && filter.direction != Direction.xy) width += xPadding;\r
+               if (filter.direction != Direction.y && filter.direction != Direction.xy) height += yPadding;\r
                Node root = new Node(0, 0, width, height);\r
                int usedPixels = 0;\r
                for (int i = images.size() - 1; i >= 0; i--) {\r
                        Image image = images.get(i);\r
                        Node node = root.insert(image, canvas, false);\r
                        if (node == null) {\r
-                               if (rotate) node = root.insert(image, canvas, true);\r
+                               if (settings.rotate) node = root.insert(image, canvas, true);\r
                                if (node == null) continue;\r
                        }\r
                        usedPixels += image.getWidth() * image.getHeight();\r
@@ -222,7 +252,7 @@ public class SpriteSheetPacker {
                                        g.rotate(90 * MathUtils.degreesToRadians);\r
                                        g.translate(-node.left, -node.top);\r
                                }\r
-                               if (debug) {\r
+                               if (settings.debug) {\r
                                        g.setColor(Color.magenta);\r
                                        int imageWidth = image.getWidth();\r
                                        int imageHeight = image.getHeight();\r
@@ -239,53 +269,58 @@ public class SpriteSheetPacker {
        private Image squeeze (File file) throws IOException {\r
                BufferedImage source = ImageIO.read(file);\r
                if (source == null) return null;\r
+               if (!filter.accept(source)) return null;\r
                uncompressedSize += source.getWidth() * source.getHeight();\r
                WritableRaster alphaRaster = source.getAlphaRaster();\r
                if (alphaRaster == null) return new Image(file, source, 0, 0, source.getWidth(), source.getHeight());\r
                final byte[] a = new byte[1];\r
                int top = 0;\r
-               outer:\r
-               for (int y = 0; y < source.getHeight(); y++) {\r
-                       for (int x = 0; x < source.getWidth(); x++) {\r
-                               alphaRaster.getDataElements(x, y, a);\r
-                               int alpha = a[0];\r
-                               if (alpha < 0) alpha += 256;\r
-                               if (alpha > alphaThreshold) break outer;\r
+               int bottom = source.getHeight();\r
+               if (filter.direction != Direction.y && filter.direction != Direction.xy) {\r
+                       outer:\r
+                       for (int y = 0; y < source.getHeight(); y++) {\r
+                               for (int x = 0; x < source.getWidth(); x++) {\r
+                                       alphaRaster.getDataElements(x, y, a);\r
+                                       int alpha = a[0];\r
+                                       if (alpha < 0) alpha += 256;\r
+                                       if (alpha > settings.alphaThreshold) break outer;\r
+                               }\r
+                               top++;\r
                        }\r
-                       top++;\r
-               }\r
-               int bottom = source.getHeight() - 1;\r
-               outer:\r
-               for (int y = source.getHeight(); --y >= top;) {\r
-                       for (int x = 0; x < source.getWidth(); x++) {\r
-                               alphaRaster.getDataElements(x, y, a);\r
-                               int alpha = a[0];\r
-                               if (alpha < 0) alpha += 256;\r
-                               if (alpha > alphaThreshold) break outer;\r
+                       outer:\r
+                       for (int y = source.getHeight(); --y >= top;) {\r
+                               for (int x = 0; x < source.getWidth(); x++) {\r
+                                       alphaRaster.getDataElements(x, y, a);\r
+                                       int alpha = a[0];\r
+                                       if (alpha < 0) alpha += 256;\r
+                                       if (alpha > settings.alphaThreshold) break outer;\r
+                               }\r
+                               bottom--;\r
                        }\r
-                       bottom--;\r
                }\r
                int left = 0;\r
-               outer:\r
-               for (int x = 0; x < source.getWidth(); x++) {\r
-                       for (int y = top; y <= bottom; y++) {\r
-                               alphaRaster.getDataElements(x, y, a);\r
-                               int alpha = a[0];\r
-                               if (alpha < 0) alpha += 256;\r
-                               if (alpha > alphaThreshold) break outer;\r
+               int right = source.getWidth();\r
+               if (filter.direction != Direction.x && filter.direction != Direction.xy) {\r
+                       outer:\r
+                       for (int x = 0; x < source.getWidth(); x++) {\r
+                               for (int y = top; y <= bottom; y++) {\r
+                                       alphaRaster.getDataElements(x, y, a);\r
+                                       int alpha = a[0];\r
+                                       if (alpha < 0) alpha += 256;\r
+                                       if (alpha > settings.alphaThreshold) break outer;\r
+                               }\r
+                               left++;\r
                        }\r
-                       left++;\r
-               }\r
-               int right = source.getWidth() - 1;\r
-               outer:\r
-               for (int x = source.getWidth(); --x >= left;) {\r
-                       for (int y = top; y <= bottom; y++) {\r
-                               alphaRaster.getDataElements(x, y, a);\r
-                               int alpha = a[0];\r
-                               if (alpha < 0) alpha += 256;\r
-                               if (alpha > alphaThreshold) break outer;\r
+                       outer:\r
+                       for (int x = source.getWidth(); --x >= left;) {\r
+                               for (int y = top; y <= bottom; y++) {\r
+                                       alphaRaster.getDataElements(x, y, a);\r
+                                       int alpha = a[0];\r
+                                       if (alpha < 0) alpha += 256;\r
+                                       if (alpha > settings.alphaThreshold) break outer;\r
+                               }\r
+                               right--;\r
                        }\r
-                       right--;\r
                }\r
                int newWidth = right - left;\r
                int newHeight = bottom - top;\r
@@ -308,6 +343,9 @@ public class SpriteSheetPacker {
                        this.height = height;\r
                }\r
 \r
+               /**\r
+                * Returns true if the image was inserted. If canvas != null, an entry is written to the pack file.\r
+                */\r
                public Node insert (Image image, BufferedImage canvas, boolean rotate) throws IOException {\r
                        if (this.image != null) return null;\r
                        if (child1 != null) {\r
@@ -350,10 +388,10 @@ public class SpriteSheetPacker {
                        if (imageName.startsWith("/") || imageName.startsWith("\\")) imageName = imageName.substring(1);\r
                        int dotIndex = imageName.lastIndexOf('.');\r
                        if (dotIndex != -1) imageName = imageName.substring(0, dotIndex);\r
-                       if (imageName.endsWith("_4444")) imageName = imageName.substring(0, imageName.length() - 5);\r
-                       if (imageName.endsWith("_565")) imageName = imageName.substring(0, imageName.length() - 4);\r
-                       if (imageName.endsWith("_a")) imageName = imageName.substring(0, imageName.length() - 2);\r
-                       if (imageName.endsWith("_pre")) imageName = imageName.substring(0, imageName.length() - 2);\r
+                       imageName = imageName.replace("_" + filter.format, "");\r
+                       imageName = imageName.replace("_" + filter.direction, "");\r
+                       imageName = imageName.replace("_" + filterToAbbrev.get(filter.minFilter) + "," + filterToAbbrev.get(filter.magFilter),\r
+                               "");\r
 \r
                        writer.write(imageName.replace("\\", "/") + "\n");\r
                        writer.write("  rotate: " + image.rotate + "\n");\r
@@ -364,9 +402,9 @@ public class SpriteSheetPacker {
 \r
                        Matcher matcher = numberedImagePattern.matcher(imageName);\r
                        if (matcher.matches())\r
-                               writer.write("offset: " + Integer.parseInt(matcher.group(1)) + "\n");\r
+                               writer.write("  index: " + Integer.parseInt(matcher.group(1)) + "\n");\r
                        else\r
-                               writer.write("offset: 0\n");\r
+                               writer.write("  index: 0\n");\r
                }\r
        }\r
 \r
@@ -414,101 +452,193 @@ public class SpriteSheetPacker {
                });\r
        }\r
 \r
-       static private Filter rgba8888 = new Filter("RGBA8888") {\r
-               public boolean accept (File dir, String name) {\r
-                       return !name.endsWith("_4444") && !name.endsWith("_565") && !name.endsWith("_a");\r
-               }\r
-       };\r
-       static private Filter rgba4444 = new Filter("RGBA4444") {\r
-               public boolean accept (File dir, String name) {\r
-                       return name.endsWith("_4444");\r
-               }\r
-       };\r
-       static private Filter rgb565 = new Filter("RGB565") {\r
-               public boolean accept (File dir, String name) {\r
-                       return name.endsWith("_565");\r
-               }\r
-       };\r
-       static private Filter alpha = new Filter("Alpha") {\r
-               public boolean accept (File dir, String name) {\r
-                       return name.endsWith("_a");\r
-               }\r
-       };\r
-\r
-       static abstract private class Filter implements FilenameFilter {\r
-               String name;\r
-\r
-               public Filter (String name) {\r
-                       this.name = name;\r
+       static private class Filter implements FilenameFilter {\r
+               Direction direction;\r
+               Format format;\r
+               TextureFilter minFilter;\r
+               TextureFilter magFilter;\r
+               int width = -1;\r
+               int height = -1;\r
+               Settings settings;\r
+\r
+               public Filter (Settings settings, Direction direction, Format format, int width, int height, TextureFilter minFilter,\r
+                       TextureFilter magFilter) {\r
+                       this.settings = settings;\r
+                       this.direction = direction;\r
+                       this.format = format;\r
+                       this.width = width;\r
+                       this.height = height;\r
+                       this.minFilter = minFilter;\r
+                       this.magFilter = magFilter;\r
                }\r
-       }\r
-\r
-       static private enum Direction {\r
-               x, y, xy, none\r
-       }\r
 \r
-       static private ArrayList<File> getFiles (File inputDir, Filter filter, Direction direction) {\r
-               ArrayList<File> files = new ArrayList();\r
-               files.addAll(Arrays.asList(inputDir.listFiles(filter)));\r
-               for (Iterator<File> iter = files.iterator(); iter.hasNext();) {\r
-                       File file = iter.next();\r
-                       String name = file.getName();\r
+               public boolean accept (File dir, String name) {\r
                        switch (direction) {\r
                        case none:\r
-                               if (name.contains("_x") || name.contains("_y")) iter.remove();\r
+                               if (name.contains("_x") || name.contains("_y")) return false;\r
                                break;\r
                        case x:\r
-                               if (!name.contains("_x") || name.contains("_xy")) iter.remove();\r
+                               if (!name.contains("_x") || name.contains("_xy")) return false;\r
                                break;\r
                        case y:\r
-                               if (!name.contains("_y")) iter.remove();\r
+                               if (!name.contains("_y") || name.contains("_xy")) return false;\r
                                break;\r
                        case xy:\r
-                               if (!name.contains("_xy")) iter.remove();\r
+                               if (!name.contains("_xy")) return false;\r
                                break;\r
                        }\r
+\r
+                       if (format != null) {\r
+                               if (!name.contains("_" + formatToAbbrev.get(format))) return false;\r
+                       } else {\r
+                               // Return if name has a format.\r
+                               for (String f : formatToAbbrev.values())\r
+                                       if (name.contains("_" + f)) return false;\r
+                       }\r
+\r
+                       if (minFilter != null && magFilter != null) {\r
+                               if (!name.contains("_" + filterToAbbrev.get(minFilter) + "," + filterToAbbrev.get(magFilter) + ".")\r
+                                       && !name.contains("_" + filterToAbbrev.get(minFilter) + "," + filterToAbbrev.get(magFilter) + "_")) return false;\r
+                       } else {\r
+                               // Return if the name has a filter.\r
+                               for (String f : filterToAbbrev.values()) {\r
+                                       String tag = "_" + f + ",";\r
+                                       int tagIndex = name.indexOf(tag);\r
+                                       if (tagIndex != -1) {\r
+                                               String rest = name.substring(tagIndex + tag.length());\r
+                                               for (String f2 : filterToAbbrev.values())\r
+                                                       if (rest.startsWith(f2 + ".") || rest.startsWith(f2 + "_")) return false;\r
+                                       }\r
+                               }\r
+                       }\r
+\r
+                       return true;\r
                }\r
-               return files;\r
+\r
+               public boolean accept (BufferedImage image) {\r
+                       if (width != -1 && image.getWidth() != width) return false;\r
+                       if (height != -1 && image.getHeight() != height) return false;\r
+                       return true;\r
+               }\r
+       }\r
+\r
+       static private enum Direction {\r
+               x, y, xy, none\r
+       }\r
+\r
+       static final HashMap<TextureFilter, String> filterToAbbrev = new HashMap();\r
+       static {\r
+               filterToAbbrev.put(TextureFilter.Linear, "l");\r
+               filterToAbbrev.put(TextureFilter.Nearest, "n");\r
+               filterToAbbrev.put(TextureFilter.MipMap, "m");\r
+               filterToAbbrev.put(TextureFilter.MipMapLinearLinear, "mll");\r
+               filterToAbbrev.put(TextureFilter.MipMapLinearNearest, "mln");\r
+               filterToAbbrev.put(TextureFilter.MipMapNearestLinear, "mnl");\r
+               filterToAbbrev.put(TextureFilter.MipMapNearestNearest, "mnn");\r
        }\r
 \r
-       static private void process (File inputDir, File outputDir, File packFile) throws Exception {\r
+       static final HashMap<Format, String> formatToAbbrev = new HashMap();\r
+       static {\r
+               formatToAbbrev.put(Format.RGBA8888, "8888");\r
+               formatToAbbrev.put(Format.RGBA4444, "4444");\r
+               formatToAbbrev.put(Format.RGB565, "565");\r
+               formatToAbbrev.put(Format.Alpha, "a");\r
+       }\r
+\r
+       static class Settings {\r
+               public Format defaultFormat = Format.RGBA8888;\r
+               public TextureFilter defaultFilterMin = TextureFilter.Linear;\r
+               public TextureFilter defaultFilterMag = TextureFilter.Linear;\r
+               public int alphaThreshold = 9;\r
+               public boolean pot = true;\r
+               public int padding = 0;\r
+               public boolean debug = false;\r
+               public boolean rotate = true;\r
+               public int minWidth = 64;\r
+               public int minHeight = 64;\r
+               public int maxWidth = 1024;\r
+               public int maxHeight = 1024;\r
+       }\r
+\r
+       static private void process (Settings settings, File inputDir, File outputDir, File packFile) throws Exception {\r
+               // Clean existing page images.\r
                if (outputDir.exists()) {\r
                        String prefix = inputDir.getName();\r
                        for (File file : outputDir.listFiles())\r
                                if (file.getName().startsWith(prefix)) file.delete();\r
                }\r
 \r
-               Direction[] directions = Direction.values();\r
-               for (int i = 0; i < directions.length; i++) {\r
-                       Direction direction = directions[i];\r
-                       new SpriteSheetPacker(inputDir, rgba8888, direction, outputDir, packFile);\r
-                       new SpriteSheetPacker(inputDir, rgba4444, direction, outputDir, packFile);\r
-                       new SpriteSheetPacker(inputDir, rgb565, direction, outputDir, packFile);\r
-                       new SpriteSheetPacker(inputDir, alpha, direction, outputDir, packFile);\r
+               // Just check all combinations, because we are extremely lazy.\r
+               ArrayList<TextureFilter> filters = new ArrayList();\r
+               filters.add(null);\r
+               filters.addAll(Arrays.asList(TextureFilter.values()));\r
+               ArrayList<Format> formats = new ArrayList();\r
+               formats.add(null);\r
+               formats.addAll(Arrays.asList(Format.values()));\r
+               for (int i = 0, n = formats.size(); i < n; i++) {\r
+                       Format format = formats.get(i);\r
+                       for (int ii = 0, nn = filters.size(); ii < nn; ii++) {\r
+                               TextureFilter min = filters.get(ii);\r
+                               for (int iii = ii; iii < nn; iii++) {\r
+                                       TextureFilter mag = filters.get(iii);\r
+                                       if ((min == null && mag != null) || (min != null && mag == null)) continue;\r
+\r
+                                       Filter filter = new Filter(settings, Direction.none, format, -1, -1, min, mag);\r
+                                       new SpriteSheetPacker(settings, inputDir, filter, outputDir, packFile);\r
+\r
+                                       for (int width = settings.minWidth; width <= settings.maxWidth; width <<= 1) {\r
+                                               filter = new Filter(settings, Direction.x, format, width, -1, min, mag);\r
+                                               new SpriteSheetPacker(settings, inputDir, filter, outputDir, packFile);\r
+                                       }\r
+\r
+                                       for (int height = settings.minHeight; height <= settings.maxHeight; height <<= 1) {\r
+                                               filter = new Filter(settings, Direction.y, format, -1, height, min, mag);\r
+                                               new SpriteSheetPacker(settings, inputDir, filter, outputDir, packFile);\r
+                                       }\r
+\r
+                                       for (int width = settings.minWidth; width <= settings.maxWidth; width <<= 1) {\r
+                                               for (int height = settings.minHeight; height <= settings.maxHeight; height <<= 1) {\r
+                                                       filter = new Filter(settings, Direction.xy, format, width, height, min, mag);\r
+                                                       new SpriteSheetPacker(settings, inputDir, filter, outputDir, packFile);\r
+                                               }\r
+                                       }\r
+                               }\r
+                       }\r
                }\r
+\r
+               // Process subdirectories.\r
                File[] files = inputDir.listFiles();\r
                if (files == null) return;\r
                for (File file : files)\r
-                       if (file.isDirectory()) process(file, new File(outputDir, file.getName()), packFile);\r
+                       if (file.isDirectory()) process(settings, file, new File(outputDir, file.getName()), packFile);\r
        }\r
 \r
-       static public void process (String inputDir, String outputDir) throws Exception {\r
-               File input = new File(inputDir);\r
-               if (!input.isDirectory()) {\r
-                       System.out.println("Not a directory: " + input);\r
+       static public void process (Settings settings, String input, String output) throws Exception {\r
+               File inputDir = new File(input);\r
+               File outputDir = new File(output);\r
+\r
+               if (!inputDir.isDirectory()) {\r
+                       System.out.println("Not a directory: " + inputDir);\r
                        return;\r
                }\r
+\r
+               // Clean pack file.\r
                File packFile = new File(outputDir, "pack");\r
                packFile.delete();\r
-               process(new File(inputDir), new File(outputDir), packFile);\r
+\r
+               process(settings, inputDir, outputDir, packFile);\r
        }\r
 \r
        public static void main (String[] args) throws Exception {\r
+               String input, output;\r
                if (args.length != 2) {\r
                        System.out.println("Usage: INPUTDIR OUTPUTDIR");\r
                        return;\r
                }\r
-               process(args[0], args[1]);\r
-               // process("c:/temp/pack-in", "c:/temp/pack-out");\r
+               input = args[0];\r
+               output = args[1];\r
+               // input = "c:/temp/pack-in";\r
+               // output = "c:/temp/pack-out";\r
+               process(new Settings(), input, output);\r
        }\r
 }\r
index 447ebad..5b2175f 100644 (file)
@@ -11,6 +11,7 @@ import java.util.PriorityQueue;
 \r
 import com.badlogic.gdx.Gdx;\r
 import com.badlogic.gdx.files.FileHandle;\r
+import com.badlogic.gdx.graphics.Pixmap.Format;\r
 import com.badlogic.gdx.graphics.Texture.TextureFilter;\r
 import com.badlogic.gdx.graphics.Texture.TextureWrap;\r
 import com.badlogic.gdx.utils.GdxRuntimeException;\r
@@ -43,6 +44,13 @@ public class SpriteSheet {
                                else if (pageImage == null) {\r
                                        FileHandle file = imagesDir.child(line);\r
 \r
+                                       // FIXME - Actually load in the requested format.\r
+                                       Format format = Format.valueOf(readValue(reader));\r
+\r
+                                       readTuple(reader);\r
+                                       TextureFilter min = TextureFilter.valueOf(tuple[0]);\r
+                                       TextureFilter max = TextureFilter.valueOf(tuple[1]);\r
+\r
                                        String direction = readValue(reader);\r
                                        TextureWrap repeatX = ClampToEdge;\r
                                        TextureWrap repeatY = ClampToEdge;\r
@@ -55,10 +63,6 @@ public class SpriteSheet {
                                                repeatY = Repeat;\r
                                        }\r
 \r
-                                       readTuple(reader);\r
-                                       TextureFilter min = TextureFilter.valueOf(tuple[0]);\r
-                                       TextureFilter max = TextureFilter.valueOf(tuple[1]);\r
-\r
                                        Texture texture = Gdx.graphics.newTexture(file, min, max, repeatX, repeatY);\r
                                        textures.add(texture);\r
 \r
index b87a34e..31324eb 100644 (file)
@@ -56,7 +56,7 @@ import com.badlogic.gdx.Graphics;
  */\r
 public interface Texture {\r
        /**\r
-        * Texture filter enum featuring the 3 most used filters.\r
+        * Texture filter enum\r
         * \r
         * @author badlogicgames@gmail.com\r
         * \r
index cf40bab..860a8f4 100644 (file)
@@ -1,43 +1,26 @@
 
-data1.png
-none
-badlogic
-0
-0
-256
-256
-0
-0
-256
-256
-0
-particle-fire
-256
-0
-127
-122
-0
-0
-128
-128
-0
+pack-in1.png
+format: RGBA8888
+filter: Linear,Linear
+repeat: none
+badlogicslice
+  rotate: true
+  xy: 0, 0
+  size: 41, 300
+  orig: 41, 300
+  offset: 0, 0
+  index: 0
 particle-star
-383
-0
-63
-63
-0
-0
-64
-64
-0
+  rotate: false
+  xy: 0, 41
+  size: 64, 64
+  orig: 64, 64
+  offset: 0, 0
+  index: 0
 badlogicsmall
-383
-63
-32
-32
-0
-0
-32
-32
-0
+  rotate: false
+  xy: 300, 0
+  size: 32, 32
+  orig: 32, 32
+  offset: 0, 0
+  index: 0
index cf40bab..860a8f4 100644 (file)
@@ -1,43 +1,26 @@
 
-data1.png
-none
-badlogic
-0
-0
-256
-256
-0
-0
-256
-256
-0
-particle-fire
-256
-0
-127
-122
-0
-0
-128
-128
-0
+pack-in1.png
+format: RGBA8888
+filter: Linear,Linear
+repeat: none
+badlogicslice
+  rotate: true
+  xy: 0, 0
+  size: 41, 300
+  orig: 41, 300
+  offset: 0, 0
+  index: 0
 particle-star
-383
-0
-63
-63
-0
-0
-64
-64
-0
+  rotate: false
+  xy: 0, 41
+  size: 64, 64
+  orig: 64, 64
+  offset: 0, 0
+  index: 0
 badlogicsmall
-383
-63
-32
-32
-0
-0
-32
-32
-0
+  rotate: false
+  xy: 300, 0
+  size: 32, 32
+  orig: 32, 32
+  offset: 0, 0
+  index: 0
index d9c717a..860a8f4 100644 (file)
@@ -1,25 +1,26 @@
 
-pack1.png
-  repeat: none
-  filter: Linear,Linear
+pack-in1.png
+format: RGBA8888
+filter: Linear,Linear
+repeat: none
 badlogicslice
   rotate: true
   xy: 0, 0
   size: 41, 300
   orig: 41, 300
   offset: 0, 0
-  offset: 0
+  index: 0
 particle-star
   rotate: false
   xy: 0, 41
-  size: 63, 63
+  size: 64, 64
   orig: 64, 64
   offset: 0, 0
-  offset: 0
+  index: 0
 badlogicsmall
   rotate: false
   xy: 300, 0
   size: 32, 32
   orig: 32, 32
   offset: 0, 0
-  offset: 0
+  index: 0