mirror of
https://github.com/vlang/v.git
synced 2023-08-10 21:13:21 +03:00
new gg/freetype modules with sokol/fontstash backends
This commit is contained in:
parent
43ba6766ba
commit
0502a54a36
50
examples/gg2.v
Normal file
50
examples/gg2.v
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
module main
|
||||||
|
|
||||||
|
import gg2 // as gg
|
||||||
|
import gx
|
||||||
|
|
||||||
|
const (
|
||||||
|
win_width = 600
|
||||||
|
win_height = 300
|
||||||
|
)
|
||||||
|
|
||||||
|
struct App {
|
||||||
|
mut:
|
||||||
|
gg &gg2.GG
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
mut app := &App{}
|
||||||
|
app.gg = gg2.new_context({
|
||||||
|
bg_color: gx.white
|
||||||
|
width: win_width
|
||||||
|
height: win_height
|
||||||
|
use_ortho: true // This is needed for 2D drawing
|
||||||
|
create_window: true
|
||||||
|
window_title: 'Empty window'
|
||||||
|
frame_fn: frame
|
||||||
|
user_data: app
|
||||||
|
font_path: 'examples/tetris/RobotoMono-Regular.ttf'
|
||||||
|
})
|
||||||
|
app.gg.run()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn frame(user_data voidptr) {
|
||||||
|
mut app := &App(user_data)
|
||||||
|
mut gg := app.gg
|
||||||
|
gg.begin()
|
||||||
|
if gg.fons == 0 {
|
||||||
|
gg.init_font()
|
||||||
|
}
|
||||||
|
app.draw()
|
||||||
|
C.sfons_flush(gg.fons)
|
||||||
|
gg.end()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn (app &App) draw() {
|
||||||
|
app.gg.draw_text_def(200,20, 'hello world!')
|
||||||
|
app.gg.draw_text_def(300,300, 'привет')
|
||||||
|
app.gg.draw_rect(10, 10, 100, 30, gx.blue)
|
||||||
|
app.gg.draw_empty_rect(10, 150, 80, 40, gx.green)
|
||||||
|
}
|
||||||
|
|
@ -52,7 +52,7 @@ fn init(user_data voidptr) {
|
|||||||
})
|
})
|
||||||
s := &C.sgl_desc_t{}
|
s := &C.sgl_desc_t{}
|
||||||
C.sgl_setup(s)
|
C.sgl_setup(s)
|
||||||
state.fons = C.sfons_create(512, 512, 1)
|
state.fons = sfons.create(512, 512, 1)
|
||||||
// or use DroidSerif-Regular.ttf
|
// or use DroidSerif-Regular.ttf
|
||||||
if bytes := os.read_bytes(os.resource_abs_path('assets/ProggyTiny.ttf')) {
|
if bytes := os.read_bytes(os.resource_abs_path('assets/ProggyTiny.ttf')) {
|
||||||
println('loaded font: $bytes.len')
|
println('loaded font: $bytes.len')
|
||||||
|
@ -561,3 +561,12 @@ fn test_push_many_self() {
|
|||||||
assert actual_arr[i] == expected_arr[i]
|
assert actual_arr[i] == expected_arr[i]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn test_for() {
|
||||||
|
nums := [1,2,3]
|
||||||
|
mut sum := 0
|
||||||
|
for num <- nums {
|
||||||
|
sum += num
|
||||||
|
}
|
||||||
|
assert sum == 6
|
||||||
|
}
|
||||||
|
@ -446,7 +446,7 @@ fn (p mut Parser) parse(pass Pass) {
|
|||||||
}
|
}
|
||||||
p.fgen_nl()
|
p.fgen_nl()
|
||||||
p.builtin_mod = p.mod == 'builtin'
|
p.builtin_mod = p.mod == 'builtin'
|
||||||
p.can_chash = p.mod in ['ui', 'uiold', 'darwin', 'clipboard', 'webview'] // TODO tmp remove
|
p.can_chash = p.mod in ['gg2', 'ui', 'uiold', 'darwin', 'clipboard', 'webview'] // TODO tmp remove
|
||||||
// Import pass - the first and the smallest pass that only analyzes imports
|
// Import pass - the first and the smallest pass that only analyzes imports
|
||||||
// if we are a building module get the full module name from v.mod
|
// if we are a building module get the full module name from v.mod
|
||||||
fq_mod := if p.pref.build_mode == .build_module && p.v.mod.ends_with(p.mod) { p.v.mod }
|
fq_mod := if p.pref.build_mode == .build_module && p.v.mod.ends_with(p.mod) { p.v.mod }
|
||||||
@ -544,10 +544,9 @@ fn (p mut Parser) parse(pass Pass) {
|
|||||||
}
|
}
|
||||||
.key_global {
|
.key_global {
|
||||||
if !p.pref.translated && !p.pref.is_live && !p.builtin_mod && !p.pref.building_v &&
|
if !p.pref.translated && !p.pref.is_live && !p.builtin_mod && !p.pref.building_v &&
|
||||||
p.mod != 'ui' && p.mod != 'uiold' && !os.getwd().contains('/volt') &&
|
p.mod != 'ui' && p.mod != 'gg2' && p.mod != 'uiold' && !os.getwd().contains('/volt') &&
|
||||||
!p.pref.enable_globals {
|
!p.pref.enable_globals {
|
||||||
p.error('use `v --enable-globals ...` to enable globals')
|
p.error('use `v --enable-globals ...` to enable globals')
|
||||||
// p.error('__global is only allowed in translated code')
|
|
||||||
}
|
}
|
||||||
p.next()
|
p.next()
|
||||||
p.fspace()
|
p.fspace()
|
||||||
|
@ -128,10 +128,11 @@ fn (p mut Parser) for_st() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
// `for val in vals`
|
// `for val in vals`
|
||||||
else if p.peek() == .key_in {
|
else if p.peek() == .key_in || p.peek() == .left_arrow {
|
||||||
val := p.check_name()
|
val := p.check_name()
|
||||||
p.fspace()
|
p.fspace()
|
||||||
p.check(.key_in)
|
//p.check(.key_in)
|
||||||
|
p.next()
|
||||||
p.fspace()
|
p.fspace()
|
||||||
tmp := p.get_tmp()
|
tmp := p.get_tmp()
|
||||||
mut typ,expr := p.tmp_expr()
|
mut typ,expr := p.tmp_expr()
|
||||||
|
@ -549,6 +549,11 @@ fn (s mut Scanner) scan() ScanRes {
|
|||||||
s.pos++
|
s.pos++
|
||||||
return scan_res(.left_shift, '')
|
return scan_res(.left_shift, '')
|
||||||
}
|
}
|
||||||
|
else if nextc == `-` {
|
||||||
|
s.pos++
|
||||||
|
println("GOT ARR")
|
||||||
|
return scan_res(.left_arrow, '')
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
return scan_res(.lt, '')
|
return scan_res(.lt, '')
|
||||||
}
|
}
|
||||||
|
@ -705,6 +705,9 @@ fn (p mut Parser) check_types2(got_, expected_ string, throw bool) bool {
|
|||||||
if got.starts_with('fn ') && (expected.ends_with('fn') || expected.ends_with('Fn')) {
|
if got.starts_with('fn ') && (expected.ends_with('fn') || expected.ends_with('Fn')) {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
if got.starts_with('fn ') && expected.starts_with('fn ') {
|
||||||
|
return true
|
||||||
|
}
|
||||||
// Allow pointer arithmetic
|
// Allow pointer arithmetic
|
||||||
if expected == 'void*' && got == 'int' {
|
if expected == 'void*' && got == 'int' {
|
||||||
return true
|
return true
|
||||||
|
@ -167,6 +167,10 @@ __global:
|
|||||||
f int // public and mutable both inside and outside parent module
|
f int // public and mutable both inside and outside parent module
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn fooo(){
|
||||||
|
a:=AttrTest{1,2,3,4,5,6}
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
[typedef]
|
[typedef]
|
||||||
struct C.fixed {
|
struct C.fixed {
|
||||||
|
@ -36,6 +36,7 @@ enum TokenKind {
|
|||||||
semicolon
|
semicolon
|
||||||
colon
|
colon
|
||||||
arrow // =>
|
arrow // =>
|
||||||
|
left_arrow // <-
|
||||||
amp
|
amp
|
||||||
hash
|
hash
|
||||||
dollar
|
dollar
|
||||||
|
14
vlib/gg/gg.v
14
vlib/gg/gg.v
@ -4,12 +4,14 @@
|
|||||||
|
|
||||||
module gg
|
module gg
|
||||||
|
|
||||||
import stbi
|
import (
|
||||||
import glm
|
stbi
|
||||||
import gl
|
glm
|
||||||
import gx
|
gl
|
||||||
import os
|
gx
|
||||||
import glfw
|
os
|
||||||
|
glfw
|
||||||
|
)
|
||||||
|
|
||||||
pub struct Vec2 {
|
pub struct Vec2 {
|
||||||
pub:
|
pub:
|
||||||
|
216
vlib/gg2/gg.v
Normal file
216
vlib/gg2/gg.v
Normal file
@ -0,0 +1,216 @@
|
|||||||
|
// Copyright (c) 2019 Alexander Medvednikov. All rights reserved.
|
||||||
|
// Use of this source code is governed by an MIT license
|
||||||
|
// that can be found in the LICENSE file.
|
||||||
|
module gg2
|
||||||
|
|
||||||
|
import (
|
||||||
|
glm
|
||||||
|
gx
|
||||||
|
os
|
||||||
|
sokol
|
||||||
|
sokol.sapp
|
||||||
|
sokol.sgl
|
||||||
|
sokol.gfx
|
||||||
|
sokol.sfons
|
||||||
|
)
|
||||||
|
const (
|
||||||
|
default_font_size = 24
|
||||||
|
)
|
||||||
|
|
||||||
|
pub struct Config {
|
||||||
|
pub:
|
||||||
|
width int
|
||||||
|
height int
|
||||||
|
use_ortho bool
|
||||||
|
retina bool
|
||||||
|
resizable bool
|
||||||
|
user_data voidptr
|
||||||
|
font_size int
|
||||||
|
font_path string
|
||||||
|
create_window bool
|
||||||
|
// window_user_ptr voidptr
|
||||||
|
window_title string
|
||||||
|
always_on_top bool
|
||||||
|
scale int
|
||||||
|
frame_fn fn(voidptr)
|
||||||
|
bg_color gx.Color
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct GG {
|
||||||
|
scale int // retina = 2 , normal = 1
|
||||||
|
pub mut:
|
||||||
|
width int
|
||||||
|
height int
|
||||||
|
clear_pass C.sg_pass_action
|
||||||
|
window C.sapp_desc
|
||||||
|
render_fn fn()
|
||||||
|
//////////// font fields
|
||||||
|
fons &C.FONScontext
|
||||||
|
font_normal int
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO remove globals
|
||||||
|
__global g_fons &C.FONScontext
|
||||||
|
__global g_font_normal int
|
||||||
|
__global g_font_path string
|
||||||
|
|
||||||
|
fn init_sokol_window() {
|
||||||
|
desc := sg_desc{
|
||||||
|
mtl_device: C.sapp_metal_get_device()
|
||||||
|
mtl_renderpass_descriptor_cb: sapp_metal_get_renderpass_descriptor
|
||||||
|
mtl_drawable_cb: sapp_metal_get_drawable
|
||||||
|
d3d11_device: sapp_d3d11_get_device()
|
||||||
|
d3d11_device_context: sapp_d3d11_get_device_context()
|
||||||
|
d3d11_render_target_view_cb: sapp_d3d11_get_render_target_view
|
||||||
|
d3d11_depth_stencil_view_cb: sapp_d3d11_get_depth_stencil_view
|
||||||
|
}
|
||||||
|
gfx.setup(&desc)
|
||||||
|
sgl_desc := sgl_desc_t{}
|
||||||
|
sgl.setup(&sgl_desc)
|
||||||
|
g_fons = sfons.create(512, 512, 1)
|
||||||
|
if g_font_path.len == 0 || !os.exists(g_font_path) {
|
||||||
|
println('failed to load font "$g_font_path"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
bytes := os.read_bytes(g_font_path) or {
|
||||||
|
println('failed to load font "$g_font_path"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
g_font_normal = C.fonsAddFontMem(g_fons, 'sans', bytes.data, bytes.len, false)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn new_context(cfg Config) &GG {
|
||||||
|
//C.printf('new_context() %p\n', cfg.user_data)
|
||||||
|
window := sapp_desc{
|
||||||
|
user_data: cfg.user_data
|
||||||
|
init_userdata_cb: init_sokol_window
|
||||||
|
frame_userdata_cb: cfg.frame_fn
|
||||||
|
window_title: cfg.window_title.str
|
||||||
|
html5_canvas_name: cfg.window_title.str
|
||||||
|
width: cfg.width
|
||||||
|
height: cfg.height
|
||||||
|
high_dpi: true
|
||||||
|
}
|
||||||
|
g_font_path = cfg.font_path
|
||||||
|
if cfg.use_ortho {}
|
||||||
|
else {}
|
||||||
|
return &GG{
|
||||||
|
width: cfg.width
|
||||||
|
height: cfg.height
|
||||||
|
window: window
|
||||||
|
clear_pass: gfx.create_clear_pass(f32(cfg.bg_color.r) / 255.0, f32(cfg.bg_color.g) / 255.0, f32(cfg.bg_color.b) / 255.0, 1.0)
|
||||||
|
scale: 1 // scale
|
||||||
|
fons:0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (gg &GG) draw_text(x, y int, text string, cfg gx.TextCfg) {
|
||||||
|
gg.fons.set_font(gg.font_normal)
|
||||||
|
gg.fons.set_size(cfg.size)
|
||||||
|
ascender := 0.0
|
||||||
|
descender := 0.0
|
||||||
|
lh := 0.0
|
||||||
|
gg.fons.vert_metrics(&ascender, &descender, &lh)
|
||||||
|
color:= C.sfons_rgba(cfg.color.r, cfg.color.g, cfg.color.b, 255)
|
||||||
|
C.fonsSetColor(gg.fons, color)
|
||||||
|
C.fonsDrawText(gg.fons, x, y, text.str, 0)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (ctx &GG) draw_text_def(x, y int, text string) {
|
||||||
|
cfg := gx.TextCfg {
|
||||||
|
color: gx.Black
|
||||||
|
size: default_font_size
|
||||||
|
align: gx.ALIGN_LEFT
|
||||||
|
}
|
||||||
|
ctx.draw_text(x, y, text, cfg)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (gg mut GG) init_font() {
|
||||||
|
// TODO
|
||||||
|
gg.fons =g_fons
|
||||||
|
gg.font_normal=g_font_normal
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (gg &GG) run() {
|
||||||
|
sapp.run(&gg.window)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (ctx &GG) draw_rect(x, y, w, h f32, c gx.Color) {
|
||||||
|
sgl.c4b(c.r, c.g, c.b, 128)
|
||||||
|
sgl.begin_quads()
|
||||||
|
sgl_v2f(x, y)
|
||||||
|
sgl_v2f(x + w, y)
|
||||||
|
sgl_v2f(x + w, y + h)
|
||||||
|
sgl_v2f(x, y + h)
|
||||||
|
sgl.end()
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn draw_rect(x, y, w, h f32, c gx.Color) {
|
||||||
|
sgl.c4b(c.r, c.g, c.b, 128)
|
||||||
|
sgl.begin_quads()
|
||||||
|
sgl_v2f(x, y)
|
||||||
|
sgl_v2f(x + w, y)
|
||||||
|
sgl_v2f(x + w, y + h)
|
||||||
|
sgl_v2f(x, y + h)
|
||||||
|
sgl.end()
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (gg &GG) draw_empty_rect(x, y, w, h f32, c gx.Color) {
|
||||||
|
sgl.c4b(c.r, c.g, c.b, 128)
|
||||||
|
sgl.begin_line_strip()
|
||||||
|
sgl.v2f(x, y)
|
||||||
|
sgl.v2f(x + w, y)
|
||||||
|
sgl.v2f(x + w, y + h)
|
||||||
|
sgl.v2f(x, y + h)
|
||||||
|
sgl.v2f(x, y)
|
||||||
|
sgl.end()
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn create_image(file string) u32 {
|
||||||
|
// println('gg create image "$file"')
|
||||||
|
if !os.exists(file) {
|
||||||
|
println('gg create image no such file "$file"')
|
||||||
|
return u32(0)
|
||||||
|
}
|
||||||
|
// img := stbi.load(file)
|
||||||
|
// img.free()
|
||||||
|
return 0 // texture
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn create_image_from_memory(buf byteptr) u32 {
|
||||||
|
// texture := gl.gen_texture()
|
||||||
|
// img := stbi.load_from_memory(buf)
|
||||||
|
// img.free()
|
||||||
|
return 0 // texture
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (gg &GG) begin() {
|
||||||
|
sgl.defaults()
|
||||||
|
sgl.matrix_mode_projection()
|
||||||
|
sgl.ortho(0.0, f32(sapp.width()), f32(sapp.height()), 0.0, -1.0, 1.0)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (gg &GG) end() {
|
||||||
|
gfx.begin_default_pass(gg.clear_pass, sapp.width(), sapp.height())
|
||||||
|
sgl.draw()
|
||||||
|
gfx.end_pass()
|
||||||
|
gfx.commit()
|
||||||
|
wait_events()
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn (ctx &GG) draw_line(x, y, x2, y2 f32, color gx.Color) {}
|
||||||
|
|
||||||
|
pub fn wait_events() {
|
||||||
|
unsafe {
|
||||||
|
$if macos {
|
||||||
|
# NSEvent *event = [NSApp nextEventMatchingMask:NSEventMaskAny
|
||||||
|
# untilDate:[NSDate distantFuture]
|
||||||
|
# inMode:NSDefaultRunLoopMode
|
||||||
|
# dequeue:YES];
|
||||||
|
# [NSApp sendEvent:event];
|
||||||
|
}
|
||||||
|
$if windows {
|
||||||
|
C.WaitMessage()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -15,6 +15,7 @@ pub const (
|
|||||||
Blue = Color { r: 0, g: 0, b: 255 }
|
Blue = Color { r: 0, g: 0, b: 255 }
|
||||||
blue = Color { r: 0, g: 0, b: 255 }
|
blue = Color { r: 0, g: 0, b: 255 }
|
||||||
Red = Color { r: 255, g: 0, b: 0 }
|
Red = Color { r: 255, g: 0, b: 0 }
|
||||||
|
red = Color { r: 255, g: 0, b: 0 }
|
||||||
Green = Color { r: 0, g: 255, b: 0 }
|
Green = Color { r: 0, g: 255, b: 0 }
|
||||||
green = Color { r: 0, g: 255, b: 0 }
|
green = Color { r: 0, g: 255, b: 0 }
|
||||||
Yellow = Color { r: 255, g: 255, b: 0 }
|
Yellow = Color { r: 255, g: 255, b: 0 }
|
||||||
|
@ -13,12 +13,12 @@ pub const (
|
|||||||
#flag windows -lgdi32
|
#flag windows -lgdi32
|
||||||
|
|
||||||
// METAL
|
// METAL
|
||||||
// #flag -DSOKOL_METAL
|
#flag darwin -DSOKOL_METAL
|
||||||
// #flag darwin -framework Metal -framework Cocoa -framework MetalKit -framework QuartzCore
|
#flag darwin -framework Metal -framework Cocoa -framework MetalKit -framework QuartzCore
|
||||||
|
|
||||||
// OPENGL
|
// OPENGL
|
||||||
#flag -DSOKOL_GLCORE33
|
#flag linux -DSOKOL_GLCORE33
|
||||||
#flag darwin -framework OpenGL -framework Cocoa -framework QuartzCore
|
//#flag darwin -framework OpenGL -framework Cocoa -framework QuartzCore
|
||||||
|
|
||||||
|
|
||||||
// for simplicity, all header includes are here because import order matters and we dont have any way
|
// for simplicity, all header includes are here because import order matters and we dont have any way
|
||||||
|
@ -8,22 +8,22 @@ const (
|
|||||||
)
|
)
|
||||||
|
|
||||||
[inline]
|
[inline]
|
||||||
pub fn sfons_create(width int, height int, flags int) &C.FONScontext {
|
pub fn create(width int, height int, flags int) &C.FONScontext {
|
||||||
return C.sfons_create(width, height, flags)
|
return C.sfons_create(width, height, flags)
|
||||||
}
|
}
|
||||||
|
|
||||||
[inline]
|
[inline]
|
||||||
pub fn sfons_destroy(ctx &C.FONScontext) {
|
pub fn destroy(ctx &C.FONScontext) {
|
||||||
C.sfons_destroy(ctx)
|
C.sfons_destroy(ctx)
|
||||||
}
|
}
|
||||||
|
|
||||||
[inline]
|
[inline]
|
||||||
pub fn sfons_rgba(r byte, g byte, b byte, a byte) u32 {
|
pub fn rgba(r byte, g byte, b byte, a byte) u32 {
|
||||||
return C.sfons_rgba(r, g, b, a)
|
return C.sfons_rgba(r, g, b, a)
|
||||||
}
|
}
|
||||||
|
|
||||||
[inline]
|
[inline]
|
||||||
pub fn sfons_flush(ctx &C.FONScontext) {
|
pub fn flush(ctx &C.FONScontext) {
|
||||||
C.sfons_flush(ctx)
|
C.sfons_flush(ctx)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -69,5 +69,15 @@ fn end() {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
fn bool_array() {
|
||||||
|
a := [true, false]
|
||||||
|
b := a[0]
|
||||||
|
if b {
|
||||||
|
println('ok')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user