From 88e33a83de69911edf656ad6c9534bf2bddb894e Mon Sep 17 00:00:00 2001 From: Alexander Medvednikov Date: Wed, 21 Dec 2022 19:33:19 +0300 Subject: [PATCH] gg: fix draw_image on macos native; vcreate: vweb template --- ROADMAP.md | 2 +- cmd/tools/vcreate.v | 87 +++++++++++++++++++++++++++++++++++- examples/gg/rectangles.v | 6 +-- examples/vweb/vweb_example.v | 2 +- vlib/builtin/array.v | 2 +- vlib/gg/gg.c.v | 1 + vlib/gg/image.c.v | 52 ++++++++++++++------- 7 files changed, 128 insertions(+), 24 deletions(-) diff --git a/ROADMAP.md b/ROADMAP.md index 58f519b3e..77fccfc35 100644 --- a/ROADMAP.md +++ b/ROADMAP.md @@ -5,7 +5,7 @@ - [ ] Parallel checker - [ ] Parallel C compilation - [ ] `recover()` from panics -- [ ] vfmt: add missing imports (like goimports) +- [x] vfmt: add missing imports (like goimports) - [ ] Recursive structs via optionals: `struct Node { next ?Node }` - [ ] Optional function struct fields - [ ] Handle function pointers safely, remove `if function == 0 {` diff --git a/cmd/tools/vcreate.v b/cmd/tools/vcreate.v index d5f44a750..fcea6a7bb 100644 --- a/cmd/tools/vcreate.v +++ b/cmd/tools/vcreate.v @@ -52,6 +52,26 @@ fn vmod_content(c Create) string { " } +fn new_project_content() string { + if os.args.len == 3 { + return main_content() + } else if os.args.len == 4 { + kind := os.args.last() + return match kind { + 'web' { + simple_web_app() + } + 'gg' { + main_content() // TODO + } + else { + '' + } + } + } + return '' +} + fn main_content() string { return "module main @@ -116,7 +136,7 @@ fn (c &Create) write_main(new bool) { return } main_path := if new { '${c.name}/${c.name}.v' } else { '${c.name}.v' } - os.write_file(main_path, main_content()) or { panic(err) } + os.write_file(main_path, new_project_content()) or { panic(err) } } fn (c &Create) write_gitattributes(new bool) { @@ -151,6 +171,13 @@ fn (c &Create) create_git_repo(dir string) { } fn create(args []string) { + if os.args.len == 4 { + template := os.args.last() + if template !in ['web', 'gg'] { + eprintln('uknown template "${template}", possible templates: web, gg') + exit(1) + } + } mut c := Create{} c.name = check_name(if args.len > 0 { args[0] } else { os.input('Input your project name: ') }) if c.name == '' { @@ -215,3 +242,61 @@ fn main() { } println('Complete!') } + +fn simple_web_app() string { + return "import vweb +import sqlite // can change to 'mysql', 'pg' + +const ( + port = 8082 +) + +struct App { + vweb.Context +mut: + db shared sqlite.DB +} + +pub fn (app App) before_request() { + println('[web] before_request: \${app.req.method} \${app.req.url}') +} + +fn main() { + vweb.run(&App{ + db: sqlite.connect('vweb.sql')! +}, port) +} + +['/users/:name'] +pub fn (mut app App) user(name string) vweb.Result { + user := sql app.db { + select from User where name == name + } + return \$vweb.html() +} + +['/api/users/:name'] +pub fn (mut app App) user(name string) vweb.Result { + user := sql app.db { + select from User where name == name + } + return app.json({ + user: id + }) +} + +pub fn (mut app App) index() vweb.Result { + return \$vweb.html() +} + +[post] +['/register'] +pub fn (mut app App) register_user(name string, password string) vweb.Result { + user := User{name:name, password, password} + sql app.db { + insert user into User + } + return app.redirect('/') +} +" +} diff --git a/examples/gg/rectangles.v b/examples/gg/rectangles.v index d60c766af..b12dbfb38 100644 --- a/examples/gg/rectangles.v +++ b/examples/gg/rectangles.v @@ -12,7 +12,7 @@ const ( struct App { mut: gg &gg.Context = unsafe { nil } - image gg.Image + image int // gg.Image } fn main() { @@ -30,7 +30,7 @@ fn main() { init_fn: init_images ) mut logo_path := os.resource_abs_path(os.join_path('..', 'assets', 'logo.png')) - app.image = app.gg.create_image(logo_path) + app.image = app.gg.create_image(logo_path).id app.gg.run() } @@ -49,5 +49,5 @@ fn (app &App) draw() { // app.gg.draw_text_def(300,300, 'привет') app.gg.draw_rect_filled(10, 10, 100, 30, gx.blue) app.gg.draw_rect_empty(110, 150, 80, 40, gx.black) - app.gg.draw_image(230, 30, app.image.width, app.image.height, app.image) + app.gg.draw_image_by_id(230, 30, 50, 50, app.image) } diff --git a/examples/vweb/vweb_example.v b/examples/vweb/vweb_example.v index db63e2fd8..fb220d14a 100644 --- a/examples/vweb/vweb_example.v +++ b/examples/vweb/vweb_example.v @@ -19,7 +19,7 @@ mut: } pub fn (app App) before_request() { - println('[Vweb] ${app.Context.req.method} ${app.Context.req.url}') + println('[vweb] before_request: ${app.req.method} ${app.req.url}') } fn main() { diff --git a/vlib/builtin/array.v b/vlib/builtin/array.v index 2d9d7e553..7d9deb2c5 100644 --- a/vlib/builtin/array.v +++ b/vlib/builtin/array.v @@ -14,7 +14,7 @@ pub: element_size int // size in bytes of one element in the array. pub mut: data voidptr - offset int // in bytes (should be `usize`) + offset int // in bytes (should be `usize`), to avoid copying data while making slices, unless it starts changing len int // length of the array in elements. cap int // capacity of the array in elements. flags ArrayFlags diff --git a/vlib/gg/gg.c.v b/vlib/gg/gg.c.v index 9f3d2d14e..53035e56c 100644 --- a/vlib/gg/gg.c.v +++ b/vlib/gg/gg.c.v @@ -307,6 +307,7 @@ fn gg_frame_fn(mut ctx Context) { ctx.record_frame() if ctx.ui_mode && !ctx.needs_refresh { + // println('ui mode, exiting') // Draw 3 more frames after the "stop refresh" command ctx.ticks++ if ctx.ticks > 3 { diff --git a/vlib/gg/image.c.v b/vlib/gg/image.c.v index 3c3f53c00..5b4aada1b 100644 --- a/vlib/gg/image.c.v +++ b/vlib/gg/image.c.v @@ -109,23 +109,6 @@ pub fn (mut img Image) init_sokol_image() &Image { // draw_image draws the provided image onto the screen. pub fn (ctx &Context) draw_image(x f32, y f32, width f32, height f32, img_ &Image) { - $if macos { - if img_.id >= ctx.image_cache.len { - eprintln('gg: draw_image() bad img id ${img_.id} (img cache len = ${ctx.image_cache.len})') - return - } - if ctx.native_rendering { - if img_.width == 0 { - return - } - if !os.exists(img_.path) { - return - } - C.darwin_draw_image(x, ctx.height - (y + height), width, height, img_) - return - } - } - ctx.draw_image_with_config( img: img_ img_rect: Rect{x, y, width, height} @@ -273,6 +256,41 @@ pub struct StreamingImageConfig { // draw_image_with_config takes in a config that details how the // provided image should be drawn onto the screen pub fn (ctx &Context) draw_image_with_config(config DrawImageConfig) { + $if macos { + unsafe { + mut img := config.img + if config.img == nil { + // Get image by id + if config.img_id > 0 { + img = &ctx.image_cache[config.img_id] + } else { + eprintln('gg: failed to get image to draw natively') + return + } + } + if img.id >= ctx.image_cache.len { + eprintln('gg: draw_image() bad img id ${img.id} (img cache len = ${ctx.image_cache.len})') + return + } + if ctx.native_rendering { + if img.width == 0 { + println('w=0') + return + } + if !os.exists(img.path) { + println('not exist path') + return + } + x := config.img_rect.x + y := config.img_rect.y + C.darwin_draw_image(x, ctx.height - (y + config.img_rect.height), config.img_rect.width, + config.img_rect.height, img) + println('ok') + return + } + } + } + id := if !isnil(config.img) { config.img.id } else { config.img_id } if id >= ctx.image_cache.len { eprintln('gg: draw_image() bad img id ${id} (img cache len = ${ctx.image_cache.len})') -- 2.30.2