Skip to content

Using libGDX

Catvert edited this page Feb 19, 2018 · 15 revisions

Setup

First of all, we need to use the LWJGL3 backend in our project to be able to use imgui. To do this, I recommend using gdx-setup by czyzby which allows you to easily add LWJGL3 to your new project.

Once the project is imported in your favorite IDE, go to the build.gradle file located in the root of your project. Then add the following repositories in the subprojects block:

subprojects {
  ...
  repositories {
    ...
    maven { url 'https://jitpack.io' }
    maven { url "https://dl.bintray.com/kotlin/kotlin-dev" } // Required since imgui uses version 1.2 of Kotlin
  }
}

Next, go to the build.gradle file located in the core module and add the following dependencies:

dependencies {
  ...
  compile "com.badlogicgames.gdx:gdx-backend-lwjgl3:$gdxVersion"
  compile "com.github.kotlin-graphics:imgui:-SNAPSHOT"
}

Now, check if all the gradle dependencies have been recovered (Idea -> View -> Window Tool -> Gradle -> Force refresh all linked Gradle projects)

All that remains is to initialize imgui.

First of all, you have to create a Context object and, for example, store it in your game class.

val ctx = Context()

Then, add at the end of the create method in your game class :

LwjglGL3.init(GlfwWindow((Gdx.graphics as Lwjgl3Graphics).window.windowHandle), false)

In the render method:

super.render()
Gdx.gl.glClearColor(0f, 0f, 0f, 1f)
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT or GL20.GL_DEPTH_BUFFER_BIT)

LwjglGL3.newFrame()

ImGui.text("Hi")

ImGui.render()

if(ImGui.drawData != null)
  LwjglGL3.renderDrawData(ImGui.drawData!!)

Finally, do not forget to dispose imgui in the dispose method:

LwjglGL3.shutdown()
ctx.destroy()

That's all!

Using imgui image with libGDX texture

In order to use image and imageButton from imgui, we need to recover the ID handle from our texture in order to be able to pass it to imgui.

To retrieve this handle, just call the getTextureObjectHandle method of our texture and pass the result to imgui for the userTextureId as for example:

ImGui.image(texture.textureObjectHandle, Vec2(imageWidth, imageHeight))

Input callbacks

To be able to use imgui inputs with libGDX, you must first create an InputProcessor or an InputAdapter in order to send the various callback to imgui.

Here is an example of the implementation :

class ImGuiInputProcessor : InputAdapter() {
    private val gdxGLFWKeyMap = mutableMapOf<Int, Int>()

    init {
        gdxGLFWKeyMap[Input.Keys.TAB] = GLFW.GLFW_KEY_TAB

        gdxGLFWKeyMap[Input.Keys.LEFT] = GLFW.GLFW_KEY_LEFT
        gdxGLFWKeyMap[Input.Keys.RIGHT] = GLFW.GLFW_KEY_RIGHT
        gdxGLFWKeyMap[Input.Keys.UP] = GLFW.GLFW_KEY_UP
        gdxGLFWKeyMap[Input.Keys.DOWN] = GLFW.GLFW_KEY_DOWN

        gdxGLFWKeyMap[Input.Keys.PAGE_UP] = GLFW.GLFW_KEY_PAGE_UP
        gdxGLFWKeyMap[Input.Keys.PAGE_DOWN] = GLFW.GLFW_KEY_PAGE_DOWN

        gdxGLFWKeyMap[Input.Keys.HOME] = GLFW.GLFW_KEY_HOME
        gdxGLFWKeyMap[Input.Keys.END] = GLFW.GLFW_KEY_END

        gdxGLFWKeyMap[Input.Keys.BACKSPACE] = GLFW.GLFW_KEY_BACKSPACE

        gdxGLFWKeyMap[Input.Keys.ENTER] = GLFW.GLFW_KEY_ENTER
        gdxGLFWKeyMap[Input.Keys.ESCAPE] = GLFW.GLFW_KEY_ESCAPE

        gdxGLFWKeyMap[Input.Keys.CONTROL_LEFT] = GLFW.GLFW_KEY_LEFT_CONTROL
        gdxGLFWKeyMap[Input.Keys.CONTROL_RIGHT] = GLFW.GLFW_KEY_RIGHT_CONTROL
        gdxGLFWKeyMap[Input.Keys.ALT_LEFT] = GLFW.GLFW_KEY_LEFT_ALT
        gdxGLFWKeyMap[Input.Keys.ALT_RIGHT] = GLFW.GLFW_KEY_RIGHT_ALT
        gdxGLFWKeyMap[Input.Keys.SHIFT_LEFT] = GLFW.GLFW_KEY_LEFT_SHIFT
        gdxGLFWKeyMap[Input.Keys.SHIFT_RIGHT] = GLFW.GLFW_KEY_RIGHT_SHIFT

        gdxGLFWKeyMap[Input.Keys.A] = GLFW.GLFW_KEY_A
        gdxGLFWKeyMap[Input.Keys.C] = GLFW.GLFW_KEY_C
        gdxGLFWKeyMap[Input.Keys.V] = GLFW.GLFW_KEY_V
        gdxGLFWKeyMap[Input.Keys.X] = GLFW.GLFW_KEY_X
        gdxGLFWKeyMap[Input.Keys.Y] = GLFW.GLFW_KEY_Y
        gdxGLFWKeyMap[Input.Keys.Z] = GLFW.GLFW_KEY_Z
    }

    override fun keyTyped(character: Char): Boolean {
        LwjglGL3.charCallback(character.toInt())
        return false
    }

    override fun scrolled(amount: Int): Boolean {
        LwjglGL3.scrollCallback(Vec2d(0, -amount))
        return false
    }

    override fun touchUp(screenX: Int, screenY: Int, pointer: Int, button: Int): Boolean {
        LwjglGL3.mouseButtonCallback(button, GLFW.GLFW_PRESS, 0)
        return false
    }

    override fun keyUp(keycode: Int): Boolean {
        gdxGLFWKeyMap[keycode]?.apply {
            LwjglGL3.keyCallback(this, 0, GLFW.GLFW_RELEASE, 0)
        }
        return false
    }

    override fun keyDown(keycode: Int): Boolean {
         gdxGLFWKeyMap[keycode]?.apply {
            LwjglGL3.keyCallback(this, 0, GLFW.GLFW_PRESS, 0)
        }
        return false
    }
}

Then, add this input processor in libGDX :

Gdx.input.inputProcessor = ImGuiInputProcessor()

Or with a multiplexer to be able to use it with a stage :

Gdx.input.inputProcessor = InputMultiplexer(stage, ImGuiInputProcessor())
Clone this wiki locally