Edge Detection & Edge AA

In order to apply edge-detect antialiasing, an efficient edge detection algorithm needed to be added after completion of the initial image. We extended our Image class (which receives samples from the main loop) to add a method to return a std::vector<int> of indices of pixels testing positive as edge pixels.

The specific algorithm chosen applied the Sobel gradient operator to every pixel excluding the border pixels of the frame. The mathematical evaluation of the Sobel operator for a pixel at coordinates (x,y) is as follows:

 S_x(x,y) = I_{(x-1,y+1)} + 2I_{(x,y+1)} + I_{(x+1,y+1)} - I_{(x-1,y-1)} - 2I_{(x,y-1)} - I_{(x+1,y-1)}  S_y(x,y) = I_{(x+1,y-1)} + 2I_{(x+1,y)} + I_{(x+1,y+1)} - I_{(x-1,y-1)} - 2I_{(x-1,y)} - I_{(x-1,y+1)}  S(x,y) = \sqrt{S^2_x(x,y) + S^2_y(x,y)}

Here, the value of each pixel is represented by a scalar intensity, evaluated as the length of the color 3-vector in a (0,1) color space.

The qualification of an edge pixel is based on the evaluation of the Sobel operator at that index. If that pixel’s Sobel value exceeds a certain threshold, its index is returned with the other edge indices in a vector by the postprocessing method of the Image object. However, setting this parameter introduces a “magic number” into the system; therefore, we decided to add a new command to the input file.

sobel threshold aa

The first argument to this command is a floating-point threshold for edge detection. Any pixel whose Sobel value is greater than this threshold have its index included in the vector of edge pixel indices.

The second argument describes the degree of antialiasing to be done for the edge pixels. This is the linear dimension of antialiaising, so “sobel 0.5 4” will reshoot 16 samples for any pixel with a Sobel value over 0.5, as computed from the initial image.

In order to facilitiate testing, a simple edge detection mode was added. This mode is activated by setting the second parameter of the “sobel” command to zero; it results in edge pixels having white color. Tests were run with threshold values of {0.1,0.3,0.5,0.7,0.9} on the (otherwise unchanged) Cornell box scene from the previous homework assignment.

Threshold value 0.9

Threshold value 0.9

Threshold value 0.7

Threshold value 0.7

Threshold value 0.5

Threshold value 0.5

Threshold value 0.3

Threshold value 0.3

Threshold value 0.1

Threshold value 0.1

After these tests in edge-detect-only mode, antialiasing was evaluated with a threshold value of 0.5, which was chosen as the highest number that seemed to cover all of the actual edges in the geometry. Next, a run with 5x edge-detect antialiasing was compared with a run with 5x regular antialiasing, both at XGA resolution.

Sobel filter 5x edge antialiasing

XGA, Sobel filter 5x edge antialiasing

Uniform 5x antialiasing

XGA, uniform 5x antialiasing

XGA, no antialiasing

XGA, no antialiasing

The visual effect achieved is very similar; however, the edge-antialiased image rendered in 9.23 seconds with a single thread, as opposed to 142.9 seconds for uniform antialiasing and 5.832 seconds for no antialiasing.