mirror of
https://github.com/Drezil/dear-imgui.hs.git
synced 2025-07-20 11:43:15 +02:00
Extended font & glyph support (#114)
* Separate font utils, add glyph support (#113) * Implement font glyph ranges builder * Implement raw font config binds * Implement font atlas module * Rewrite font altas rebuilder in Managed
This commit is contained in:
150
examples/fonts/Main.hs
Normal file
150
examples/fonts/Main.hs
Normal file
@ -0,0 +1,150 @@
|
||||
{-# language BlockArguments #-}
|
||||
{-# language LambdaCase #-}
|
||||
{-# language OverloadedStrings #-}
|
||||
{-# language RecordWildCards #-}
|
||||
{-# language NamedFieldPuns #-}
|
||||
{-# language DeriveTraversable #-}
|
||||
|
||||
{- | Font usage example.
|
||||
|
||||
Loads two non-standard fonts
|
||||
|
||||
This example uses NotoSansJP-Regular.otf from Google Fonts
|
||||
Licensed under the SIL Open Font License, Version 1.1
|
||||
https://fonts.google.com/noto/specimen/Noto+Sans+JP
|
||||
-}
|
||||
|
||||
module Main ( main ) where
|
||||
|
||||
import Control.Exception
|
||||
import Control.Monad
|
||||
import Control.Monad.IO.Class
|
||||
import Control.Monad.Managed
|
||||
import Data.IORef
|
||||
import DearImGui
|
||||
import qualified DearImGui.FontAtlas as FontAtlas
|
||||
import DearImGui.OpenGL2
|
||||
import DearImGui.SDL
|
||||
import DearImGui.SDL.OpenGL
|
||||
import Graphics.GL
|
||||
import SDL
|
||||
|
||||
-- Rebuild syntax enables us to keep fonts in any
|
||||
-- traversable type, so let's make our life a little easier.
|
||||
-- But feel free to use lists or maps.
|
||||
data FontSet a = FontSet
|
||||
{ droidFont :: a
|
||||
, defaultFont :: a
|
||||
, notoFont :: a
|
||||
}
|
||||
deriving (Functor, Foldable, Traversable)
|
||||
|
||||
main :: IO ()
|
||||
main = do
|
||||
-- Window initialization is similar to another examples.
|
||||
initializeAll
|
||||
runManaged do
|
||||
window <- do
|
||||
let title = "Hello, Dear ImGui!"
|
||||
let config = defaultWindow { windowGraphicsContext = OpenGLContext defaultOpenGL }
|
||||
managed $ bracket (createWindow title config) destroyWindow
|
||||
glContext <- managed $ bracket (glCreateContext window) glDeleteContext
|
||||
_ <- managed $ bracket createContext destroyContext
|
||||
_ <- managed_ $ bracket_ (sdl2InitForOpenGL window glContext) sdl2Shutdown
|
||||
_ <- managed_ $ bracket_ openGL2Init openGL2Shutdown
|
||||
|
||||
-- We use high-level syntax to build font atlas and
|
||||
-- get handles to use in the main loop.
|
||||
fontSet <- FontAtlas.rebuild FontSet
|
||||
{ -- The first mentioned font is loaded first
|
||||
-- and set as a global default.
|
||||
droidFont =
|
||||
FontAtlas.FromTTF
|
||||
"./imgui/misc/fonts/DroidSans.ttf"
|
||||
15
|
||||
Nothing
|
||||
FontAtlas.Cyrillic
|
||||
|
||||
-- You also may use a default hardcoded font for
|
||||
-- some purposes (i.e. as fallback)
|
||||
, defaultFont =
|
||||
FontAtlas.DefaultFont
|
||||
|
||||
-- To optimize atlas size, use ranges builder and
|
||||
-- provide source localization data.
|
||||
, notoFont =
|
||||
FontAtlas.FromTTF
|
||||
"./examples/fonts/NotoSansJP-Regular.otf"
|
||||
20
|
||||
Nothing
|
||||
( FontAtlas.RangesBuilder $ mconcat
|
||||
[ FontAtlas.addRanges FontAtlas.Latin
|
||||
, FontAtlas.addText "私をクリックしてください"
|
||||
, FontAtlas.addText "こんにちは"
|
||||
]
|
||||
)
|
||||
}
|
||||
|
||||
liftIO $ do
|
||||
fontFlag <- newIORef False
|
||||
mainLoop window do
|
||||
let FontSet{..} = fontSet
|
||||
withWindowOpen "Hello, ImGui!" do
|
||||
-- To use a font for widget text, you may either put it
|
||||
-- into a 'withFont' block:
|
||||
withFont defaultFont do
|
||||
text "Hello, ImGui!"
|
||||
|
||||
text "Привет, ImGui!"
|
||||
|
||||
-- ...or you can explicitly push and pop a font.
|
||||
-- Though it's not recommended.
|
||||
toggled <- readIORef fontFlag
|
||||
|
||||
when toggled $
|
||||
pushFont notoFont
|
||||
|
||||
-- Some of those are only present in Noto font range
|
||||
-- and will render as `?`s.
|
||||
text "こんにちは, ImGui!"
|
||||
|
||||
let buttonText = if toggled then "私をクリックしてください" else "Click Me!"
|
||||
button buttonText >>= \clicked ->
|
||||
when clicked $
|
||||
modifyIORef' fontFlag not
|
||||
|
||||
when toggled
|
||||
popFont
|
||||
|
||||
showDemoWindow
|
||||
|
||||
mainLoop :: Window -> IO () -> IO ()
|
||||
mainLoop window frameAction = loop
|
||||
where
|
||||
loop = unlessQuit do
|
||||
openGL2NewFrame
|
||||
sdl2NewFrame
|
||||
newFrame
|
||||
|
||||
frameAction
|
||||
|
||||
glClear GL_COLOR_BUFFER_BIT
|
||||
render
|
||||
openGL2RenderDrawData =<< getDrawData
|
||||
glSwapWindow window
|
||||
|
||||
loop
|
||||
|
||||
unlessQuit action = do
|
||||
shouldQuit <- checkEvents
|
||||
if shouldQuit then pure () else action
|
||||
|
||||
checkEvents = do
|
||||
pollEventWithImGui >>= \case
|
||||
Nothing ->
|
||||
return False
|
||||
Just event ->
|
||||
(isQuit event ||) <$> checkEvents
|
||||
|
||||
isQuit event =
|
||||
SDL.eventPayload event == SDL.QuitEvent
|
BIN
examples/fonts/NotoSansJP-Regular.otf
Normal file
BIN
examples/fonts/NotoSansJP-Regular.otf
Normal file
Binary file not shown.
@ -134,12 +134,6 @@ app = do
|
||||
ImGui.createContext
|
||||
ImGui.destroyContext
|
||||
|
||||
logDebug "Adding fonts"
|
||||
ImGui.clearFontAtlas
|
||||
_default <- ImGui.addFontDefault
|
||||
_custom <- ImGui.addFontFromFileTTF "imgui/misc/fonts/ProggyTiny.ttf" 10
|
||||
ImGui.buildFontAtlas
|
||||
|
||||
let
|
||||
preferredFormat :: Vulkan.SurfaceFormatKHR
|
||||
preferredFormat =
|
||||
|
Reference in New Issue
Block a user