【GAMES101】作业2 Triangles and Z-buffering

作业2的内容包含两个部分:

1、完成三角形栅格化算法

2、编写函数insideTriangel,用于在栅格化的时候判断某一点是否在三角形内

insideTriangel 

如何判断某一点与三角形的内外关系,使用到的方法是叉乘,将三角形的三个顶点顺序相连形成三个有序的向量AB,BC,CA,分别与向量AP,BP,CP相乘,如果符号相同,则P在三角形内,否者在三角形外。

 实现代码如下

static bool insideTriangle(int x, int y, const Vector3f* _v)
{   
    // TODO : Implement this function to check if the point (x, y) is inside the triangle represented by _v[0], _v[1], _v[2]
    Eigen::Vector3f p(x, y, 1);
    Eigen::Vector3f ab = _v[1] - _v[0];
    Eigen::Vector3f bc = _v[2] - _v[1];
    Eigen::Vector3f ca = _v[0] - _v[2];

    Eigen::Vector3f ap = p - _v[0];
    Eigen::Vector3f bp = p - _v[1];
    Eigen::Vector3f cp = p - _v[2];

    if (ab.cross(ap).dot(bc.cross(bp)) > 0 &&
        ab.cross(ap).dot(ca.cross(cp)) > 0) {
        return true;
    }
    else {
        return false;
    }
}

 三角形栅格化

代码框架的注释中其实给出了具体的思路

1、获取三角形的包围盒,用于减少计算量,不至于遍历屏幕上的每一个点

    // TODO : Find out the bounding box of current triangle.
    float Xmin = INT_MAX;
    float Xmax = INT_MIN;
    float Ymin = INT_MAX;
    float Ymax = INT_MIN;
    for (auto v : t.v) {
        Xmin = std::min(Xmin, v.x());
        Xmax = std::max(Xmax, v.x());
        Ymin = std::min(Ymin, v.y());
        Ymax = std::max(Ymax, v.y());
    }

2、遍历包围盒中的每一个像素,并且判断是否在三角形内部

这一步用到了insideTriangle函数,注意的是并不是针对x,y坐标计算是否在三角形内,而是计算每个像素中心是否在三角形内部,所以是x+0.5,y+0.5

    for (int x = Xmin; x <= Xmax; x++) {
        for (int y = Ymin; y <= Ymax; y++) {
            if (insideTriangle(x + 0.5, y + 0.5, t.v)) {
                float alpha, beta, gamma;
                std::tie(alpha, beta, gamma) = computeBarycentric2D(x+0.5, y+0.5, 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)]) {
                    depth_buf[get_index(x, y)] = z_interpolated;
                    set_pixel(Vector3f(x, y, 1), t.getColor());
                }
            }
        }
    }

第二个if语句实现了z-buffer深度缓存,判断当前点的z值是否小于buffer中存储的值,只有当该z值小于buffer中的值时,才会将该点显示在屏幕上,并且更新z-buffer

运行结果

        三角形上下颠倒的原因可能是框架中使用的时左手系,所以与作业1的结果不太一样。 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值