如何实现三角形内部颜色由三个顶点颜色开始渐变渲染的效果?

概述

图-1

推导

图-2

计算

图-3

结论

P点的重心坐标,可以按照拆分三角形占总三角形比例进行计算
图-4

P点的任何属性值都可以通过重心坐标作为比例,通过ABC顶点的数据作为源来计算获得,颜色举例如下:
图-5

算法实现

void Raster::interpolantTriangle(const Point& v0, const Point& v1, const Point& v2, Point& p) {
auto e1 = math::vec2f(v1.x - v0.x, v1.y - v0.y);
auto e2 = math::vec2f(v2.x - v0.x, v2.y - v0.y);
float sumArea = std::abs(math::cross(e1, e2));

auto pv0 = math::vec2f(v0.x - p.x, v0.y - p.y);
auto pv1 = math::vec2f(v1.x - p.x, v1.y - p.y);
auto pv2 = math::vec2f(v2.x - p.x, v2.y - p.y);
//计算v0的权重

float v0Area = std::abs(math::cross(pv1, pv2));
float v1Area = std::abs(math::cross(pv0, pv2));
float v2Area = std::abs(math::cross(pv0, pv1));

float weight0 = v0Area / sumArea;
float weight1 = v1Area / sumArea;
float weight2 = v2Area / sumArea;

RGBA result;
auto c0 = v0.color;
auto c1 = v1.color;
auto c2 = v2.color;

result.mR = static_cast<float>(c0.mR) * weight0 + static_cast<float>(c1.mR) * weight1 + static_cast<float>(c2.mR) * weight2;
result.mG = static_cast<float>(c0.mG) * weight0 + static_cast<float>(c1.mG) * weight1 + static_cast<float>(c2.mG) * weight2;
result.mB = static_cast<float>(c0.mB) * weight0 + static_cast<float>(c1.mB) * weight1 + static_cast<float>(c2.mB) * weight2;
result.mA = static_cast<float>(c0.mA) * weight0 + static_cast<float>(c1.mA) * weight1 + static_cast<float>(c2.mA) * weight2;

p.color = result;
}