使用Imgui实现一个简单加法计算器

实现一个 加法计算的功能 两个输入框 中间一个+号 一个等号按钮 输入两个数字后 点击= 把计算的结果显示到第三个输入框。

功能很简单,但是,我们借助这个功能,可以了解imgui的基本表单功能。

先看最终的允许截图

很简单的例子,我们先看所有代码,大部分代码和上节课的例子基本一样,就是中间UI渲染部分不一样,还有几个存储数据的遍历,另外主题样式我们也改成了浅色的,这样更加和我们的平常从GUI程序很像了。

#pragma comment(linker, "/SUBSYSTEM:windows /ENTRY:mainCRTStartup")

#include <GLFW/glfw3.h>
#include "imgui.h"
#include "backends/imgui_impl_glfw.h"
#include "backends/imgui_impl_opengl3.h"
#include <cstdio>

int main()
{
    if (!glfwInit())
    {
        printf("GLFW initialization failed\n");
        return -1;
    }

    const char* glsl_version = "#version 330";
    glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
    glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
    glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);

    GLFWwindow* window = glfwCreateWindow(500, 200, "Add Calculator", nullptr, nullptr); //窗口大小和标题
    if (!window)
    {
        glfwTerminate();
        return -1;
    }
    glfwMakeContextCurrent(window);
    glfwSwapInterval(1);

    IMGUI_CHECKVERSION();
    ImGui::CreateContext();
    ImGuiIO& io = ImGui::GetIO();
	ImGui::StyleColorsLight(); //设置为浅色主题

    ImGui_ImplGlfw_InitForOpenGL(window, true);
    ImGui_ImplOpenGL3_Init(glsl_version);

    // 加法计算器全局变量
    float num1 = 0.0f;    // 第一个加数
    float num2 = 0.0f;    // 第二个加数
    float result = 0.0f;  // 两数相加结果

    while (!glfwWindowShouldClose(window))
    {
        glfwPollEvents();

        ImGui_ImplOpenGL3_NewFrame();
        ImGui_ImplGlfw_NewFrame();
        ImGui::NewFrame();

        ImGui::SetNextWindowPos(ImVec2(0, 0));
        ImGui::SetNextWindowSize(io.DisplaySize);

        ImGuiWindowFlags window_flags = ImGuiWindowFlags_NoDecoration
            | ImGuiWindowFlags_NoMove
            | ImGuiWindowFlags_NoResize
            | ImGuiWindowFlags_NoSavedSettings;

        ImGui::PushStyleVar(ImGuiStyleVar_WindowRounding, 0.0f);
        ImGui::PushStyleVar(ImGuiStyleVar_WindowBorderSize, 0.0f);

        ImGui::Begin("Control Panel", nullptr, window_flags);

        // 计算器标题
        ImGui::Text("Please input two number"); //文字提示 会独占一行的
	ImGui::Spacing();// 添加垂直间距

        // 第一个数字输入框,宽度120,
	ImGui::SetNextItemWidth(120);// 设置下一个控件的宽度为120像素 这个是为了设置下一个控件的属性,本身不会呈现内容
	ImGui::InputFloat("##num1", &num1);// 创建一个浮点数输入框,绑定变量num1,标签隐藏 也是独占一行的

        // 同一行绘制加号分隔符
	ImGui::SameLine(); // 让下一个控件在同一行显示 如果不增加这个,默认每个控件都是独占一行的 增加了 下一个控件就会在同一行显示
	ImGui::Text(" + "); // 显示加号分隔符 和上面是输入框同一行

        // 第二个数字输入框
	ImGui::SameLine(); // 让下一个控件在同一行显示 每次准备渲染下一个控件前 如果希望同一行都要使用这个
        ImGui::SetNextItemWidth(120);//同上 也是设置下一个输入框宽度
        ImGui::InputFloat("##num2", &num2);

        // 等号计算按钮,点击执行加法运算
        ImGui::SameLine();
        if (ImGui::Button(" = ", ImVec2(40, 0)))
        {
            // 计算两数之和并赋值给结果变量
            result = num1 + num2;
        }

        // 结果只读输入框,禁止手动编辑,数值保留2位小数展示
        ImGui::SameLine();
        ImGui::SetNextItemWidth(180);
        ImGui::InputFloat("##result", &result, 0.0f, 0.0f, "%.2f", ImGuiInputTextFlags_ReadOnly);

        ImGui::End();

	// 弹出样式变量,恢复默认样式
        ImGui::PopStyleVar(2);

        ImGui::Render();
        int width, height;
        glfwGetFramebufferSize(window, &width, &height);
        glViewport(0, 0, width, height);
        glClearColor(0.12f, 0.12f, 0.12f, 1.f);
        glClear(GL_COLOR_BUFFER_BIT);
        ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData());

        glfwSwapBuffers(window);
    }

    ImGui_ImplOpenGL3_Shutdown();
    ImGui_ImplGlfw_Shutdown();
    ImGui::DestroyContext();
    glfwDestroyWindow(window);
    glfwTerminate();
    return 0;
}Code language: C++ (cpp)

设置浅色,只需要修改,ImGui::StyleColorsLight(); //设置为浅色主题 就可以。

设置窗口标题和大小, GLFWwindow* window = glfwCreateWindow(400, 60, “Add Calculator”, nullptr, nullptr); //窗口大小和标题

ImGui::Text("Please input two number");

ImGui::Spacing(); // 在标题和下方输入框之间空出一段距离Code language: PHP (php)

输出第一行文本,然后在第二行输出一个间距。

其他的属性读者可以看上面的注释,主要是默认情况,Text InputFloat Button 这些都是独占一行的,如果不需要换行,那么在调用这些之前,执行一下ImGui::SameLine(); 这个,那么就下一个控件就不会换行了

如果需要设置下一个控件的宽度,则需要SetNextItemWidth通过这个来设置。

按钮点击

if (ImGui::Button(" = ", ImVec2(40, 0)))
 {
            // 计算两数之和并赋值给结果变量
            result = num1 + num2;
 }Code language: C++ (cpp)

这句代码中ImGui::Button(” = “, ImVec2(40, 0)) 是渲染一个按钮出来,前面是按钮显示的问题,后面是按钮的宽高,高度0,则表示高度自适应。

只有鼠标完整点击(按下 + 松开)按钮时返回 true,其余情况 false。一旦返回了true,则表示用户点击了按钮,这个时候,就执行里面的{}中的代码。

你可以想象一下,这是一个循环的过程,界面是不断刷新的,每次刷新就执行一次while里面的代码,如果用户什么都不操作,就每次渲染出来的页面都是一样的。只要某次,用户点击了按钮,这时候,渲染这个按钮的时候,就会返回true,表示按钮点击了,然后就会执行按钮中的代码,

按钮中的代码是把两个输入框绑定的num,计算他们的和,然后给result这个变量赋值,然后下一步

ImGui::SameLine();
ImGui::SetNextItemWidth(180);
ImGui::InputFloat("##result", &result, 0.0f, 0.0f, "%.2f", ImGuiInputTextFlags_ReadOnly);Code language: C++ (cpp)

还是在同一行中,把上面计算的result最新的值,呈现到带三个输入框,第三个输入框是只读的。

然后完成一次刷新,下一次刷新,如果用户没有操作,那就至少绘制上一次的值出来。

这个过程和游戏的渲染很像的。游戏还有动画的显示方式也是类似。

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注