图形学EGE实现: 图形学EGE实现
配置相关参见 EGE专栏 (二)EGE安装与配置
https://blog.csdn.net/qq_39151563/article/details/100161986
下面仅对EGE进行简要的讲解,详细使用请参见EGE专栏
参见EGE专栏
https://blog.csdn.net/qq_39151563/category_9311717.html
EGE很多情况会遇到控制台问题,因为EGE是创建一个新的窗口,而不是直接在控制台上绘画,使用时可以根据个人需要关闭或显示控制台。
控制台显示和关闭设置参见:
https://blog.csdn.net/qq_39151563/article/details/104342295
void initgraph(int width, int height, int mode);
注意一下第三个参数 mode, 这里一般都传入 INIT_RENDERMANUAL,即手动渲染模式,是为了绘制更快,避免闪烁。
(隐藏不显示)
。void closegraph();
下面是窗口的创建与关闭示例:
#include
int main()
{
//创建宽高为640 x 480的窗口,手动渲染模式
initgraph(640, 480, INIT_RENDERMANUAL);
//暂停,等待用户按键
getch();
//关闭窗口
closegraph();
return 0;
}
运行后会创建一个窗口,默认背景色为黑色,按下任意键后窗口关闭。
EGE中的颜色类型为 color_t, 为ARGB颜色。存储格式为,小端模式下,由高位到低位,每一个字节,依次为 A,R,G,B, 即0xAARRGGBB。
普通绘图函数使用RGB颜色,即0x00RRGGBB, 高级绘图函数使用ARGB颜色。
有常用的生成对应颜色的宏
EGERGB(r, g, b)
EGEARGB(a, r, g, b)
EGEACOLOR(a, color)
EGEGRAY(gray)
EGEAGRAY(a, gray)
内部定义的颜色枚举
// 颜色
enum COLORS {
BLACK = 0,
BLUE = EGERGB(0, 0, 0xA8),
GREEN = EGERGB(0, 0xA8, 0),
CYAN = EGERGB(0, 0xA8, 0xA8),
RED = EGERGB(0xA8, 0, 0),
MAGENTA = EGERGB(0xA8, 0, 0xA8),
BROWN = EGERGB(0xA8, 0xA8, 0),
LIGHTGRAY = EGERGB(0xA8, 0xA8, 0xA8),
DARKGRAY = EGERGB(0x54, 0x54, 0x54),
LIGHTBLUE = EGERGB(0x54, 0x54, 0xFC),
LIGHTGREEN = EGERGB(0x54, 0xFC, 0x54),
LIGHTCYAN = EGERGB(0x54, 0xFC, 0xFC),
LIGHTRED = EGERGB(0xFC, 0x54, 0x54),
LIGHTMAGENTA = EGERGB(0xFC, 0x54, 0xFC),
YELLOW = EGERGB(0xFC, 0xFC, 0x54),
WHITE = EGERGB(0xFC, 0xFC, 0xFC),
};
使用如下:
颜色变量赋值为红色
//RGB
color_t color = RED;
color_t color = EGERGB(0xFF, 0x0, 0x0);
color_t color = 0xFF0000;
//ARGB
color_t color = EGEARGB(0xFF, 0xFF, 0x0, 0x0);
color_t color = EGEACOLOR(0xFF, RED);
color_t color = 0xFFFF0000;
颜色分为背景色,前景色,填充色三种,分别由一下设置:
设置背景色,并旧背景色的像素更换为新背景颜色
void setbkcolor(color_t color);
只设置背景色,不更换像素
void setbkcolor_f(color_t color);
void setcolor(color_t color);
void setfillcolor(color_t color);
color_t getbkcolor();
color_t getcolor();
color_t getfillcolor();
字体的设置一般使用 setfont(height, width, 字体名) 即可。
void setfont(int height, int width, const char* font);
其中字体参数 font 是字符串,如 “楷体”, “宋体”。
height 为文字高度,单位为像素。
width 为文字宽度,单位为像素。设置为0 则 根据字体高度,对宽度自适应,一般设置为0。
setfont(24, 0, "宋体");
void outtextxy(int x, int y, const char* text);
void xyprintf(int x, int y, const char* format, ...);
使用如下:
xyprintf(20, 10, "圆周率 Pi = %lf,大约为直径的%.2lf倍", PI, 3.14);
窗口的坐标系如下图,x轴向右为正,y轴向下为正
左上角 (x,y) 为 (0, 0),右下角为 (width-1, height-1)
因此是和平时所看的坐标系是上下相反的,窗口坐标系和平时阅读的顺序是一致的
窗口的刷新显示有时需要窗口暂停一下,即调用一些延时的函数,如常用的 getch(), delay_fps()。
getch();
如果你的程序运行时没有调用到延时类的函数,并且窗口上没有显示出绘制的内容,有可能是窗口没有刷新,可以调用 delay_ms(0) 进行手动刷新 (这个是不延时刷新的方法)。
这个会根据是否调用了绘图函数决定是否刷新。
delay_ms(0);
窗口强制刷新可以使用 delay_ms(1), 或delay_fps()。如果你没有调用绘图函数,而是通过其它方法进行了绘图,此时可能手动刷新也无效,因此需要进行强制刷新。
delay_ms(1);
getch();
动画需要控制一定的帧率,通常用 delay_fps() 来延时以保持一定的帧率,因为屏幕刷新速率一般是60FPS,所以一般设置为60
delay_fps(60);
获取窗口刷新帧率用getfps();
float getfps();
动画和交互中的帧循环通常如下写法:
is_run() 是判断窗口环境是否还在运行,窗口初始化模式没有INIT_NOFORCEEXIT设置的情况下,等效为 true。
for (; is_run(); delay_fps(60)) {
绘图、交互
}
int width = getwidth();
int height = getheight();
在对应坐标绘制一个颜色为color 的像素点,里面有参数有效检测,超出范围也没问题。
void putpixel(int x, int y, color_t color);
还有没有参数有效检测的画点函数,如果已经确定点不超出窗口范围,能够减少绘制时间。
putpixel_f(int x, int y, color_t color)
还有更快地绘制方法,即获取窗口帧缓存首地址,将对应的像素设置为目标颜色,需要自己防止越界。得到的是一维数组
color_t* buff = getbuffer(NULL);
坐标为(x, y)的像素,对应为 buff[x + y * width], 其中width为窗口宽度。
如,在(100, 20) 的位置画一个红色的点
int width = getwidth();
buff[100 + 20 * width] = RED;
不过这样可能需要强制刷新
如果绘制过程中有上一次绘画时留下的痕迹,绘画时能简单覆盖就覆盖,不能简单覆盖的,需要清屏重绘,以消除痕迹。
窗口将全部变为背景色
cleardevice();
简单地可以设置填充色为背景色,然后用填充矩形覆盖即可。
或者可以通过设置视口区域,然后对视口区域进行清除。区域固定比较比较快。
其中,clip是绘制到视口区域外的图形是否需要裁剪。
设置视口区域
setviewport(left, top right, bottom, clip);
清除视口区域
clearviewport();
绘图函数直接根据函数的参数说明使用即可,参见
(七)EGE基础绘图
https://blog.csdn.net/qq_39151563/article/details/104342390
高级函数即可透明和带抗锯齿绘图函数,画出的图形比较美观。
参见 (八)EGE高级绘图
https://blog.csdn.net/qq_39151563/article/details/104342471
请查看 EGE专栏 中键盘消息和鼠标消息 部分