Games101作业1

1.get_model_matrix(float rotation_angle)

构建出旋转矩阵即可,注意角度要转换成弧度

Eigen::Matrix4f get_model_matrix(float rotation_angle)
{
    Eigen::Matrix4f model = Eigen::Matrix4f::Identity();

    // TODO: Implement this function
    // Create the model matrix for rotating the triangle around the Z axis.
    // Then return it.
    Matrix4f R;
    float angle = rotation_angle / 180.0 * MY_PI;
    R << cos(angle), -sin(angle), 0, 0,
         sin(angle), cos(angle), 0, 0,
         0, 0, 1, 0,
         0, 0, 0, 1;
    model =  R;
    return model;
}

2.get_projection_matrix(float eye_fov, float aspect_ratio, float zNear, float zFar):

因为这里输入的zNear和zFar都是正值,实际上应该是个负值,所以计算t的时候 对n取反

然后就是逐个构建出透视-->正交,正交变换矩阵,正交变换矩阵是一个先平移再缩放的顺序

Eigen::Matrix4f get_projection_matrix(float eye_fov, float aspect_ratio,
                                      float zNear, float zFar)
{
    // Students will implement this function

    Eigen::Matrix4f projection = Eigen::Matrix4f::Identity();

    // TODO: Implement this function
    // Create the projection matrix for the given parameters.
    // Then return it.
    float angle = eye_fov/2 / 180.0 * MY_PI;
    float t = tan(angle) * -zNear;//这里因为z的输入是正值,但实际上应该是个负值,所以应该取反
    float r = aspect_ratio * t;
    float n = zNear, f = zFar;

    Matrix4f perspToOrthoMatrix,ortho,translate,scale;
    perspToOrthoMatrix << n, 0, 0, 0,
             0, n, 0, 0,
             0, 0, n+f, -n*f,
             0, 0, 1, 0;
    translate <<  1, 0, 0, 0,
                  0, 1, 0, 0,
                  0, 0, 1, -(n+f) / 2,
                  0, 0, 0, 1;
    scale << 1 / r, 0, 0, 0,
            0, 1 / t, 0, 0,
            0, 0, 2 / (n - f), 0,
            0, 0, 0, 1;
     ortho =scale*translate;     

     projection = ortho * perspToOrthoMatrix;

    return projection;
}

3.提高项

Eigen::Matrix4f get_rotation(Vector3f axis, float angle):是得到绕任意 过原点的轴的旋转变换矩阵。

很明显是通过罗德里格斯旋转公式

这里按照公式构建出矩阵即可,最后要变成四阶矩阵,因为要进行仿射变换

//提高部分
Matrix4f get_rotation_matrix(Vector3f axis, float angle)
{
    Vector3f n = axis;//旋转轴
    float rad = angle / 180.0 * MY_PI;//旋转角度
    Matrix3f rMatrix;
    Matrix3f identityMatrix = Matrix3f::Identity();
    Matrix3f nMatrix;
    nMatrix << 0, -n.z(), n.y(),
        n.z(), 0, -n.x(),
        -n.y(), n.x(), 0;
    rMatrix = cos(rad) * identityMatrix + (1 - cos(rad)) * n * n.transpose() + sin(rad) * nMatrix;
    Matrix4f rotationMatrix;//要进行仿射变换就要变成四阶矩阵
    rotationMatrix << rMatrix(0, 0), rMatrix(0, 1), rMatrix(0, 2), 0,
        rMatrix(1, 0), rMatrix(1, 1), rMatrix(1, 2), 0,
        rMatrix(2, 0), rMatrix(2, 1), rMatrix(2, 2), 0,
        0, 0, 0, 1;
    return rotationMatrix;
}

最后就是将绕任意轴旋转应用到图像上,要先在在rasterizer.cpp加入接口函数设置旋转矩阵

void rst::rasterizer::set_rodrigues(const Eigen::Matrix4f& r)
{
    rodrigues = r;
}

在draw函数里加入mvp矩阵的计算:

    Eigen::Matrix4f mvp = projection * view * model * rodrigues;//计算mvp矩阵,因为绕任意轴旋转也是模型变换的一种,所以放在model矩阵的相邻位置

在rasterizer.hpp里声明接口函数和矩阵

  public:
    void set_rodrigues(const Eigen::Matrix4f& r);
  private:
    Eigen::Matrix4f rodrigues;

在main函数里面加入旋转轴和角度的参数输入:

    Vector3f raxis;
    float ra = 0, rangle = 0;
    std::cout << "Please enter the axis and angle:" << std::endl;
    std::cin >> raxis.x() >> raxis.y() >> raxis.z() >> ra;//定义罗德里格斯旋转轴和角
    rangle = ra;

在循环里面加上按下r键就绕指定轴旋转

        if (key == 'a') {
            angle += 10;
        }
        else if (key == 'd') {
            angle -= 10;
        }
        else if (key == 'r') {//按下r,再次绕给定任意轴旋转
            rflag = true;
            rangle += ra;
        }

然后就大功告成了

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值