Skip to content

imgui_md: post-1.92, line wrapping does not behave as expected #366

@bgribble

Description

@bgribble

Hi, I am porting my code to 1.92 and I have come across a change in the behavior of imgui_md that I haven't been able to trace back to a commit.

Paragraphs of text are not line-wrapped as expected. A paragraph with no newlines is not wrapped at all; soft newlines within the paragraph are sometimes used as wrap points, but not always (only when the preceding gline "should" have already been wrapped) and are off by one character.

Runnable example. I would expect the 2 paragraphs of Lorem Ipsum to be formatted similarly (the second one is shorter, but the first few lines should be the same)

from imgui_bundle import imgui
from imgui_bundle import imgui_md as markdown
from imgui_bundle.python_backends.sdl2_backend import SDL2Renderer

import OpenGL.GL as gl  # type: ignore
from sdl2 import *  # type: ignore
import ctypes
import sys

md_text = """

Soft newlines seem to be the only
point where line wraps
can occur, but they don't always cause them
and they seem 
to be off by one char

Lorem ipsum dolor sit amet, consectetur adipiscing elit. Cras interdum diam id lorem tincidunt vulputate. Mauris quam mi, aliquam pretium sapien vitae, laoreet pellentesque libero. Sed lobortis eu mi quis tincidunt. Vivamus erat purus, fringilla vel mauris sit amet, rutrum maximus erat. Praesent vitae nulla euismod, rhoncus turpis ut, vulputate turpis. Donec euismod in massa vitae scelerisque. Nunc ac urna sit amet ex scelerisque rhoncus. Donec convallis sem et pretium scelerisque. Quisque libero dolor, euismod et tortor quis, euismod vehicula urna. Proin posuere ultrices tortor, at commodo enim volutpat tristique.

Lorem ipsum dolor sit amet, consectetur 
adipiscing elit. Cras interdum diam id lorem 
tincidunt vulputate. Mauris quam mi, aliquam 
pretium sapien vitae, laoreet pellentesque libero. 
Sed lobortis eu mi quis tincidunt. Vivamus erat purus, 
fringilla vel mauris sit amet, rutrum maximus erat. 
"""


def div_callback(*args, **kwargs):
    return True

def main():
    window, gl_context = impl_pysdl2_init()
    imgui.create_context()
    impl = SDL2Renderer(window)

    running = True
    event = SDL_Event()

    io = imgui.get_io()
    imgui.backends.opengl3_init("#version 100")
    io.fonts.clear()
    io.fonts.add_font_default()

    md_options = markdown.MarkdownOptions()
    md_options.callbacks.on_html_div = div_callback
    md_options.font_options.regular_size = 16
    markdown.initialize_markdown(md_options)
    font_loader = markdown.get_font_loader_function()
    font_loader()

    imgui.backends.opengl3_new_frame()
    while running:
        while SDL_PollEvent(ctypes.byref(event)) != 0:
            if event.type == SDL_QUIT:
                running = False
                break
            impl.process_event(event)
        impl.process_inputs()

        imgui.new_frame()

        imgui.begin("content")
        imgui.text("Problem with imgui_md wrapping text in a paragraph")

        imgui.dummy((1, 6))
        markdown.render(md_text)

        imgui.end()

        gl.glClearColor(1.0, 1.0, 1.0, 1)
        gl.glClear(gl.GL_COLOR_BUFFER_BIT)

        imgui.render()
        impl.render(imgui.get_draw_data())
        SDL_GL_SwapWindow(window)


    impl.shutdown()
    SDL_GL_DeleteContext(gl_context)
    SDL_DestroyWindow(window)
    SDL_Quit()


def impl_pysdl2_init():
    width, height = 1280, 720
    window_name = "minimal ImGui/SDL2 example"

    if SDL_Init(SDL_INIT_EVERYTHING) < 0:
        print(
            "Error: SDL could not initialize! SDL Error: "
            + SDL_GetError().decode("utf-8")
        )
        sys.exit(1)

    SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1)
    SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24)
    SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, 8)
    SDL_GL_SetAttribute(SDL_GL_ACCELERATED_VISUAL, 1)
    SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 1)
    SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, 8)
    SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, SDL_GL_CONTEXT_FORWARD_COMPATIBLE_FLAG)
    SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 4)
    SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 1)
    SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_CORE)

    SDL_SetHint(SDL_HINT_MAC_CTRL_CLICK_EMULATE_RIGHT_CLICK, b"1")
    SDL_SetHint(SDL_HINT_VIDEO_HIGHDPI_DISABLED, b"1")
    SDL_SetHint(SDL_HINT_VIDEODRIVER, b"wayland,x11")
    SDL_SetHint(SDL_HINT_VIDEO_X11_FORCE_EGL, b"1")

    window = SDL_CreateWindow(
        window_name.encode("utf-8"),
        SDL_WINDOWPOS_CENTERED,
        SDL_WINDOWPOS_CENTERED,
        width,
        height,
        SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE,
    )

    if window is None:
        print(
            "Error: Window could not be created! SDL Error: "
            + SDL_GetError().decode("utf-8")
        )
        sys.exit(1)

    gl_context = SDL_GL_CreateContext(window)
    if gl_context is None:
        print(
            "Error: Cannot create OpenGL Context! SDL Error: "
            + SDL_GetError().decode("utf-8")
        )
        sys.exit(1)

    SDL_GL_MakeCurrent(window, gl_context)
    if SDL_GL_SetSwapInterval(1) < 0:
        print(
            "Warning: Unable to set VSync! SDL Error: " + SDL_GetError().decode("utf-8")
        )
        sys.exit(1)

    return window, gl_contex


if __name__ == "__main__":
    main()

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions