two parts included:
1. write the bool function insideTriangle
2. rasterize function
MSAA means that there will be supersampling inside each pixel. Yan supposed there are 4 samples. We need to figure out whether these samples of each pixel are inside the triangle separately.
Two ways to do this:
1. Define a variable fineness, which is used as the color percentage of the final pixel.
2. Calculates the color of each sub-pixel sample individually and averages them to get the final color of the pixel.
// // MSAA
// for (int x = xmin; x <= xmax; ++x)
// {
// for (int y = ymin; y <= ymax; ++y)
// {
// float fineness = 0;
// if (insideTriangle(x + 0.25, y + 0.25, t.v)) fineness += 0.25;
// if (insideTriangle(x + 0.25, y + 0.75, t.v)) fineness += 0.25;
// if (insideTriangle(x + 0.75, y + 0.25, t.v)) fineness += 0.25;
// if (insideTriangle(x + 0.75, y + 0.75, t.v)) fineness += 0.25;
// if (fineness != 0)
// {
// auto[alpha, beta, gamma] = computeBarycentric2D(x, y, t.v);
// float w_reciprocal = 1.0/(alpha / v[0].w() + beta / v[1].w() + gamma / v[2].w());
// float z_interpolated = alpha * v[0].z() / v[0].w() + beta * v[1].z() / v[1].w() + gamma * v[2].z() / v[2].w();
// z_interpolated *= w_reciprocal;
// if (z_interpolated < depth_buf[get_index(x, y)])
// {
// set_pixel(Vector3f(x, y, z_interpolated), t.getColor() * fineness);
// depth_buf[get_index(x, y)] = z_interpolated;
// }
// }
// }
// }
// Better MSAA
for (int x = xmin; x <= xmax; ++x)
{
for (int y = ymin; y <= ymax; ++y)
{
Vector3f color_sum(0, 0, 0);
int sample_count = 0;
std::vector<Vector2f> offsets = {{0.25, 0.25}, {0.25, 0.75}, {0.75, 0.25}, {0.75, 0.75}};
for (const auto& offset : offsets)
{
if (insideTriangle(x + offset.x(), y + offset.y(), t.v))
{
auto[alpha, beta, gamma] = computeBarycentric2D(x, y, t.v);
float w_reciprocal = 1.0/(alpha / v[0].w() + beta / v[1].w() + gamma / v[2].w());
float z_interpolated = alpha * v[0].z() / v[0].w() + beta * v[1].z() / v[1].w() + gamma * v[2].z() / v[2].w();
z_interpolated *= w_reciprocal;
if (z_interpolated < depth_buf[get_index(x, y)])
{
color_sum += t.getColor();
depth_buf[get_index(x, y)] = z_interpolated;
sample_count++;
}
}
}
if (sample_count > 0)
{
set_pixel(Vector3f(x, y, depth_buf[get_index(x, y)]), color_sum / sample_count);
}
}
}