A Quick Fix for Fuzzy SKShapeNode Lines

February 16, 2015

I’ve been using Apple’s SpriteKit for the train game. It’s gone fairly well, except there have been a few unpleasant surprises with SKShapeNode, which strokes/fills a bezier path. The internet is filled with folks complaining about buggy behavior from it and I’ve definitely had more than a few moments where I daydreamed about dusting off my OpenGL chops.

This is an A/B screenshot of an issue I was running into. At left is before, right is after:

These are SKShapeNodes with paths for the track segments, which are 2pt wide, stroked, and, most importantly scaled up several times (zoomed in on the map). The issue of course is the blurry/fuzzy line rendering.

The ‘fix’ was startlingly simple: setting antialiased = false makes your blurry lines crystal clear when scaled up. This isn’t at all what I was expecting (antialiasing off == stair-stepping, pixelated lines in my mind).

My guess is that this is an optimization. For SKShapeNode, antialiased means it will be drawn on a texture at unscaled resolution and that texture is then scaled as needed. With antialiased off, the curve drawing occurs at the current resolution. This is only reasoning off of the visual results. I don’t notice any significant difference in CPU overhead when antialiased is off.

It’s also curious because SpriteKit seems to perpetually re-render SKShapeNodes whether they have changed or not. At some point I will likely end up writing code to render them to textures, or just moving over to OpenGL and rendering the tracks myself.

At this point in development the visuals are secondary, however. I ran an experiment with SKShapeNode’s strokeTexture and aside from some strange rendering artifacts (texture scaled unevenly), the result was much too busy. For now I rather like this abstract appearance for the tracks.