display.save and saved resolution

Hi, I’m trying to figure out how to display.save things to the documents directory with a POT (power of two) resolution. I’m having trouble understanding the relationship between a display object’s height/width, contentHeight/contentWidth, the screen’s contentHeight/contentWidth, its pixelWidth/pixelHeight, and the size of a saved .png file that I make with display.save.

For example, in the simulator, when I’m using the iPad Air skin, there appears to be a direct relationship (or a very close one) between an object’s .width and .height property and the resolution that they save at. For example, if I have a display object whose .width and .height properties are 657, then it will save to an image whose resolution is also 657. But something goes wrong when I want to save at a different resolution. Let’s say instead I want to save an image which is 1024 x 1024. So I scale the image by 1024/657 (which is 1.5585), then it seems to me that with this increased scale, my saved image should be 1024. But it’s not – it’s 1028! I’m not sure why. Am I missing a variable?

The problem gets bigger when I’m working in different device skins – when the ratio of the screen is much different, on an iPhoneX skin, for example, if the .height and .width properties of that same display object become 643 (not 657), and the saved image size becomes 1029 x 1029, instead of the desired 1024 pixels. So it seems clear it’s not just the width/height properties.

What should I use, then, to save to the right size? Here is the relevant portion of my config.lua:

application = {     launchPad = false, content =  {          width = 320,         height = 480,          fps = 30,         scale = "letterbox",         audioPlayFrequency = 44100,         antialias = true,         imageSuffix =         {             ["@2x"] = 0.1,         }, }, }

I gave up on finding a solution for this. The formula that came the closest was:

local pixelWidthOfImageThatWillBeSaved = math.round(thingToSave.contentWidth/display.contentScaleX) local pixelHeightOfImageThatWillBeSaved = math.round(thingToSave.contentHeight/display.contentScaleY)

I generally save square objects, so I don’t need to do both dimensions, but that’s how it ALMOST works, so far as I can see.  The problem is that it seems to work on some resolutions, at some devices, but it’s off by somewhere between 0 and 4 pixels depending on how big your desired resolution is. I’ve attached the project I was using to test it, and which exhibits the strange behavior I’m discussing. Try adjusting the “width” and “height” parameters for the compositor in main.lua and you’ll see the problem. Here’s a link to download the project:


Further update: I had yet another stab at this, and found something that really makes it impossible – when you save an image to disk, it is a certain size – but this size is not directly related to the scale. For example, If I saved something whose contentWidth and contentHeight was 100, and the saved resolution was 156, then you’d expect that as I scaled it down gradually, the saved resolution would also go down gradually, to 155, then 154, 153, 152, etc. But it does not – it jumps in patterns, both on device and in the simulator. In my testing, the size of the saved image usually jumped down from 156 pixels to 152, then 149, then 145, then 142. No matter how small the scale was being moved down, these jumps always occurred at the same points – So an object whose contentWidth is between 100 and 98 will always save to have a width of 156, and then an object whose contentWidth is between 98 and 96 will save to have a width of 152, so there’s no way to get to, say, 154, if that’s what you wanted. I suspect that this jump occurs because of some OpenGL algorithm, but who knows?

And thus I am completely giving up!