Speed Coding 2016 – Q2


13 April 2016, by

Here’s question 2 from our recent speed coding competition. See how quickly you can solve it.

Question 2

iPhone icons are displayed with transparent rounded corners, but these are applied at display time: they’re stored as fully-opaque squares.

Facebook App Icon

I would like to take any 120×120 app icon and apply iPhone-like transparent rounding to it so I can display it on a web page.

For simplicity let’s do this by editing the alpha channels only for the affected pixels i.e. there’s no need to remove no-longer-visible colour information from a now completely transparent pixel. The rounding I’d like to use is the following super-ellipse, which is very close to the rounding used by iOS:

Super-ellipse example

where (0,0) is the centre of the 120×120 image, i.e. so that x/60 has range -1 to +1.

Problem 1 (optional) – A simple approach first

  • read in a 120×120 icon from a PNG or BMP file
  • apply a very simple version of the transparency: make a pixel fully transparent (alpha = 0) if the centre of the pixel falls outside the curve in each quadrant or fully opaque (alpha = 255) if it is inside
  • write the output back to a PNG or BMP and send it to me, along with the program you used.

N.B. I want to use the centre of each pixel for this calculation, not the corner. i.e.

Super-ellipse center explanation

and in the unlikely event a point falls precisely on the curve we’ll count it as inside.

Problem 2 (main problem)

That looks OK, but the edges of the curve could be smoother. The alpha channel has range 0-255 for the alpha channel so let’s try and pick a more precise number for each pixel on the curve. We’ll use a simple form of ray-tracing: divide each pixel into a 16×16 grid and count the number of cells in that grid whose centres fall inside the curve.

This will give us a number from 0 (no cells fall inside => fully transparent) to 256 (all cells fall inside => fully opaque). To clip this to the 0-255 range let’s drop one counted cell, i.e.

alpha = max(cells_inside_curve – 1, 0)

Bonus discussion

If I’m super-obsessive about accuracy of the alpha as the fraction of the pixel inside the curve then even this isn’t enough: why not? Suggest a simple-to-implement approach that would get more accurate corners.

Tags: , ,

Categories: Social, Softwire, Technical

«
»

Leave a Reply

* Mandatory fields


4 − three =

Submit Comment