How to Set Up Dear ImGui with OpenGL: Complete Integration Guide

To set up Dear ImGui with OpenGL, create an OpenGL 3+ context, initialize the core ImGui context with ImGui::CreateContext(), initialize the platform backend (e.g., GLFW) and the OpenGL 3 renderer backend (ImGui_ImplOpenGL3_Init), then execute the per-frame sequence of ImGui_ImplOpenGL3_NewFrame, ImGui::NewFrame, ImGui::Render, and ImGui_ImplOpenGL3_RenderDrawData in your main loop.

Dear ImGui is a bloat-free, immediate-mode graphical user interface library for C++ that outputs geometry and draw commands rather than rendering pixels directly. To set up Dear ImGui with OpenGL, you must integrate the official OpenGL 3 backend provided in the ocornut/imgui repository, which translates ImGui's draw lists into OpenGL API calls using vertex buffer objects and shaders.

Dear ImGui OpenGL Architecture Overview

The integration follows a strict separation between UI logic, platform handling, and rendering. Understanding these layers ensures you initialize components in the correct order.

Core ImGui Library

The core ImGui logic lives in imgui.h and imgui.cpp. This code is graphics-API agnostic—it calculates layouts, handles user input state, and produces draw lists containing vertices, indices, and texture coordinates. It does not perform any actual rendering.

OpenGL Renderer Backend

The renderer backend in backends/imgui_impl_opengl3.h and backends/imgui_impl_opengl3.cpp implements the actual GPU communication:

  • Creates a vertex array object (VAO) and vertex/index buffer objects (VBO/IBO) that persist across frames
  • Compiles and links a minimal vertex/fragment shader pair internally (you do not write these shaders)
  • Uploads vertex data via glBufferData and issues glDrawElements calls
  • Manages font texture creation via glTexImage2D

The backend includes imgui_impl_opengl3_loader.h, which abstracts GL function pointer loading and supports glad, gl3w, GLEW, or custom loaders.

Platform Backend

The platform backend (e.g., backends/imgui_impl_glfw.h for GLFW) handles OS windowing events, including mouse position, keyboard input, window resizing, clipboard access, and timing. You can substitute GLFW with SDL2 (imgui_impl_sdl2.h) or Win32 (imgui_impl_win32.h) depending on your application.

Required Files for OpenGL Integration

To set up Dear ImGui with OpenGL in your build system, include these specific files from the ocornut/imgui repository:

Reference implementations are available in examples/example_glfw_opengl3/main.cpp and examples/example_sdl2_opengl3/main.cpp.

Step-by-Step Integration Guide

1. Create an OpenGL Context

First, initialize your windowing library and request an OpenGL 3.2+ core profile context. The following example uses GLFW:

glfwInit();
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
GLFWwindow* window = glfwCreateWindow(1280, 720, "ImGui + OpenGL3", nullptr, nullptr);
glfwMakeContextCurrent(window);
glfwSwapInterval(1); // Enable vsync

2. Initialize the ImGui Context

Create the global ImGui context and configure default styling:

IMGUI_CHECKVERSION();
ImGui::CreateContext();
ImGuiIO& io = ImGui::GetIO(); (void)io;
ImGui::StyleColorsDark();

3. Initialize Platform and Renderer Backends

Initialize the platform backend first, then the OpenGL backend. The ImGui_ImplOpenGL3_Init function requires a GLSL version string matching your OpenGL context:

// Initialize GLFW platform backend
ImGui_ImplGlfw_InitForOpenGL(window, true);

// Initialize OpenGL renderer backend with appropriate GLSL version
const char* glsl_version = "#version 150"; // OpenGL 3.2 core
ImGui_ImplOpenGL3_Init(glsl_version);

Valid GLSL strings include "#version 130" (OpenGL 3.0), "#version 150" (OpenGL 3.2), or "#version 330 core" (OpenGL 3.3).

4. Implement the Main Render Loop

Each frame follows a strict three-part new-frame sequence, UI construction, and rendering phase:

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

    // Start the Dear ImGui frame
    ImGui_ImplOpenGL3_NewFrame();
    ImGui_ImplGlfw_NewFrame();
    ImGui::NewFrame();

    // ==== Build your UI here ====
    ImGui::Begin("Hello, ImGui!");
    ImGui::Text("This is rendered with OpenGL 3.");
    if (ImGui::Button("Click Me")) {
        // Handle interaction
    }
    ImGui::End();
    // ============================

    // Rendering
    ImGui::Render();
    int display_w, display_h;
    glfwGetFramebufferSize(window, &display_w, &display_h);
    glViewport(0, 0, display_w, display_h);
    glClearColor(0.45f, 0.55f, 0.60f, 1.00f);
    glClear(GL_COLOR_BUFFER_BIT);
    
    // Execute ImGui draw commands
    ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData());
    
    glfwSwapBuffers(window);
}

5. Cleanup and Shutdown

Release resources in reverse initialization order to prevent memory leaks:

ImGui_ImplOpenGL3_Shutdown();
ImGui_ImplGlfw_Shutdown();
ImGui::DestroyContext();
glfwDestroyWindow(window);
glfwTerminate();

Complete Working Example

Here is a minimal, compilable program integrating Dear ImGui with OpenGL 3 and GLFW, based on the official example in examples/example_glfw_opengl3/main.cpp:

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

int main()
{
    // 1. Setup window
    glfwInit();
    glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
    glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
    glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
    GLFWwindow* window = glfwCreateWindow(1280, 720, "Dear ImGui + OpenGL3 Example", nullptr, nullptr);
    glfwMakeContextCurrent(window);
    glfwSwapInterval(1);

    // 2. Setup Dear ImGui context
    IMGUI_CHECKVERSION();
    ImGui::CreateContext();
    ImGuiIO& io = ImGui::GetIO(); (void)io;
    ImGui::StyleColorsDark();

    // 3. Setup Platform/Renderer backends
    ImGui_ImplGlfw_InitForOpenGL(window, true);
    const char* glsl_version = "#version 150";
    ImGui_ImplOpenGL3_Init(glsl_version);

    // 4. Main loop
    while (!glfwWindowShouldClose(window))
    {
        glfwPollEvents();

        // Frame start
        ImGui_ImplOpenGL3_NewFrame();
        ImGui_ImplGlfw_NewFrame();
        ImGui::NewFrame();

        // UI Construction
        ImGui::Begin("Demo Window");
        ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate);
        ImGui::End();

        // Render
        ImGui::Render();
        int display_w, display_h;
        glfwGetFramebufferSize(window, &display_w, &display_h);
        glViewport(0, 0, display_w, display_h);
        glClearColor(0.45f, 0.55f, 0.60f, 1.00f);
        glClear(GL_COLOR_BUFFER_BIT);
        ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData());

        glfwSwapBuffers(window);
    }

    // 5. Cleanup
    ImGui_ImplOpenGL3_Shutdown();
    ImGui_ImplGlfw_Shutdown();
    ImGui::DestroyContext();
    glfwDestroyWindow(window);
    glfwTerminate();

    return 0;
}

Selecting the Correct GLSL Version

The glsl_version parameter passed to ImGui_ImplOpenGL3_Init must match the OpenGL context version you created:

  • OpenGL 3.0: "#version 130"
  • OpenGL 3.2 (core profile): "#version 150"
  • OpenGL 3.3+: "#version 330 core" or higher

Mismatching these versions results in shader compilation errors during ImGui_ImplOpenGL3_Init.

Summary

  • Dear ImGui requires two backends: a platform backend (GLFW/SDL/Win32) for input/windowing and the imgui_impl_opengl3 renderer backend for GPU output.
  • Initialization order matters: Create OpenGL context → Create ImGui context → Init platform backend → Init OpenGL backend.
  • Per-frame sequence: Call ImGui_ImplOpenGL3_NewFrame(), then platform NewFrame(), then ImGui::NewFrame(), build UI, call ImGui::Render(), and finally ImGui_ImplOpenGL3_RenderDrawData().
  • Cleanup in reverse: Shutdown OpenGL backend → Shutdown platform backend → Destroy ImGui context.
  • GLSL version strings must match your OpenGL context profile to ensure internal shaders compile correctly.

Frequently Asked Questions

Do I need to write custom OpenGL shaders to use Dear ImGui?

No. The imgui_impl_opengl3.cpp backend contains its own minimal vertex and fragment shaders that it compiles automatically during ImGui_ImplOpenGL3_Init. These shaders handle the anti-aliased font rendering and vertex color interpolation required by ImGui's draw lists. You only need to provide the correct GLSL version string.

Can I use Dear ImGui with OpenGL 2.1 or OpenGL ES?

Yes. The repository provides separate backends for legacy OpenGL 2 (imgui_impl_opengl2.h/cpp) and OpenGL ES 2/3 (imgui_impl_opengl3.h/cpp with appropriate GL loader configuration). Use imgui_impl_opengl2 for compatibility with older hardware, or ensure your GL loader in imgui_impl_opengl3_loader.h defines the necessary ES symbols when targeting mobile platforms.

Why is my Dear ImGui window blank or not rendering?

A blank screen typically indicates a mismatch between your OpenGL context version and the GLSL version string passed to ImGui_ImplOpenGL3_Init, or failure to call glfwMakeContextCurrent before initializing the backend. Ensure you have created a valid OpenGL context, specified the correct GLSL version (e.g., "#version 150" for OpenGL 3.2 core), and included the ImGui_ImplOpenGL3_RenderDrawData call after ImGui::Render in your main loop.

How do I handle DPI scaling with Dear ImGui and OpenGL?

Handle DPI scaling by detecting the framebuffer scale via your platform backend (e.g., glfwGetWindowContentScale for GLFW), then set io.DisplayFramebufferScale to the appropriate scale factor before calling ImGui::NewFrame. The OpenGL backend automatically adjusts vertex positions and font texture sampling to account for high-DPI displays when this scale is configured correctly.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →