|
| 1 | +local app = require "soluna.app" |
| 2 | +local soluna = require "soluna" |
| 3 | +local quad = require "soluna.material.quad" |
| 4 | + |
| 5 | +local args = ... |
| 6 | +local batch = args.batch |
| 7 | + |
| 8 | +local KEY_ESCAPE <const> = 256 |
| 9 | +local KEYSTATE_PRESS <const> = 1 |
| 10 | +local TILE_W <const> = 132 |
| 11 | +local TILE_H <const> = 76 |
| 12 | +local GAP <const> = 18 |
| 13 | +local PADDING <const> = 28 |
| 14 | + |
| 15 | +local tiles <const> = { |
| 16 | + { cursor = "default", color = 0xff39445f, hover = 0xff536181 }, |
| 17 | + { cursor = "arrow", color = 0xff3f4b6b, hover = 0xff5a6b95 }, |
| 18 | + { cursor = "ibeam", color = 0xff46506d, hover = 0xff64739c }, |
| 19 | + { cursor = "crosshair", color = 0xff40546b, hover = 0xff5c7895 }, |
| 20 | + { cursor = "pointing_hand", color = 0xff3e5960, hover = 0xff5a808a }, |
| 21 | + { cursor = "resize_ew", color = 0xff4f5364, hover = 0xff74798f }, |
| 22 | + { cursor = "resize_ns", color = 0xff4a5863, hover = 0xff6c808f }, |
| 23 | + { cursor = "resize_nwse", color = 0xff4b5064, hover = 0xff6f7692 }, |
| 24 | + { cursor = "resize_nesw", color = 0xff46556a, hover = 0xff667d9b }, |
| 25 | + { cursor = "resize_all", color = 0xff4f5961, hover = 0xff74828e }, |
| 26 | + { cursor = "not_allowed", color = 0xff5c4556, hover = 0xff8a657f }, |
| 27 | +} |
| 28 | + |
| 29 | +for _, tile in ipairs(tiles) do |
| 30 | + tile.fill = quad.quad(TILE_W, TILE_H, tile.color) |
| 31 | + tile.hover_fill = quad.quad(TILE_W, TILE_H, tile.hover) |
| 32 | + tile.outline = quad.quad(TILE_W + 4, TILE_H + 4, 0xff8fb2ff) |
| 33 | +end |
| 34 | + |
| 35 | +soluna.set_window_title "soluna mouse cursor test" |
| 36 | + |
| 37 | +local callback = {} |
| 38 | +local mouse_x = -1 |
| 39 | +local mouse_y = -1 |
| 40 | +local active_cursor |
| 41 | + |
| 42 | +local function columns() |
| 43 | + return math.max(1, math.floor((args.width - PADDING * 2 + GAP) / (TILE_W + GAP))) |
| 44 | +end |
| 45 | + |
| 46 | +local function tile_rect(index) |
| 47 | + local cols = columns() |
| 48 | + local col = (index - 1) % cols |
| 49 | + local row = math.floor((index - 1) / cols) |
| 50 | + return PADDING + col * (TILE_W + GAP), PADDING + row * (TILE_H + GAP) |
| 51 | +end |
| 52 | + |
| 53 | +local function contains(x, y, left, top) |
| 54 | + return x >= left and x < left + TILE_W and y >= top and y < top + TILE_H |
| 55 | +end |
| 56 | + |
| 57 | +local function cursor_at(x, y) |
| 58 | + for index, tile in ipairs(tiles) do |
| 59 | + local left, top = tile_rect(index) |
| 60 | + if contains(x, y, left, top) then |
| 61 | + return tile.cursor |
| 62 | + end |
| 63 | + end |
| 64 | +end |
| 65 | + |
| 66 | +local function set_cursor(cursor) |
| 67 | + if cursor == active_cursor then |
| 68 | + return |
| 69 | + end |
| 70 | + active_cursor = cursor |
| 71 | + soluna.set_mouse_cursor(cursor) |
| 72 | +end |
| 73 | + |
| 74 | +function callback.mouse_move(x, y) |
| 75 | + mouse_x, mouse_y = x, y |
| 76 | + set_cursor(cursor_at(x, y)) |
| 77 | +end |
| 78 | + |
| 79 | +function callback.key(keycode, state) |
| 80 | + if keycode == KEY_ESCAPE and state == KEYSTATE_PRESS then |
| 81 | + app.quit() |
| 82 | + end |
| 83 | +end |
| 84 | + |
| 85 | +function callback.frame() |
| 86 | + for index, tile in ipairs(tiles) do |
| 87 | + local left, top = tile_rect(index) |
| 88 | + local hovered = contains(mouse_x, mouse_y, left, top) |
| 89 | + if hovered then |
| 90 | + batch:add(tile.outline, left - 2, top - 2) |
| 91 | + end |
| 92 | + batch:add(hovered and tile.hover_fill or tile.fill, left, top) |
| 93 | + end |
| 94 | +end |
| 95 | + |
| 96 | +return callback |
0 commit comments