Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import bgfx, nuklear, glfw3 as glfw
- import vs_nuklear_texture
- import fs_nuklear_texture
- import ../../graphics, ../../fpumath
- import ../../font/robotomono_regular.nim
- const MAX_VERTEX_BUFFER_SIZE = 512 * 1024
- const MAX_INDEX_BUFFER_SIZE = 128 * 1024
- template offsetof(typ, field): untyped = (var dummy: typ; cast[uint](addr(dummy.field)) - cast[uint](addr(dummy)))
- template alignof(typ) : uint =
- if sizeof(typ) > 1:
- offsetof(tuple[c: char, x: typ], x)
- else:
- 1
- type
- nk_bgfx_vertex* = object
- position: array[2, cfloat]
- uv: array[2, cfloat]
- col: array[4, nk_byte]
- type
- NuklearBGFXDevice = object
- cmds: nk_buffer
- vsh: ShaderHandle
- fsh: ShaderHandle
- sph: ProgramHandle
- vdecl: ptr VertexDecl
- uh: UniformHandle
- vbh: DynamicVertexBufferHandle
- ibh: DynamicIndexBufferHandle
- cc: nk_convert_config
- null: nk_draw_null_texture
- fah: TextureHandle
- vb: nk_buffer
- ib: nk_buffer
- NuklearBGFX* = object
- ctx*: nk_context
- dev*: NuklearBGFXDevice
- fa*: nk_font_atlas
- proc nk_bgfx_init*(nkbgfx: ptr NuklearBGFX) =
- nk_buffer_init_default(addr nkbgfx.dev.cmds)
- nkbgfx.dev.vsh = CreateShader(MakeRef(addr vs_nuklear_texture.vs[0], uint32_t sizeof(vs_nuklear_texture.vs)))
- nkbgfx.dev.fsh = CreateShader(MakeRef(addr fs_nuklear_texture.fs[0], uint32_t sizeof(fs_nuklear_texture.fs)))
- nkbgfx.dev.sph = CreateProgram(nkbgfx.dev.vsh, nkbgfx.dev.fsh)
- nkbgfx.dev.vdecl = createShared(VertexDecl)
- nkbgfx.dev.vdecl.Begin()
- nkbgfx.dev.vdecl.Add(bgfx.Attrib_Position, 2, bgfx.AttribType_Float)
- nkbgfx.dev.vdecl.Add(bgfx.Attrib_TexCoord0, 2, bgfx.AttribType_Float)
- nkbgfx.dev.vdecl.Add(bgfx.Attrib_Color0, 4, bgfx.AttribType_Uint8, true, false)
- nkbgfx.dev.vdecl.End()
- nkbgfx.dev.uh = CreateUniform("s_texColor", UniformType_Int1)
- var vertexLayout : seq[nk_draw_vertex_layout_element] = @[
- nk_draw_vertex_layout_element(
- attribute: NK_VERTEX_POSITION,
- format: NK_FORMAT_FLOAT,
- offset: nkbgfx.dev.vdecl.offset[Attrib_Position]
- ),
- nk_draw_vertex_layout_element(
- attribute: NK_VERTEX_TEXCOORD,
- format: NK_FORMAT_FLOAT,
- offset: nkbgfx.dev.vdecl.offset[Attrib_TexCoord0]
- ),
- nk_draw_vertex_layout_element(
- attribute: NK_VERTEX_COLOR,
- format: NK_FORMAT_R8G8B8A8,
- offset: nkbgfx.dev.vdecl.offset[Attrib_Color0]
- ),
- nk_draw_vertex_layout_element(
- attribute: NK_VERTEX_ATTRIBUTE_COUNT,
- format: NK_FORMAT_COUNT,
- offset: 0
- )
- ]
- nkbgfx.dev.vbh = CreateDynamicVertexBuffer(MAX_VERTEX_BUFFER_SIZE, nkbgfx.dev.vdecl, BGFX_BUFFER_ALLOW_RESIZE)
- nkbgfx.dev.ibh = CreateDynamicIndexBuffer(MAX_INDEX_BUFFER_SIZE, BGFX_BUFFER_ALLOW_RESIZE)
- nkbgfx.dev.cc.vertex_layout = addr vertexLayout[0]
- nkbgfx.dev.cc.vertex_size = nk_size sizeof(nk_bgfx_vertex)
- nkbgfx.dev.cc.vertex_alignment = alignof(nk_bgfx_vertex)
- nkbgfx.dev.cc.null = nkbgfx.dev.null
- nkbgfx.dev.cc.circle_segment_count = 22
- nkbgfx.dev.cc.curve_segment_count = 22
- nkbgfx.dev.cc.arc_segment_count = 22
- nkbgfx.dev.cc.global_alpha = 1.0
- nkbgfx.dev.cc.shape_AA = NK_ANTIALIASING_ON
- nkbgfx.dev.cc.line_AA = NK_ANTIALIASING_ON
- nk_font_atlas_init_default(addr nkbgfx.fa)
- nk_font_atlas_begin(addr nkbgfx.fa)
- let roboto_ttf = addr s_robotoMonoRegularTtf
- var font = nk_font_atlas_add_from_memory(addr nkbgfx.fa, roboto_ttf, uint sizeof(s_robotoMonoRegularTtf), 13, nil)
- # Uncomment for default font
- #var font = nk_font_atlas_add_default(addr fa, 13, nil)
- var w, h : cint
- let image = nk_font_atlas_bake(addr nkbgfx.fa, addr w, addr h, NK_FONT_ATLAS_RGBA32)
- let size : uint32_t = uint32_t(w * h * 4)
- var mem : ptr bgfx.Memory = bgfx.Alloc(size)
- copymem(mem.data, image, size)
- nkbgfx.dev.fah = CreateTexture2D(uint16_t w, uint16_t h, false, 1, TextureFormat_RGBA8, 0, mem)
- nk_font_atlas_end(addr nkbgfx.fa, nk_handle_ptr(addr nkbgfx.dev.fah), addr nkbgfx.dev.null)
- discard nk_init_default(addr nkbgfx.ctx, addr font.handle)
- proc nk_bgfx_render*(nkbgfx: var NuklearBGFX) =
- var width, height : cint
- var displayWidth, displayHeight : cint
- glfw.GetWindowSize(graphics.rootWindow, addr width, addr height);
- glfw.GetFramebufferSize(graphics.rootWindow, addr displayWidth, addr displayHeight)
- var ortho : Mat4
- mtxOrtho(ortho, 0.0, float displayWidth, float displayHeight, 0.0, 0.0, 1.0)
- SetViewRect(uint8_t 0, uint16_t 0, uint16_t 0, uint16_t displayWidth, uint16_t displayHeight)
- SetViewTransform(uint8_t 0, nil, addr ortho[0])
- var scale : nuk_vec2
- scale.x = float(displayWidth) / float(width)
- scale.y = float(displayHeight) / float(height)
- nk_buffer_init_default(addr nkbgfx.dev.vb)
- nk_buffer_init_default(addr nkbgfx.dev.ib)
- nk_convert(addr nkbgfx.ctx, addr nkbgfx.dev.cmds, addr nkbgfx.dev.vb, addr nkbgfx.dev.ib, addr nkbgfx.dev.cc)
- let vertexData = nkbgfx.dev.vb.memory.`ptr`
- let elementData = nkbgfx.dev.ib.memory.`ptr`
- let vertexDataSize = nkbgfx.dev.vb.allocated
- let elementDataSize = nkbgfx.dev.ib.allocated
- let vertexMemory = MakeRef(vertexData, uint32_t vertexDataSize)
- let elementMemory = MakeRef(elementdata, uint32_t elementDataSize)
- UpdateDynamicVertexBuffer(nkbgfx.dev.vbh, 0, vertexMemory)
- UpdateDynamicIndexBuffer(nkbgfx.dev.ibh, 0, elementMemory)
- var offset : uint32_t = 0
- var vertexCount = uint32_t(vertexDataSize div nkbgfx.dev.vdecl.stride)
- var cmd : ptr nk_draw_command = nk_draw_begin(addr nkbgfx.ctx, addr nkbgfx.dev.cmds)
- while not isNil(cmd):
- SetState( BGFX_STATE_RGB_WRITE or BGFX_STATE_ALPHA_WRITE or BGFX_STATE_BLEND_EQUATION_ADD or
- BGFX_STATE_BLEND_FUNC( BGFX_STATE_BLEND_SRC_ALPHA, BGFX_STATE_BLEND_INV_SRC_ALPHA ) )
- if not cmd.texture.`ptr`.isNil:
- let textureHandle = cast[ptr TextureHandle](cmd.texture.`ptr`)[]
- SetTexture(0, nkbgfx.dev.uh, textureHandle)
- SetVertexBuffer( nkbgfx.dev.vbh, 0, vertexCount )
- SetIndexBuffer( nkbgfx.dev.ibh, offset, cmd.elem_count)
- Submit(0, nkbgfx.dev.sph)
- offset += cmd.elem_count
- cmd = nk_draw_next(cmd, addr nkbgfx.dev.cmds, addr nkbgfx.ctx)
- nk_clear(addr nkbgfx.ctx)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement