treeform / windy

Windowing library for Nim using OS native APIs.
MIT License
114 stars 16 forks source link

ImGui implementation example #80

Open Patitotective opened 2 years ago

Patitotective commented 2 years ago

I just discovered windy and it looks like a promising library. And I'd really like to use windy instead of GLFW for ImGui but I haven't got it working.

Here's the example I'd like to work with windy ```nim import nimgl/[opengl, glfw] import nimgl/imgui, nimgl/imgui/[impl_opengl, impl_glfw] proc main() = doAssert glfwInit() glfwWindowHint(GLFWContextVersionMajor, 3) glfwWindowHint(GLFWContextVersionMinor, 3) glfwWindowHint(GLFWOpenglForwardCompat, GLFW_TRUE) glfwWindowHint(GLFWOpenglProfile, GLFW_OPENGL_CORE_PROFILE) glfwWindowHint(GLFWResizable, GLFW_TRUE) var win: GLFWWindow = glfwCreateWindow(600, 400, "Example") if win == nil: quit(-1) win.makeContextCurrent() doAssert glInit() let context = igCreateContext() #let io = igGetIO() doAssert igGlfwInitForOpenGL(win, true) doAssert igOpenGL3Init() igStyleColorsCherry() var somefloat: float32 = 0.0f var counter: int32 = 0 while not win.windowShouldClose: glfwPollEvents() igOpenGL3NewFrame() igGlfwNewFrame() igNewFrame() # Simple window igBegin("Hello, world!") igText("This is some useful text.") igSliderFloat("float", somefloat.addr, 0.0f, 1.0f) if igButton("Button", ImVec2(x: 0, y: 0)): counter.inc igSameLine() igText("counter = %d", counter) igText("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / igGetIO().framerate, igGetIO().framerate) igEnd() # End simple window igRender() glClearColor(0.45f, 0.55f, 0.60f, 1.00f) glClear(GL_COLOR_BUFFER_BIT) igOpenGL3RenderDrawData(igGetDrawData()) win.swapBuffers() igOpenGL3Shutdown() igGlfwShutdown() context.igDestroyContext() win.destroyWindow() glfwTerminate() when isMainModule: main() ```
treeform commented 2 years ago

What have you tried so far? Where do you run into issues?

Patitotective commented 2 years ago

I get a bit confused since windy uses opengl but ImGui uses nimgl/opengl This is how the code looks:

import windy
import opengl
import nimgl/imgui

let window = newWindow("Windy Example", ivec2(1280, 800))

window.makeContextCurrent()
loadExtensions()

let context = igCreateContext()
#let io = igGetIO()

proc display() =
  glClear(GL_COLOR_BUFFER_BIT)
  # Your OpenGL display code here
  # igOpenGL3NewFrame()
  # igGlfwNewFrame()
  igNewFrame()

  var somefloat: float32 = 0.0f
  var counter: int32 = 0

  # Begin
  igBegin("Hello, world!")

  igText("This is some useful text.")

  igSliderFloat("float", somefloat.addr, 0.0f, 1.0f)

  if igButton("Button", ImVec2(x: 0, y: 0)):
    counter.inc
  igSameLine()
  igText("counter = %d", counter)

  igText("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / igGetIO().framerate, igGetIO().framerate)
  igEnd()
  # End

  igRender()

  glClearColor(0.45f, 0.55f, 0.60f, 1.00f)
  glClear(GL_COLOR_BUFFER_BIT)

  # igOpenGL3RenderDrawData(igGetDrawData())

  window.swapBuffers()

while not window.closeRequested:
  display()
  pollEvents()

# igOpenGL3Shutdown()
# igGlfwShutdown()
context.igDestroyContext()

# window.destroyWindow()
# glfwTerminate()
trial: /home/cristobal/.nimble/pkgs/nimgl-1.3.2/nimgl/private/cimgui/imgui/imgui.cpp:7229: void ImGui::ErrorCheckNewFrameSanityChecks(): Assertion `g.IO.DisplaySize.x >= 0.0f && g.IO.DisplaySize.y >= 0.0f && "Invalid DisplaySize value!"' failed.
Traceback (most recent call last)
/home/cristobal/.../trial.nim(49) trial
/home/cristobal/.../trial.nim(18) display
SIGABRT: Abnormal termination.
Aborted (core dumped)
Error: execution of an external program failed: '/home/cristobal/.../trial '
treeform commented 2 years ago

This seems like an issue with imgui, it does not know the side of the frame. It almost feels like igNewFrame should take a frame size or some thing should have set it. It looks like its set manually here: https://github.com/nimgl/imgui/blob/master/src/imgui/impl_glfw.nim#L190-L191

Patitotective commented 2 years ago

It still asks for ImGui_ImplXXXX_NewFrame (igGlfwNewFrame i think)

import windy
import opengl
import nimgl/imgui

let window = newWindow("Windy Example", ivec2(1280, 800))
window.makeContextCurrent()
loadExtensions()

let context = igCreateContext()
let io = igGetIO()

proc igWindyNewFrame() = 
  assert io.fonts.isBuilt()

  var s = window.size
  var displayS = window.framebufferSize()

  io.displaySize = ImVec2(x: s.x.float32, y: s.y.float32)
  io.displayFramebufferScale = ImVec2(x: if s.x > 0: displayS.x.float32 / s.x.float32 else: 0.0f, y: if s.y > 0: displayS.y.float32 / s.y.float32 else: 0.0f)

  io.deltaTime = (1.0f / 60.0f).float32

  # igGlfwUpdateMousePosAndButtons()
  # igGlfwUpdateMouseCursor()

proc display() =
  glClear(GL_COLOR_BUFFER_BIT)
  # Your OpenGL display code here
  # igOpenGL3NewFrame()
  # igGlfwNewFrame()
  igWindyNewFrame()
  igNewFrame()

  var somefloat: float32 = 0.0f
  var counter: int32 = 0

  # Begin
  igBegin("Hello, world!")

  igText("This is some useful text.")

  igSliderFloat("float", somefloat.addr, 0.0f, 1.0f)

  if igButton("Button", ImVec2(x: 0, y: 0)):
    counter.inc
  igSameLine()
  igText("counter = %d", counter)

  igText("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / igGetIO().framerate, igGetIO().framerate)
  igEnd()
  # End

  igRender()

  glClearColor(0.45f, 0.55f, 0.60f, 1.00f)
  glClear(GL_COLOR_BUFFER_BIT)

  # igOpenGL3RenderDrawData(igGetDrawData())

  window.swapBuffers()

while not window.closeRequested:
  display()
  pollEvents()

# igOpenGL3Shutdown()
# igGlfwShutdown()
context.igDestroyContext()

# window.destroyWindow()
# glfwTerminate()
trial: /home/cristobal/.nimble/pkgs/nimgl-1.3.2/nimgl/private/cimgui/imgui/imgui.cpp:7230: void ImGui::ErrorCheckNewFrameSanityChecks(): Assertion `g.IO.Fonts->IsBuilt() && "Font Atlas not built! Make sure you called ImGui_ImplXXXX_NewFrame() function for renderer backend, which should call io.Fonts->GetTexDataAsRGBA32() / GetTexDataAsAlpha8()"' failed.
Traceback (most recent call last)
/home/cristobal/minidev/.../trial.nim(65) trial
/home/cristobal/minidev/.../trial.nim(34) display
SIGABRT: Abnormal termination.
Aborted (core dumped)
Error: execution of an external program failed: '/home/cristobal/minidev/.../trial '
treeform commented 2 years ago

Sorry, I just don't know how ImGui works in order to help you.