DEV C++ 计算机图形学期末作业简单示例(1)

目录

一、题目需求分析

基础图形绘制系统分析

1. ​功能模块划分​

2. ​核心实现逻辑​

3. ​输入与坐标处理​

4. ​数据结构设计​

5. ​OpenGL初始化与渲染流程​

6. ​技术难点与解决方案​

7. ​注释与文档要求​

8. ​扩展性考虑​

二、核心代码实现

2.1 系统架构设计

2.2 图形绘制模块

2.2.1 直线绘制引擎

2.2.2 矩形绘制引擎

2.2.3 圆形生成算法

三、渲染系统集成

3.1 主渲染循环

3.2 交互控制扩展

四、关键技术详解

4.1 坐标系映射机制

4.2 颜色模型应用

4.3 性能优化策略


1. 基础图形绘制系统

功能:基于OpenGL,实现一个可绘制直线、圆形、矩形等基础图形的程序。

要求:支持图形颜色、大小参数化设置,能通过输入坐标确定图形位置,添加基础注释说明绘制逻辑。

一、题目需求分析

基础图形绘制系统分析

1. ​功能模块划分
  • 图形绘制模块​:负责实现直线、圆形、矩形的绘制逻辑。
  • 参数设置模块​:处理颜色(RGB/RGBA)、线宽(直线)、尺寸(矩形长宽、圆形半径)的参数传递。
  • 输入处理模块​:解析用户输入的坐标数据,转换为OpenGL坐标系。
  • 渲染引擎​:整合图形数据,调用OpenGL API完成绘制。
2. ​核心实现逻辑
  • 图形绘制原理​:
    • 直线​:通过GL_LINES模式,使用两个顶点坐标绘制,线宽通过glLineWidth控制。
    • 矩形​:基于顶点坐标生成四边形,可用GL_QUADSGL_POLYGON模式,需处理位置(左上/右下角)与尺寸参数。
    • 圆形​:通过顶点生成算法(如极坐标细分)构造近似圆形,用GL_TRIANGLE_FANGL_LINE_LOOP模式,半径参数决定顶点分布密度。
  • 颜色与参数传递​:
    • 颜色值通过glColor3f在绘制前设置,需为每个图形单独指定。
    • 大小参数(如线宽、半径)作为变量传入绘制函数,动态调整渲染效果。
3. ​输入与坐标处理
  • 坐标输入​:需支持用户输入(如控制台/文件)或交互式输入(如鼠标点击)。
  • 坐标系转换​:将窗口坐标(像素单位)转换为OpenGL标准化设备坐标(NDC,范围[-1,1]),需处理视口变换(glViewport)和投影矩阵(正交投影)。
4. ​数据结构设计
  • 图形对象结构体​:存储图形类型、位置(x,y)、颜色(r,g,b,a)、尺寸(宽度/高度/半径)等属性。
  • 图形列表管理​:使用数组或链表维护所有图形对象,便于批量渲染。
5. ​OpenGL初始化与渲染流程
  • 初始化​:设置OpenGL上下文、视口、投影矩阵(正交投影适配窗口比例)。
  • 渲染循环​:
    1. 清空缓冲区(glClear)。
    2. 遍历图形列表,按类型调用对应绘制函数。
    3. 交换缓冲区(双缓冲模式下)。
6. ​技术难点与解决方案
  • 圆形近似精度​:通过增加顶点分段数(如360段)提升圆形平滑度,但需平衡性能。
  • 线宽一致性​:不同硬件对glLineWidth支持差异,需测试并设置合理范围。
  • 交互式定位​:鼠标点击坐标转换需考虑窗口缩放与视口映射,使用gluUnProject实现精确转换。
7. ​注释与文档要求
  • 代码注释​:关键函数(如drawCircle)需说明算法逻辑(如极坐标顶点生成)、参数意义(半径、分段数)。
  • 设计文档​:描述模块交互、数据流(如输入→参数存储→渲染)、性能考量(如立即模式 vs VBO)。
8. ​扩展性考虑
  • 新增图形支持​:通过扩展图形对象结构体和绘制函数,可兼容未来添加的图形(如多边形、曲线)。
  • 交互增强​:预留接口支持拖拽调整图形参数(如框选修改大小)。

二、核心代码实现

2.1 系统架构设计

#include <GL/glut.h>
#include <cmath> // 数学计算库

// 系统常量定义
constexpr int WINDOW_WIDTH  = 800;
constexpr int WINDOW_HEIGHT = 600;

/* 初始化OpenGL环境
   功能:设置投影坐标系与背景色
   参数:无
   返回:void */
void initGL() {
    glClearColor(0.0f, 0.0f, 0.0f, 1.0f); // RGBA黑色背景
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    gluOrtho2D(0, WINDOW_WIDTH, 0, WINDOW_HEIGHT); // 建立2D正交投影
}

2.2 图形绘制模块

2.2.1 直线绘制引擎
/* 线条绘制函数
   参数说明:
   (x1,y1) - 起点坐标(左下角原点)
   (x2,y2) - 终点坐标
   (r,g,b) - RGB颜色值(0.0~1.0范围)
   width   - 线宽(像素单位)
   
   算法特点:
   - 使用GL_LINES图元类型
   - 支持抗锯齿线宽渲染 */
void drawLine(float x1, float y1, float x2, float y2,
             float r, float g, float b, float width = 1.0f) {
    glColor3f(r, g, b);
    glLineWidth(width);
    glBegin(GL_LINES);
        glVertex2f(x1, y1);
        glVertex2f(x2, y2);
    glEnd();
}
2.2.2 矩形绘制引擎
/* 矩形绘制函数
   参数说明:
   (x,y)    - 左下角坐标
   w        - 宽度
   h        - 高度
   filled   - 填充模式标志位(true=实心,false=线框)
   
   坐标系特性:
   - Y轴正方向向上(与屏幕坐标系Y轴向下相反)
   - 使用GL_QUADS进行填充绘制 */
void drawRect(float x, float y, float w, float h,
             float r, float g, float b, bool filled = true) {
    glColor3f(r, g, b);
    glBegin(filled ? GL_QUADS : GL_LINE_LOOP);
        glVertex2f(x,     y);       // 左下角
        glVertex2f(x + w, y);       // 右下角
        glVertex2f(x + w, y + h);   // 右上角
        glVertex2f(x,     y + h);   // 左上角
    glEnd();
}
2.2.3 圆形生成算法
/* 圆形绘制函数
   参数说明:
   cx,cy    - 圆心坐标
   radius   - 半径
   segments - 分段数(精度控制)
   
   算法原理:
   - 采用极坐标方程:x = r*cosθ, y = r*sinθ
   - 使用GL_TRIANGLE_FAN进行填充绘制
   分段数建议:
   - ≥12:可消除明显锯齿
   - 64:达到屏幕显示极限精度 */
void drawCircle(float cx, float cy, float radius,
               int segments = 32, float r = 1.0f, 
               float g = 1.0f, float b = 1.0f, 
               bool filled = true) {
    glColor3f(r, g, b);
    glBegin(filled ? GL_TRIANGLE_FAN : GL_LINE_LOOP);
        for (int i = 0; i < segments; ++i) {
            float theta = 2.0f * M_PI * i / segments;
            float x = cx + radius * cos(theta);
            float y = cy + radius * sin(theta);
            glVertex2f(x, y);
        }
    glEnd();
}

三、渲染系统集成

3.1 主渲染循环

void display() {
    glClear(GL_COLOR_BUFFER_BIT); // 清空颜色缓冲区
    
    /* 示例图形绘制
       坐标系验证:
       - 原点(0,0)位于窗口左下角
       - X轴向右延伸,Y轴向上延伸 */
    
    // 白色斜线(线宽2.0)
    drawLine(50, 50, 200, 200, 1.0f, 1.0f, 1.0f, 2.0f);
    
    // 红色填充矩形(左下角坐标250,50)
    drawRect(250, 50, 150, 100, 1.0f, 0.0f, 0.0f, true);
    
    // 绿色空心圆(半径80)
    drawCircle(150, 400, 80, 64, 0.0f, 1.0f, 0.0f, false);
    
    // 蓝色实心圆(分层绘制示例)
    drawCircle(400, 350, 60, 64, 0.0f, 0.0f, 1.0f, true);
    
    glutSwapBuffers(); // 双缓冲技术防闪烁
}

3.2 交互控制扩展

// 键盘事件处理(ESC退出)
void keyboard(unsigned char key, int x, int y) {
    if (key == 27) exit(0); // ASCII码27对应ESC键
}

// 主函数入口
int main(int argc, char**​ argv) {
    glutInit(&argc, argv);
    glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGBA);
    glutInitWindowSize(WINDOW_WIDTH, WINDOW_HEIGHT);
    glutCreateWindow("OpenGL图形绘制系统");
    
    initGL(); // 初始化图形环境
    
    glutDisplayFunc(display);
    glutKeyboardFunc(keyboard);
    
    glutMainLoop(); // 进入渲染循环
    return 0;
}

四、关键技术详解

4.1 坐标系映射机制

  • 投影设置​:gluOrtho2D(0, WIDTH, 0, HEIGHT)建立左手坐标系
  • 坐标转换​:窗口坐标与OpenGL坐标对应关系:
    屏幕左下角 → (0,0)
    屏幕右上角 → (800,600)

4.2 颜色模型应用

  • RGB色彩空间​:参数取值范围0.0~1.0(非0~255)
  • 颜色混合​:通过glColor3f()设置当前绘制颜色

4.3 性能优化策略

  • 双缓冲技术​:glutSwapBuffers()避免画面撕裂
  • 批处理绘制​:相同属性图形合并绘制调用

完整代码

#define GLUT_DISABLE_ATEXIT_HACK

#include <windows.h>    // Windows 平台必须
#include <GL/gl.h>
#include <GL/glu.h>
#include <GL/glut.h>
#include <cmath>

// 窗口尺寸
const int windowWidth  = 800;
const int windowHeight = 600;

// -------------------------------------------------------------------
// 初始化 OpenGL 环境
void initGL() {
    // 背景色:黑色
    glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
    // 投影:2D 正交投影,从 (0,0) 到 (windowWidth, windowHeight)
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    gluOrtho2D(0.0, windowWidth, 0.0, windowHeight);
}

// -------------------------------------------------------------------
// 绘制直线:起点(x1,y1)、终点(x2,y2)、颜色(r,g,b)、线宽 width
void drawLine(float x1, float y1,
              float x2, float y2,
              float r, float g, float b,
              float width)
{
    glColor3f(r, g, b);      // 设置颜色
    glLineWidth(width);      // 设置线宽
    glBegin(GL_LINES);
        glVertex2f(x1, y1);
        glVertex2f(x2, y2);
    glEnd();
}

// -------------------------------------------------------------------
// 绘制矩形:左下角(x,y)、宽 w、高 h、颜色、是否填充
void drawRect(float x, float y,
              float w, float h,
              float r, float g, float b,
              bool filled)
{
    glColor3f(r, g, b);
    if (filled) glBegin(GL_QUADS);
    else        glBegin(GL_LINE_LOOP);
        glVertex2f(x,     y);
        glVertex2f(x + w, y);
        glVertex2f(x + w, y + h);
        glVertex2f(x,     y + h);
    glEnd();
}

// -------------------------------------------------------------------
// 绘制圆形:圆心(cx,cy)、半径 radius、分段数 segments、颜色、是否填充
void drawCircle(float cx, float cy,
                float radius,
                int segments,
                float r, float g, float b,
                bool filled)
{
    glColor3f(r, g, b);
    if (filled) glBegin(GL_TRIANGLE_FAN);
    else        glBegin(GL_LINE_LOOP);

    for (int i = 0; i < segments; ++i) {
        float theta = 2.0f * 3.1415926f * float(i) / float(segments);
        float x = radius * cosf(theta);
        float y = radius * sinf(theta);
        glVertex2f(cx + x, cy + y);
    }
    glEnd();
}

// -------------------------------------------------------------------
// 渲染回调:在窗口中绘制示例图形
void display() {
    // 清屏
    glClear(GL_COLOR_BUFFER_BIT);

    // 示例:白色直线
    drawLine(50, 50, 200, 200, 1.0f, 1.0f, 1.0f, 2.0f);

    // 示例:红色填充矩形
    drawRect(250, 50, 150, 100, 1.0f, 0.0f, 0.0f, true);

    // 示例:绿色空心圆
    drawCircle(150, 400, 80, 64, 0.0f, 1.0f, 0.0f, false);

    // 示例:蓝色填充圆
    drawCircle(400, 350, 60, 64, 0.0f, 0.0f, 1.0f, true);

    // 交换缓冲
    glutSwapBuffers();
}

// -------------------------------------------------------------------
// 键盘回调:按 ESC 退出
void keyboard(unsigned char key, int x, int y) {
    if (key == 27) { // ESC
        exit(0);
    }
}

// -------------------------------------------------------------------
// 主函数:初始化 GLUT,注册回调,启动主循环
int main(int argc, char** argv) {
    // 初始化 GLUT
    glutInit(&argc, argv);
    glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGBA);
    glutInitWindowSize(windowWidth, windowHeight);
    glutInitWindowPosition(100, 100);
    glutCreateWindow("基础图形绘制系统");

    // 初始化 OpenGL
    initGL();

    // 注册回调
    glutDisplayFunc(display);
    glutKeyboardFunc(keyboard);
    // 如需鼠标或其他输入,可在此注册 glutMouseFunc 等

    // 进入 GLUT 主循环
    glutMainLoop();
    return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值