When people are doing programming exercises, a large number of them make 3D raytracers. While this is a really fun project with exciting results, it also results in people losing interest or typing code that they don’t necessarily understand.
While the end product doesn’t look as nice, I think people should start with 2D ray tracing before moving on to 3D. In this document, I will attempt to go through a simple computer program that can draw 2D shapes.
Outputting an image
To make the implementation simpler, and to follow the raytracer convention, I will be outputting the image in the PPM format.
HEIGHT = 500
WIDTH = 500
print("P3")
print(f"{WIDTH} {HEIGHT}")
print("255")
for x in range(WIDTH):
for y in range(HEIGHT):
r, g, b = (100, 100, 200)
print(f"{r} {g} {b}", end=" ")
print()
Running this code should result in a 500x500 image with a solid blue-ish colour. The whole point of this exercise will be deciding what to put in the RGB colour values in order to produce interesting results.
Drawable objects
We will have a list of shapes that return whether a given (x, y)
coordinate pair falls within it, and what colour it should be. Let’s create that list and replace put the call in our loop.
def solid_red(x, y):
if y > 150 or x > 150:
return (230, 100, 100)
shapes = [
solid_red,
]
shapes.reverse()
# ...
r, g, b = (0, 0, 0)
for drawable in shapes:
temp = drawable(x, y)
if temp:
r, g, b = temp
Running this code should give you an image with a black square on the top left, and a red background.
Drawing a square
def square(x, y, length, colour=(255, 255, 255)):
def inner(ix, iy):
if ix > x and iy > y and ix < x + length and iy < y + length:
return colour
return inner
def checkerboard(x, y):
if (x / 50) + (y / 50) % 2 == 0:
return (100, 100, 100)
shapes = [
checkerboard,
square(50, 50, 100)
]