趣味编程:答案之书

概述:该篇博客主要介绍的是曾经一度风靡全网的答案之书小程序。

目录

[1. 效果展示](#1. 效果展示)

[2. 源码展示](#2. 源码展示)

[3. 代码逻辑详解](#3. 代码逻辑详解)

[3.1 头文件与全局变量](#3.1 头文件与全局变量)

[3.2 main函数](#3.2 main函数)

[3.3 主循环](#3.3 主循环)

[3. 4 绘制界面](#3. 4 绘制界面)

[4. 运行问题](#4. 运行问题)

5.小结


1. 效果展示

该小程序是动态的效果, 因此实际运行的效果相较于博客会更具有动态感一点。

2. 源码展示

复制代码
#include <graphics.h>
#include <conio.h>
#include <time.h>
#include <vector>
// 答案库
std::vector<const char*> answers =
{
    "是", "否", "或许", "稍后再问",
    "毫无疑问", "结果未明", "保持期待",
    "别指望", "绝对肯定", "暂时观望",
    "机会渺茫", "积极行动", "改变策略",
    "无法预测", "遵循直觉", "需要努力",
    "时机未到", "放手去做", "谨慎为好"
};
// 窗口尺寸
const int WIDTH = 800;
const int HEIGHT = 600;

int main()
{
    // 初始化图形窗口
    initgraph(WIDTH, HEIGHT);
    srand(time(NULL)); // 随机种子

    bool isPaused = false;
    int answerIndex = 0;

    // 主循环
    while (true)
    {
        // 检查窗口关闭
        if (MouseHit())
        {
            MOUSEMSG msg = GetMouseMsg();
            if (msg.uMsg == WM_CLOSE) break;
        }

        // 按键检测
        if (_kbhit())
        {
            int key = _getch();
            if (key == ' ') // 空格键切换暂停状态
            {
                isPaused = !isPaused;
            }
        }

        // 非暂停时更新答案
        if (!isPaused)
        {
            answerIndex = rand() % answers.size();
        }

        // 绘制界面
        BeginBatchDraw();
        cleardevice();

        // 绘制背景
        setfillcolor(RGB(30, 30, 30));
        solidrectangle(0, 0, WIDTH, HEIGHT);
        // 设置文字样式
        settextstyle(100, 0, "楷体");
        setbkmode(TRANSPARENT);
        // 设置文字颜色
        settextcolor(RGB(200, 200, 100));
        RECT r = { 0, 0, WIDTH, HEIGHT };
        drawtext(answers[answerIndex], &r, DT_CENTER | DT_VCENTER | DT_SINGLELINE);
        // 绘制提示文字
        settextcolor(WHITE);
        settextstyle(20, 0, _T("宋体"));
        outtextxy(20, HEIGHT - 50, "按空格键暂停/继续");
        outtextxy(20, HEIGHT - 30, "点击右上角关闭程序");

        EndBatchDraw();
        Sleep(50); // 控制刷新速度
    }
    closegraph();
    return 0;
}

3. 代码逻辑详解

3.1 头文件与全局变量
复制代码
#include <graphics.h>
#include <conio.h>
#include <time.h>
#include <vector>
// 答案库
std::vector<const char*> answers =
{
    "是", "否", "或许", "稍后再问",
    "毫无疑问", "结果未明", "保持期待",
    "别指望", "绝对肯定", "暂时观望",
    "机会渺茫", "积极行动", "改变策略",
    "无法预测", "遵循直觉", "需要努力",
    "时机未到", "放手去做", "谨慎为好"
};
// 窗口尺寸
const int WIDTH = 800;
const int HEIGHT = 600;
  • 引入了多个头文件,graphics.h 用于图形界面的绘制,conio.h 用于控制台输入输出,time.h 用于处理时间,vector 用于使用 C++ 的向量容器。
  • answers 是一个存储各种答案的向量,这些答案将在程序中随机显示。
  • WIDTH 和 HEIGHT 定义了图形窗口的宽度和高度。
3.2 main函数
复制代码
int main()
{
    // 初始化图形窗口
    initgraph(WIDTH, HEIGHT);
    srand(time(NULL)); // 随机种子

    bool isPaused = false;
    int answerIndex = 0;
  • initgraph(WIDTH, HEIGHT) 初始化一个指定宽度和高度的图形窗口。
  • srand(time(NULL)) 设置随机数种子,以确保每次运行程序时生成的随机数不同。
  • isPaused 是一个布尔变量,用于表示程序是否处于暂停状态,初始值为 false。
  • answerIndex 用于记录当前显示的答案在 answers 向量中的索引,初始值为 0。
3.3 主循环
复制代码
    // 主循环
    while (true)
    {
        // 检查窗口关闭
        if (MouseHit())
        {
            MOUSEMSG msg = GetMouseMsg();
            if (msg.uMsg == WM_CLOSE) break;
        }

        // 按键检测
        if (_kbhit())
        {
            int key = _getch();
            if (key == ' ') // 空格键切换暂停状态
            {
                isPaused = !isPaused;
            }
        }

        // 非暂停时更新答案
        if (!isPaused)
        {
            answerIndex = rand() % answers.size();
        }
  • while (true) 是一个无限循环,程序将在这个循环中不断运行,直到满足特定条件退出。
  • MouseHit() 检查是否有鼠标事件发生,如果有则通过 GetMouseMsg() 获取鼠标消息。如果鼠标消息的类型是 WM_CLOSE(即用户点击了窗口的关闭按钮),则使用 break 语句跳出循环,结束程序。
  • _kbhit() 检查是否有按键被按下,如果有则通过 _getch() 获取按键的 ASCII 码。如果按下的是空格键(ASCII 码为 ' '),则切换 isPaused 的状态。
  • 如果 isPaused 为 false,表示程序未暂停,使用 rand() % answers.size() 随机生成一个 answers 向量的索引,更新 answerIndex。
3. 4 绘制界面
复制代码
        // 绘制界面
        BeginBatchDraw();
        cleardevice();

        // 绘制背景
        setfillcolor(RGB(30, 30, 30));
        solidrectangle(0, 0, WIDTH, HEIGHT);
        // 设置文字样式
        settextstyle(100, 0, "楷体");
        setbkmode(TRANSPARENT);
        // 设置文字颜色
        settextcolor(RGB(200, 200, 100));
        RECT r = { 0, 0, WIDTH, HEIGHT };
        drawtext(answers[answerIndex], &r, DT_CENTER | DT_VCENTER | DT_SINGLELINE);
        // 绘制提示文字
        settextcolor(WHITE);
        settextstyle(20, 0, _T("宋体"));
        outtextxy(20, HEIGHT - 50, "按空格键暂停/继续");
        outtextxy(20, HEIGHT - 30, "点击右上角关闭程序");

        EndBatchDraw();
        Sleep(50); // 控制刷新速度
    }
  • BeginBatchDraw() 开始批量绘图,避免屏幕闪烁。
  • cleardevice() 清除当前绘图设备上的所有内容。
  • setfillcolor(RGB(30, 30, 30)) 设置填充颜色为深灰色,solidrectangle(0, 0, WIDTH, HEIGHT) 绘制一个填充的矩形作为背景。
  • settextstyle(100, 0, "楷体") 设置文字样式为 100 磅的楷体,setbkmode(TRANSPARENT) 设置文字背景为透明。
  • settextcolor(RGB(200, 200, 100)) 设置文字颜色为浅黄色,drawtext(answers[answerIndex], &r, DT_CENTER | DT_VCENTER | DT_SINGLELINE) 在窗口中心绘制当前的答案。
  • settextcolor(WHITE) 设置提示文字颜色为白色,settextstyle(20, 0, _T("宋体")) 设置提示文字样式为 20 磅的宋体,outtextxy(20, HEIGHT - 50, "按空格键暂停/继续") 和 outtextxy(20, HEIGHT - 30, "点击右上角关闭程序") 在窗口底部绘制提示文字。
  • EndBatchDraw() 结束批量绘图,将绘制的内容一次性显示在屏幕上。
  • Sleep(50) 暂停程序 50 毫秒,控制界面的刷新速度。

4. 运行问题

该程序运行问题的解决如上篇博客所讲 :趣味编程:爱心-CSDN博客

5.小结

以上就是本篇博客的所有内容了,如果大家能从中学到知识的话,还请给博主点点赞。

相关推荐
谢亮_vipxieliang2 分钟前
Go 并发控制进阶:sync 包高级原语与 Context 生命周期管理
开发语言·后端·golang
成旭先生12 分钟前
银行卡识别 API:一张照片读出卡号、BIN 与发卡行
人工智能·算法·ocr·api接口·金融科技·银行卡识别·支付风控
xuxigifxfh18 分钟前
HJ5 进制转换
java·开发语言·华为机考
denlaku19 分钟前
JDK 12 新特性详解
java·开发语言
陌上花开缓缓归以23 分钟前
mebdlts3.4.1安全启动全流程
服务器·算法
Nebula_g24 分钟前
JavaSE拓展:可变参数
java·开发语言·算法·安全·javase·可变参数
Logic10134 分钟前
C语言/数据结构字符串题解:最短循环节——找出能重复构成原串的最短基础子串
c语言·数据结构·字符串·枚举·时间复杂度·算法题·kmp优化
129Lab43 分钟前
BMS 核心算法:SOC 估算从安时积分到 LSTM-UKF 串级融合的 30 年演进(附 Python 实现)
python·算法·lstm·python3.11·bms·soc估算
kgkg44 分钟前
我通过逆向学到了douyin的美颜算法
算法
我就是不信1 小时前
CuTest:轻量级 C 语言单元测试框架实战指南
c语言·单元测试·log4j