How do deal with blurry/jagged sprites? (CE 2.7.3)

I’m working on a card game that involves a sprite that is made up of multiple child sprites which make up the layers of the card. This allows for modularity when it comes to various attributes. However an issue I’ve been unable to rectify involves this significant drop in quality when I need to scale the cards. See image below:
EDIT: I see the uploaded image itself is blurry, but it still can sort of show what I mean.

As you can see, depending on the size (the smaller the worse it gets) the card’s parts get more jagged and blurry. I don’t mind if text can’t be read when its small enough, but you can clearly see its more than just a size issue, but a quality drop as well.

Most of the card assets are 700x1050 in total size (some may have transparency, but by keeping them all like that, it avoid fiddling with the position in-game. The total window size I’m working with is 1280x800. So I attach all the children and then scale the parent sprite as needed - mostly to the extent of how scaled down it’ll be depending on if the player is hovering over a card, etc.

When I load the images I go by the format

this.load.image(‘image name’, image_file_path, true);

I had read something about the 3rd parameter being used for mipmaps but after re-reading the Phaser CE wiki, I’m not too sure about that. Regardless, it isn’t doing anything one way or another. I’ve also read some things that say for mipmaps to work it has to be power of 2 and others that say it does not so I really don’t know.

My scaling numbers at the moment are 0.11, 0.17, and 0.35 if perhaps the exact scaling number is contributing to the drop in quality and jaggedness.

I’ve also read a bit about having to have multiple versions of the same assets, but besides the fact that increases the storage requirements and the amount of time it’d take to create these alternate versions, I’m not entirely sure how to implement that when, I say, tween the card to expand or shrink.

Any help or guidance would be really appreciated.

1 Like

I think this may be unavoidable. You can try antialias: false in the game config, but generally you may get either unwanted blur (true) or jags (false). Scaling to 0.1, 0.2, 0.4 might look a little better.

If possible, don’t scale the game canvas as well. If you do, try crisp: true in the game config.

For multiple versions, you would combine these in a single texture so you could switch frames. For tweens you would use onUpdateCallback. I think TexturePacker can do something like this but I don’t know the details.

1 Like

I was afraid of that. Could you clarify what you mean by scaling the canvas? In my initial file I have

game = new Phaser.Game(1280, 800, Phaser.AUTO, 'gameContainer');

then in my boot file, inside my init function I have

var gameThis = this;
var theGame = this.game;

//  Unless you specifically know your game needs to support multi-touch I would recommend setting this to 1
this.input.maxPointers = 1;

//  Phaser will automatically pause if the browser tab the game is in loses focus. You can disable that here:
this.stage.disableVisibilityChange = true;

if (this.game.device.desktop)
        {
			
			this.scale.scaleMode = Phaser.ScaleManager.USER_SCALE;
            this.scale.setUserScale(this.game.global.theScaleFactor,this.game.global.theScaleFactor);
                
            // Set the callback for size changes
                theGame.scale.setResizeCallback(function(scale,parentrectangle){

                        // On resize event I calc the new scaleFactor
                        theGame.global.theScaleFactor = theGame.global.theBox.clientHeight / theGame.height;

                        //Applying the same scale to the height and width the proportion is 
                        //maintained 
                        theGame.scale.setUserScale(theGame.global.theScaleFactor, theGame.global.theScaleFactor);
                },this);
			
            //  If you have any desktop specific settings, they can go in here
        }

Is that what you mean? I wanted to have the scaling so that the game looks the same regardless of the user’s screen size or if they shrink the browser window. That’s why you see the grey bars on the sides to account for the end max screen resolution. I’ll try the crisp keyword you mentioned.

I’ll also try those specific scaling values you mentioned. Out of curiosity could you explain your thought process for picking those values?

For the multiple versions are you saying to treat the card versions like frames in a sprite sheet? So for example, I could have three versions of each card layer something like 700x1050, 350x525, and 175x262.5 (or really 263 since no half pixels). Then from the looks of the onUpdateCallback, it checks the progress of the tween so for example if I did a shrink tween, I could check when it’s half done and then switch to the 2nd version and when done or nearly done switch to the 3rd version.

I suppose I’d need to change the interactable area of the cards on a per frame basis so that the transparent area of the layers that are smaller is interactable. I see something about sprite atlas so maybe I can look into that.

Yes, that’s scaling the game canvas. Try without that to see if it makes a difference.

I don’t think the scaling values (0.1, 0.2, 0.4) will make much difference below 50%.

Yes, you would create a multiframe texture — texture atlas in Phaser terms. But test this first to see if it looks any better before you go to all that work.

I realized it’s not really practical to change frames (sizes) during a scale tween. You would change at the end of the tween instead.

I’ll do some testing and see what I can do. Otherwise, in the future I might need to just redesign the board to have less cards on it so that it can be bigger. I’ll need to keep the scaling as its necessary for my use case. As a final question, I’m using 1280x800 for the game area. Do you think the visuals would look better if I used a 1920x1080 game area and scaled that accordingly?

1 Like

You should get some more detail, yes.