Move input handling to script only

This commit is contained in:
John Alanbrook 2024-03-11 22:23:02 -05:00
parent 74a59a1e35
commit 4843981527
16 changed files with 246 additions and 549 deletions

View file

@ -180,7 +180,7 @@ ifdef STEAM
# BIN += /steam # BIN += /steam
endif endif
WARNING_FLAGS = -Wno-incompatible-function-pointer-types WARNING_FLAGS = -Wno-incompatible-function-pointer-types -Wno-incompatible-pointer-types
NAME = primum$(EXT) NAME = primum$(EXT)
SEM = 0.3.0 SEM = 0.3.0

View file

@ -442,14 +442,14 @@ polygon2d.inputs.f10 = function() {
polygon2d.inputs.f10.doc = "Sort all points to be CCW order."; polygon2d.inputs.f10.doc = "Sort all points to be CCW order.";
polygon2d.inputs['C-lm'] = function() { polygon2d.inputs['C-lm'] = function() {
this.points.push(this.gameobject.world2this(Mouse.worldpos)); this.points.push(this.gameobject.world2this(Mouse.worldpos()));
}; };
polygon2d.inputs['C-lm'].doc = "Add a point to location of mouse."; polygon2d.inputs['C-lm'].doc = "Add a point to location of mouse.";
polygon2d.inputs.lm = function(){}; polygon2d.inputs.lm = function(){};
polygon2d.inputs.lm.released = function(){}; polygon2d.inputs.lm.released = function(){};
polygon2d.inputs['C-M-lm'] = function() { polygon2d.inputs['C-M-lm'] = function() {
var idx = Math.grab_from_points(Mouse.worldpos, this.points.map(p => this.gameobject.this2world(p)), 25); var idx = Math.grab_from_points(Mouse.worldpos(), this.points.map(p => this.gameobject.this2world(p)), 25);
if (idx === -1) return; if (idx === -1) return;
this.points.splice(idx, 1); this.points.splice(idx, 1);
}; };
@ -753,7 +753,7 @@ bucket.inputs['C-o'].doc = "Set spline to linear.";
bucket.inputs['C-M-lm'] = function() { bucket.inputs['C-M-lm'] = function() {
if (Spline.is_catmull(this.type)) { if (Spline.is_catmull(this.type)) {
var idx = Math.grab_from_points(Mouse.worldpos, this.points.map(p => this.gameobject.this2world(p)), 25); var idx = Math.grab_from_points(Mouse.worldpos(), this.points.map(p => this.gameobject.this2world(p)), 25);
if (idx === -1) return; if (idx === -1) return;
} else { } else {
@ -763,16 +763,16 @@ bucket.inputs['C-M-lm'] = function() {
}; };
bucket.inputs['C-M-lm'].doc = "Select the given point as the '0' of this spline."; bucket.inputs['C-M-lm'].doc = "Select the given point as the '0' of this spline.";
bucket.inputs['C-lm'] = function() { this.add_node(Mouse.worldpos); } bucket.inputs['C-lm'] = function() { this.add_node(Mouse.worldpos()); }
bucket.inputs['C-lm'].doc = "Add a point to the spline at the mouse position."; bucket.inputs['C-lm'].doc = "Add a point to the spline at the mouse position.";
bucket.inputs['C-M-lm'] = function() { bucket.inputs['C-M-lm'] = function() {
var idx = -1; var idx = -1;
if (Spline.is_catmull(this.type)) if (Spline.is_catmull(this.type))
idx = Math.grab_from_points(Mouse.worldpos, this.points.map(p => this.gameobject.this2world(p)), 25); idx = Math.grab_from_points(Mouse.worldpos(), this.points.map(p => this.gameobject.this2world(p)), 25);
else { else {
var nodes = Spline.bezier_nodes(this.points); var nodes = Spline.bezier_nodes(this.points);
idx = Math.grab_from_points(Mouse.worldpos, nodes.map(p => this.gameobject.this2world(p)), 25); idx = Math.grab_from_points(Mouse.worldpos(), nodes.map(p => this.gameobject.this2world(p)), 25);
idx *= 3; idx *= 3;
} }

View file

@ -25,7 +25,7 @@ var editor = {
desktop: undefined, /* The editor desktop, where all editing objects live */ desktop: undefined, /* The editor desktop, where all editing objects live */
working_layer: 0, working_layer: 0,
get cursor() { get cursor() {
if (this.selectlist.length === 0 ) return Mouse.worldpos; if (this.selectlist.length === 0 ) return Mouse.worldpos();
return physics.com(this.selectlist.map(x => x.pos)); return physics.com(this.selectlist.map(x => x.pos));
}, },
edit_mode: "basic", edit_mode: "basic",
@ -35,7 +35,7 @@ var editor = {
get_that() { return this.selectlist.length === 1 ? this.selectlist[0] : this.get_this(); }, get_that() { return this.selectlist.length === 1 ? this.selectlist[0] : this.get_this(); },
try_select() { /* nullify true if it should set selected to null if it doesn't find an object */ try_select() { /* nullify true if it should set selected to null if it doesn't find an object */
var go = physics.pos_query(Mouse.worldpos); var go = physics.pos_query(Mouse.worldpos());
return this.do_select(go); return this.do_select(go);
}, },
@ -382,7 +382,7 @@ var editor = {
/* Draw selection box */ /* Draw selection box */
if (this.sel_start) { if (this.sel_start) {
var endpos = Mouse.worldpos; var endpos = Mouse.worldpos();
var c = []; var c = [];
c[0] = (endpos[0] - this.sel_start[0]) / 2; c[0] = (endpos[0] - this.sel_start[0]) / 2;
c[0] += this.sel_start[0]; c[0] += this.sel_start[0];
@ -462,7 +462,7 @@ var editor = {
render.circle(x[1].screenpos(),10,Color.blue.alpha(0.3)); render.circle(x[1].screenpos(),10,Color.blue.alpha(0.3));
}); });
var mg = physics.pos_query(Mouse.worldpos,10); var mg = physics.pos_query(Mouse.worldpos(),10);
if (mg) { if (mg) {
var p = mg.path_from(thiso); var p = mg.path_from(thiso);
@ -530,7 +530,7 @@ var editor = {
load(urstr) { load(urstr) {
var obj = editor.edit_level.spawn(urstr); var obj = editor.edit_level.spawn(urstr);
obj.set_worldpos(Mouse.worldpos); obj.set_worldpos(Mouse.worldpos());
this.selectlist = [obj]; this.selectlist = [obj];
}, },
@ -611,7 +611,7 @@ var editor = {
editor.new_object = function() editor.new_object = function()
{ {
var obj = editor.edit_level.spawn(); var obj = editor.edit_level.spawn();
obj.set_worldpos(Mouse.worldpos); obj.set_worldpos(Mouse.worldpos());
this.selectlist = [obj]; this.selectlist = [obj];
return obj; return obj;
} }
@ -657,7 +657,7 @@ editor.inputs.drop = function(str) {
return; return;
} }
var mg = physics.pos_query(Mouse.worldpos,10); var mg = physics.pos_query(Mouse.worldpos(),10);
if (!mg) return; if (!mg) return;
var img = mg.get_comp_by_name('sprite'); var img = mg.get_comp_by_name('sprite');
if (!img) return; if (!img) return;
@ -804,7 +804,7 @@ editor.inputs['C-r'].doc = "Negate the selected's angle.";
editor.inputs.r = function() { editor.inputs.r = function() {
if (editor.sel_comp && 'angle' in editor.sel_comp) { if (editor.sel_comp && 'angle' in editor.sel_comp) {
var relpos = Mouse.worldpos.sub(editor.sel_comp.gameobject.worldpos()); var relpos = Mouse.worldpos().sub(editor.sel_comp.gameobject.worldpos());
editor.startoffset = Math.atan2(relpos.y, relpos.x); editor.startoffset = Math.atan2(relpos.y, relpos.x);
editor.startrot = editor.sel_comp.angle; editor.startrot = editor.sel_comp.angle;
@ -813,7 +813,7 @@ editor.inputs.r = function() {
editor.rotlist = []; editor.rotlist = [];
editor.selectlist.forEach(function(x) { editor.selectlist.forEach(function(x) {
var relpos = Mouse.worldpos.sub(editor.cursor); var relpos = Mouse.worldpos().sub(editor.cursor);
editor.rotlist.push({ editor.rotlist.push({
obj: x, obj: x,
angle: x.angle, angle: x.angle,
@ -1026,7 +1026,7 @@ editor.inputs.f3 = function() {
this.openpanel(componentexplorer); this.openpanel(componentexplorer);
}; };
editor.inputs.lm = function() { editor.sel_start = Mouse.worldpos; }; editor.inputs.lm = function() { editor.sel_start = Mouse.worldpos(); };
editor.inputs.lm.doc = "Selection box."; editor.inputs.lm.doc = "Selection box.";
editor.inputs.lm.released = function() { editor.inputs.lm.released = function() {
@ -1043,11 +1043,11 @@ editor.inputs.lm.released = function() {
var selects = []; var selects = [];
/* TODO: selects somehow gets undefined objects in here */ /* TODO: selects somehow gets undefined objects in here */
if (Vector.equal(Mouse.worldpos, editor.sel_start, 5)) { if (Vector.equal(Mouse.worldpos(), editor.sel_start, 5)) {
var sel = editor.try_select(); var sel = editor.try_select();
if (sel) selects.push(sel); if (sel) selects.push(sel);
} else { } else {
var box = bbox.frompoints([editor.sel_start, Mouse.worldpos]); var box = bbox.frompoints([editor.sel_start, Mouse.worldpos()]);
var hits = physics.box_query(bbox.tocwh(box)); var hits = physics.box_query(bbox.tocwh(box));
@ -1104,7 +1104,7 @@ editor.try_pick = function()
editor.grabselect = []; editor.grabselect = [];
if (editor.sel_comp && 'pick' in editor.sel_comp) if (editor.sel_comp && 'pick' in editor.sel_comp)
return editor.sel_comp.pick(Mouse.worldpos); return editor.sel_comp.pick(Mouse.worldpos());
return editor.try_select(); return editor.try_select();
} }
@ -1112,7 +1112,7 @@ editor.try_pick = function()
editor.inputs.mm = function() { editor.inputs.mm = function() {
if (editor.brush_obj) { if (editor.brush_obj) {
editor.selectlist = editor.dup_objects([editor.brush_obj]); editor.selectlist = editor.dup_objects([editor.brush_obj]);
editor.selectlist[0].pos = Mouse.worldpos; editor.selectlist[0].pos = Mouse.worldpos();
editor.grabselect = editor.selectlist[0]; editor.grabselect = editor.selectlist[0];
return; return;
} }
@ -1126,18 +1126,18 @@ editor.inputs['C-mm'] = editor.inputs.mm;
editor.inputs['C-M-lm'] = function() editor.inputs['C-M-lm'] = function()
{ {
var go = physics.pos_query(Mouse.worldpos); var go = physics.pos_query(Mouse.worldpos());
if (!go) return; if (!go) return;
editor.edit_level = go.master; editor.edit_level = go.master;
} }
editor.inputs['C-M-mm'] = function() { editor.inputs['C-M-mm'] = function() {
editor.mousejoy = Mouse.pos; editor.mousejoy = Mouse.screenpos();
editor.joystart = editor.camera.pos; editor.joystart = editor.camera.pos;
}; };
editor.inputs['C-M-rm'] = function() { editor.inputs['C-M-rm'] = function() {
editor.mousejoy = Mouse.pos; editor.mousejoy = Mouse.screenpos();
editor.z_start = editor.camera.zoom; editor.z_start = editor.camera.zoom;
Mouse.disabled(); Mouse.disabled();
}; };
@ -1170,7 +1170,7 @@ editor.inputs.mouse.move = function(pos, dpos)
x.sync(); x.sync();
}); });
var relpos = Mouse.worldpos.sub(editor.cursor); var relpos = Mouse.worldpos().sub(editor.cursor);
var dist = Vector.length(relpos); var dist = Vector.length(relpos);
editor.scalelist?.forEach(function(x) { editor.scalelist?.forEach(function(x) {
@ -1205,7 +1205,7 @@ editor.inputs.mouse['C-scroll'] = function(scroll)
editor.camera.zoom += scroll.y/100; editor.camera.zoom += scroll.y/100;
} }
editor.inputs['C-M-S-lm'] = function() { editor.selectlist[0].set_center(Mouse.worldpos); }; editor.inputs['C-M-S-lm'] = function() { editor.selectlist[0].set_center(Mouse.worldpos()); };
editor.inputs['C-M-S-lm'].doc = "Set world center to mouse position."; editor.inputs['C-M-S-lm'].doc = "Set world center to mouse position.";
editor.inputs.delete = function() { editor.inputs.delete = function() {
@ -1242,7 +1242,7 @@ editor.inputs.g = function() {
if (editor.sel_comp) { if (editor.sel_comp) {
if ('pick' in editor.sel_comp) { if ('pick' in editor.sel_comp) {
editor.grabselect = [editor.sel_comp.pick(Mouse.worldpos)]; editor.grabselect = [editor.sel_comp.pick(Mouse.worldpos())];
return; return;
} }
@ -1259,7 +1259,7 @@ editor.inputs.g = function() {
} }
if (editor.sel_comp && 'pick' in editor.sel_comp) { if (editor.sel_comp && 'pick' in editor.sel_comp) {
var o = editor.sel_comp.pick(Mouse.worldpos); var o = editor.sel_comp.pick(Mouse.worldpos());
if (o) editor.grabselect = [o]; if (o) editor.grabselect = [o];
return; return;
} }
@ -1386,7 +1386,7 @@ compmode.inputs['C-x'] = function() {};
editor.scalelist = []; editor.scalelist = [];
editor.inputs.s = function() { editor.inputs.s = function() {
var scaleoffset = Vector.length(Mouse.worldpos.sub(editor.cursor)); var scaleoffset = Vector.length(Mouse.worldpos().sub(editor.cursor));
editor.scalelist = []; editor.scalelist = [];
if (editor.sel_comp) { if (editor.sel_comp) {
@ -1593,7 +1593,7 @@ replpanel.inputs = Object.create(inputpanel.inputs);
replpanel.inputs.block = true; replpanel.inputs.block = true;
replpanel.inputs.lm = function() replpanel.inputs.lm = function()
{ {
var mg = physics.pos_query(Mouse.worldpos); var mg = physics.pos_query(Mouse.worldpos());
if (!mg) return; if (!mg) return;
var p = mg.path_from(editor.get_this()); var p = mg.path_from(editor.get_this());
this.value = p; this.value = p;

View file

@ -57,10 +57,8 @@ global.check_registers = function(obj)
var signal = k.fromfirst("on_"); var signal = k.fromfirst("on_");
Event.observe(signal, obj, obj[k]); Event.observe(signal, obj, obj[k]);
}; };
} }
eval_env.dov = `Counterpart to /load_env/, but with a string.`; eval_env.dov = `Counterpart to /load_env/, but with a string.`;
function feval_env(file, env) function feval_env(file, env)
@ -88,6 +86,7 @@ global.mixin("scripts/render.js");
global.Game = { global.Game = {
engine_start(fn) { engine_start(fn) {
console.warn("engine starting.");
cmd(257, fn); cmd(257, fn);
}, },
@ -163,16 +162,7 @@ Game.doc.dt = "Current frame dt.";
Game.doc.view_camera = "Set the camera for the current view."; Game.doc.view_camera = "Set the camera for the current view.";
Game.doc.camera = "Current camera."; Game.doc.camera = "Current camera.";
global.mixin("scripts/input.js"); global.prosperon = {};
global.mixin("scripts/std.js");
global.mixin("scripts/diff.js");
console.level = 1;
global.mixin("scripts/color.js");
var prosperon = {};
prosperon.version = cmd(255); prosperon.version = cmd(255);
prosperon.revision = cmd(256); prosperon.revision = cmd(256);
@ -225,7 +215,11 @@ Range is given by a semantic versioning number, prefixed with nothing, a ~, or a
~ means that MAJOR and MINOR must match exactly, but any PATCH greater or equal is valid. ~ means that MAJOR and MINOR must match exactly, but any PATCH greater or equal is valid.
^ means that MAJOR must match exactly, but any MINOR and PATCH greater or equal is valid.`; ^ means that MAJOR must match exactly, but any MINOR and PATCH greater or equal is valid.`;
global.mixin("scripts/input.js");
global.mixin("scripts/std.js");
console.level = 1;
global.mixin("scripts/diff.js");
global.mixin("scripts/color.js");
global.mixin("scripts/gui.js"); global.mixin("scripts/gui.js");
var timer = { var timer = {
@ -253,10 +247,7 @@ var timer = {
}; };
global.mixin("scripts/tween.js"); global.mixin("scripts/tween.js");
global.mixin("scripts/physics.js"); global.mixin("scripts/physics.js");
global.mixin("scripts/ai.js"); global.mixin("scripts/ai.js");
global.mixin("scripts/geometry.js"); global.mixin("scripts/geometry.js");
@ -315,7 +306,7 @@ var Register = {
registries: [], registries: [],
add_cb(idx, name) { add_cb(name) {
var n = {}; var n = {};
var fns = []; var fns = [];
@ -326,11 +317,9 @@ var Register = {
fns.push(fn); fns.push(fn);
return function() { fns.remove(fn); }; return function() { fns.remove(fn); };
} }
n.broadcast = function(...args) { fns.forEach(x => x(...args)); } prosperon[name] = function(...args) { fns.forEach(x => x(...args)); }
n.clear = function() { fns = []; } n.clear = function() { fns = []; }
register(idx, n.broadcast, n);
Register[name] = n; Register[name] = n;
Register.registries.push(n); Register.registries.push(n);
@ -338,16 +327,13 @@ var Register = {
}, },
}; };
Register.add_cb(0, "update").doc = "Called once per frame."; Register.add_cb("update").doc = "Called once per frame.";
Register.add_cb(11, "appupdate"); Register.add_cb("appupdate");
Register.add_cb(1, "physupdate"); Register.add_cb("physupdate");
Register.add_cb(2, "gui"); Register.add_cb("gui");
Register.add_cb(6, "debug"); Register.add_cb("debug");
register(7, Register.kbm_input, Register); Register.add_cb("gamepad_input");
Register.add_cb(8, "gamepad_input"); Register.add_cb("draw");
Register.add_cb(10, "draw");
register(9, console.stack, this);
Register.gamepad_playermap[0] = Player.players[0]; Register.gamepad_playermap[0] = Player.players[0];

View file

@ -84,7 +84,7 @@ GUI.controls.set_mum = function(mum)
} }
GUI.controls.check_bb = function(mum) GUI.controls.check_bb = function(mum)
{ {
if (bbox.pointin(mum.bb, Mouse.pos)) if (bbox.pointin(mum.bb, Mouse.screenpos()))
GUI.controls.set_mum(mum); GUI.controls.set_mum(mum);
} }
GUI.controls.inputs = {}; GUI.controls.inputs = {};

View file

@ -1,7 +1,130 @@
var keycodes = {
0x00E: "back",
0x00F: "tab",
0x01C: "enter",
0x001: "esc",
0x039: "space",
0x149: "pgup",
0x151: "pgdown",
0x14F: "end",
0x147: "home",
0x14B: "left",
0x148: "up",
0x14D: "right",
0x150: "down",
0x152: "insert",
0x153: "delete",
45: "minus",
};
var mod = {
shift: 0,
ctrl: 0,
alt: 0,
super: 0
};
/*
released
rep
pressed
pressrep
down
*/
function keyname_extd(key)
{
if (key > 289 && key < 302) {
var num = key-289;
return `f${num}`;
}
if (key >= 320 && key <= 329) {
var num = key-320;
return `kp${num}`;
}
if (keycodes[key]) return keycodes[key];
if (key >= 32 && key <= 126) return String.fromCharCode(key).lc();
return undefined;
}
prosperon.keys = [];
function modstr()
{
var s = "";
if (mod.ctrl) s += "C-";
if (mod.alt) s += "M-";
if (mod.super) s += "S-";
return s;
}
prosperon.keydown = function(key, repeat)
{
prosperon.keys[key] = true;
if (key == 341 || key == 345)
mod.ctrl = 1;
else if (key == 342 || key == 346)
mod.alt = 1;
else if (key == 343 || key == 347)
mod.super = 1;
else if (key == 340 || key == 344)
mod.shift = 1;
else {
var emacs = modstr() + keyname_extd(key);
player[0].raw_input(emacs, "pressrep");
if (repeat)
player[0].raw_input(emacs, "rep");
else
player[0].raw_input(emacs, "pressed");
}
}
prosperon.keyup = function(key)
{
prosperon.keys[key] = false;
if (key == 341 || key == 345)
mod.ctrl = 0;
else if (key == 342 || key == 346)
mod.alt = 0;
else if (key == 343 || key == 347)
mod.super = 0;
else if (key == 340 || key == 344)
mod.shift = 0;
else {
var emacs = modstr() + keyname_extd(key);
player[0].raw_input(emacs, "released");
}
}
prosperon.droppedfile = function(path)
{
player[0].raw_input("drop", "pressed", path);
}
var mousepos = [0,0];
prosperon.textinput = function(){};
prosperon.mousemove = function(pos, dx){
mousepos = pos;
player[0].mouse_input(modstr() + "move", pos, dx);
};
prosperon.mousescroll = function(dx){
player[0].mouse_input(modstr() + "scroll", dx);
};
prosperon.mousedown = function(b){
player[0].raw_input(modstr() + Mouse.button[b], "pressed");
};
prosperon.mouseup = function(b){
player[0].raw_input(modstr() + Mouse.button[b], "released");
};
var Mouse = { var Mouse = {
get pos() { return cmd(45); }, screenpos() { return mousepos.slice(); },
screenpos() { return cmd(45); }, worldpos() { return Window.screen2world(mousepos); },
get worldpos() { return Window.screen2world(cmd(45)); },
disabled() { cmd(46, 1); }, disabled() { cmd(46, 1); },
normal() { cmd(46, 0);}, normal() { cmd(46, 0);},
@ -21,6 +144,12 @@ var Mouse = {
Mouse.custom[mode] = img; Mouse.custom[mode] = img;
} }
}, },
button: { /* left, right, middle mouse */
0: "lm",
1: "rm",
2: "mm"
},
custom:[], custom:[],
cursor: { cursor: {
default: 0, default: 0,
@ -44,10 +173,9 @@ Mouse.disabled.doc = "Set the mouse to hidden. This locks it to the game and hid
Mouse.normal.doc = "Set the mouse to show again after hiding."; Mouse.normal.doc = "Set the mouse to show again after hiding.";
var Keys = { var Keys = {
shift() { return cmd(50, 340); }, down(code) {
ctrl() { return cmd(50, 341); }, return prosperon.keys[code];
alt() { return cmd(50, 342); }, },
super() { return cmd(50, 343); },
}; };
var input = {}; var input = {};
@ -137,6 +265,7 @@ var Player = {
for (var pawn of this.pawns.reversed()) { for (var pawn of this.pawns.reversed()) {
if (typeof pawn.inputs?.any === 'function') { if (typeof pawn.inputs?.any === 'function') {
pawn.inputs.any(cmd); pawn.inputs.any(cmd);
if (!pawn.inputs.fallthru) if (!pawn.inputs.fallthru)
return; return;
} }

View file

@ -259,6 +259,11 @@ void mesh_add_primitive(mesh *mesh, cgltf_primitive *prim)
case cgltf_attribute_type_invalid: case cgltf_attribute_type_invalid:
YughWarn("Invalid type."); YughWarn("Invalid type.");
break; break;
case cgltf_attribute_type_custom:
break;
case cgltf_attribute_type_max_enum:
break;
} }
} }
/* /*

View file

@ -10,199 +10,12 @@
#include "resources.h" #include "resources.h"
#include "jsffi.h" #include "jsffi.h"
static int mouse_states[3] = {INPUT_UP};
static int key_states[512] = {INPUT_UP};
HMM_Vec2 mousewheel = {0,0};
HMM_Vec2 mouse_pos = {0, 0};
HMM_Vec2 mouse_delta = {0, 0};
struct joystick {
int id;
};
static int *downkeys = NULL;
static struct joystick *joysticks = NULL;
static int mquit = 0;
static struct callee pawn_callee; static struct callee pawn_callee;
static struct callee gamepad_callee; static struct callee gamepad_callee;
void add_downkey(int key) {
for (int i = 0; i < arrlen(downkeys); i++)
if (downkeys[i] == key) return;
arrput(downkeys, key);
}
void rm_downkey(int key) {
for (int i = 0; i < arrlen(downkeys); i++)
if (downkeys[i] == key) {
arrdelswap(downkeys, i);
return;
}
}
char *mb2str(int btn)
{
switch(btn) {
case 0:
return "lm";
break;
case 1:
return "rm";
break;
case 2:
return "mm";
break;
}
return "NULLMOUSE";
}
JSValue input2js(int state)
{
switch(state) {
case INPUT_UP: return jstr("released");
case INPUT_REPEAT: return jstr("rep");
case INPUT_DOWN: return jstr("pressed");
case 3: return jstr("pressrep");
case 4: return jstr("down");
}
return JS_UNDEFINED;
}
void input_mouse(int btn, int state, uint32_t mod)
{
char out[16] = {0};
snprintf(out, 16, "%s%s%s%s",
mod & SAPP_MODIFIER_CTRL ? "C-" : "",
mod & SAPP_MODIFIER_ALT ? "M-" : "",
mod & SAPP_MODIFIER_SUPER ? "S-" : "",
mb2str(btn)
);
JSValue argv[3];
argv[0] = jstr("emacs");
argv[1] = jstr(out);
argv[2] = input2js(state);
script_callee(pawn_callee, 3, argv);
}
void input_mouse_move(float x, float y, float dx, float dy, uint32_t mod)
{
mouse_pos.x = x;
mouse_pos.y = mainwin.height - y;
mouse_delta.x = dx;
mouse_delta.y = -dy;
JSValue argv[4];
argv[0] = jstr("mouse");
argv[1] = jstr("move");
argv[2] = vec2js(mouse_pos);
argv[3] = vec2js(mouse_delta);
script_callee(pawn_callee, 4, argv);
JS_FreeValue(js, argv[2]);
JS_FreeValue(js, argv[3]);
}
void input_mouse_scroll(float x, float y, uint32_t mod)
{
mousewheel.x = x;
mousewheel.y = y;
JSValue argv[4];
argv[0] = jstr("mouse");
char out[16] = {0};
snprintf(out, 16, "%s%s%sscroll",
mod & SAPP_MODIFIER_CTRL ? "C-" : "",
mod & SAPP_MODIFIER_ALT ? "M-" : "",
mod & SAPP_MODIFIER_SUPER ? "S-" : ""
);
argv[1] = jstr(out);
argv[2] = vec2js(mousewheel);
script_callee(pawn_callee, 3, argv);
JS_FreeValue(js, argv[2]);
}
void input_btn(int btn, int state, uint32_t mod)
{
char keystr[16] = {0};
strncat(keystr,keyname_extd(btn),16);
if (strlen(keystr) == 1 && mod & SAPP_MODIFIER_SHIFT)
keystr[0] = toupper(keystr[0]);
char out[16] = {0};
snprintf(out, 16, "%s%s%s%s",
mod & SAPP_MODIFIER_CTRL ? "C-" : "",
mod & SAPP_MODIFIER_ALT ? "M-" : "",
mod & SAPP_MODIFIER_SUPER ? "S-" : "",
keystr
);
JSValue argv[3];
argv[1] = jstr(out);
argv[2] = input2js(state);
argv[0] = jstr("emacs");
script_callee(pawn_callee, 3, argv);
argv[0] = jstr("action");
script_callee(pawn_callee, 3, argv);
if (state == INPUT_DOWN) {
key_states[btn] = INPUT_DOWN;
add_downkey(btn);
}
else if (state == INPUT_UP) {
key_states[btn] = INPUT_UP;
rm_downkey(btn);
}
}
static const uint32_t UNCHAR_FLAGS = SAPP_MODIFIER_CTRL | SAPP_MODIFIER_ALT | SAPP_MODIFIER_SUPER;
void input_key(uint32_t key, uint32_t mod)
{
if (mod & UNCHAR_FLAGS) return;
if (key <= 31 || key >= 127) return;
JSValue argv[2];
char s[2] = {key, '\0'};
argv[0] = jstr("char");
argv[1] = jstr(s);
script_callee(pawn_callee, 2, argv);
}
void register_pawn(struct callee c) {
pawn_callee = c;
}
void register_gamepad(struct callee c) {
gamepad_callee = c;
}
void input_dropped_files(int n) void input_dropped_files(int n)
{ {
JSValue argv[4]; script_evalf("prosperon.droppedfile('%s');", sapp_get_dropped_file_path(0));
argv[0] = jstr("emacs");
argv[1] = jstr("drop");
argv[2] = jstr("pressed");
argv[3] = str2js(sapp_get_dropped_file_path(0));
script_callee(pawn_callee, 4, argv);
JS_FreeValue(js,argv[3]);
}
static void pawn_call_keydown(int key) {
JSValue argv[4];
argv[0] = jstr("input");
argv[1] = jstr("num");
argv[2] = input2js(INPUT_DOWN);
/* TODO: Could cache */
argv[3] = JS_NewInt32(js, key);
script_callee(pawn_callee, 4, argv);
JS_FreeValue(js, argv[3]);
} }
/* /*
@ -211,114 +24,6 @@ static void pawn_call_keydown(int key) {
*/ */
void set_mouse_mode(int mousemode) { sapp_lock_mouse(mousemode); } void set_mouse_mode(int mousemode) { sapp_lock_mouse(mousemode); }
void input_init() {
for (int i = 0; i < 512; i++)
key_states[i] = INPUT_UP;
for (int i = 0; i < 3; i++)
mouse_states[i] = INPUT_UP;
}
#define KEYBUFLEN 50
char keybuf[KEYBUFLEN];
const char *keyname_extd(int key) {
if (key > 289 && key < 302) {
int num = key - 289;
snprintf(keybuf, KEYBUFLEN, "f%d", num);
return keybuf;
}
if (key >= 320 && key <= 329) {
int num = key - 320;
snprintf(keybuf, KEYBUFLEN, "kp%d", num);
return keybuf;
}
switch (key) {
case SAPP_KEYCODE_ENTER:
return "enter";
case SAPP_KEYCODE_ESCAPE:
return "escape";
case SAPP_KEYCODE_DELETE:
return "delete";
case SAPP_KEYCODE_INSERT:
return "insert";
case SAPP_KEYCODE_TAB:
return "tab";
case SAPP_KEYCODE_RIGHT:
return "right";
case SAPP_KEYCODE_LEFT:
return "left";
case SAPP_KEYCODE_UP:
return "up";
case SAPP_KEYCODE_DOWN:
return "down";
case SAPP_KEYCODE_LEFT_SHIFT:
return "lshift";
case SAPP_KEYCODE_RIGHT_SHIFT:
return "rshift";
case SAPP_KEYCODE_LEFT_CONTROL:
return "lctrl";
case SAPP_KEYCODE_LEFT_ALT:
return "lalt";
case SAPP_KEYCODE_RIGHT_CONTROL:
return "rctrl";
case SAPP_KEYCODE_RIGHT_ALT:
return "ralt";
case SAPP_KEYCODE_SPACE:
return "space";
case SAPP_KEYCODE_KP_ADD:
return "plus";
case '=':
return "plus";
case '-':
return "minus";
case SAPP_KEYCODE_KP_SUBTRACT:
return "minus";
case SAPP_KEYCODE_GRAVE_ACCENT:
return "`";
case SAPP_KEYCODE_LEFT_BRACKET:
return "lbracket";
case SAPP_KEYCODE_RIGHT_BRACKET:
return "rbracket";
case SAPP_KEYCODE_BACKSPACE:
return "backspace";
case SAPP_KEYCODE_PAGE_UP:
return "pgup";
case SAPP_KEYCODE_PAGE_DOWN:
return "pgdown";
}
if (key >= 32 && key <=90) {
keybuf[0] = tolower(key);
keybuf[1] = '\0';
return keybuf;
}
return "NULL";
}
void call_input_down(int *key) {
JSValue argv[3];
argv[0] = jstr("emacs");
argv[1] = jstr(keyname_extd(*key));
argv[2] = input2js(4);
script_callee(pawn_callee, 3, argv);
}
/* This is called once every frame - or more if we want it more! */
void input_poll(double wait) {
for (int i = 0; i < arrlen(downkeys); i++)
call_input_down(&downkeys[i]);
}
int key_is_num(int key) {
return key <= 57 && key >= 48;
}
void cursor_hide() { sapp_show_mouse(0); } void cursor_hide() { sapp_show_mouse(0); }
void cursor_show() { sapp_show_mouse(1); } void cursor_show() { sapp_show_mouse(1); }
@ -330,6 +35,3 @@ void cursor_img(const char *path)
[custom set]; [custom set];
*/ */
} }
int action_down(int key) { return key_states[key] == INPUT_DOWN; }
int action_up(int key) { return key_states[key] == INPUT_UP; }

View file

@ -5,35 +5,14 @@
#include <stdint.h> #include <stdint.h>
#include "HandmadeMath.h" #include "HandmadeMath.h"
extern HMM_Vec2 mousewheel;
extern HMM_Vec2 mouse_pos;
extern HMM_Vec2 mouse_delta;
#define INPUT_DOWN 0
#define INPUT_UP 1
#define INPUT_REPEAT 2
void input_init();
void input_poll(double wait);
void cursor_hide(); void cursor_hide();
void cursor_show(); void cursor_show();
void cursor_img(const char *path); void cursor_img(const char *path);
void set_mouse_mode(int mousemode); void set_mouse_mode(int mousemode);
void input_mouse(int btn, int state, uint32_t mod);
void input_mouse_move(float x, float y, float dx, float dy, uint32_t mod);
void input_mouse_scroll(float x, float y, uint32_t mod);
void input_btn(int btn, int state, uint32_t mod);
void input_key(uint32_t key, uint32_t mod);
void input_dropped_files(int n); void input_dropped_files(int n);
const char *keyname_extd(int key); const char *keyname_extd(int key);
int action_down(int key);
void register_pawn(struct callee c);
void register_gamepad(struct callee c);
void quit(); void quit();

View file

@ -351,10 +351,12 @@ char *js_nota_encode(JSValue v, char *nota)
nota = js_nota_encode(val, nota); nota = js_nota_encode(val, nota);
JS_FreeValue(js,val); JS_FreeValue(js,val);
} }
js_free(js, ptab); js_free(js, ptab);
return nota; return nota;
default:
return nota;
} }
return nota;
} }
struct rgba js2color(JSValue v) { struct rgba js2color(JSValue v) {
@ -852,10 +854,6 @@ JSValue duk_cmd(JSContext *js, JSValueConst this, int argc, JSValueConst *argv)
ret = go ? JS_DupValue(js,go->ref) : JS_UNDEFINED; ret = go ? JS_DupValue(js,go->ref) : JS_UNDEFINED;
break; break;
case 45:
ret = vec2js(mouse_pos);
break;
case 46: case 46:
set_mouse_mode(js2int(argv[1])); set_mouse_mode(js2int(argv[1]));
break; break;
@ -872,10 +870,6 @@ JSValue duk_cmd(JSContext *js, JSValueConst this, int argc, JSValueConst *argv)
ret = JS_NewInt64(js, mainwin.rheight); ret = JS_NewInt64(js, mainwin.rheight);
break; break;
case 50:
ret = JS_NewBool(js, action_down(js2int(argv[1])));
break;
case 51: case 51:
draw_cppoint(js2vec2(argv[1]), js2number(argv[2]), js2color(argv[3])); draw_cppoint(js2vec2(argv[1]), js2number(argv[2]), js2color(argv[3]));
break; break;
@ -1458,7 +1452,6 @@ JSValue duk_cmd(JSContext *js, JSValueConst this, int argc, JSValueConst *argv)
break; break;
case 264: case 264:
aspect_mode = js2int(argv[1]); aspect_mode = js2int(argv[1]);
window_resize(0,0);
break; break;
case 265: case 265:
ret = vec2js((HMM_Vec2){mainwin.width, mainwin.height}); ret = vec2js((HMM_Vec2){mainwin.width, mainwin.height});
@ -1481,52 +1474,6 @@ JSValue duk_cmd(JSContext *js, JSValueConst this, int argc, JSValueConst *argv)
return JS_UNDEFINED; return JS_UNDEFINED;
} }
JSValue duk_register(JSContext *js, JSValueConst this, int argc, JSValueConst *argv) {
int cmd = js2int(argv[0]);
struct callee c;
c.fn = argv[1];
c.obj = argv[2];
switch (cmd) {
case 0:
register_update(c);
break;
case 1:
register_physics(c);
break;
case 2:
register_gui(c);
break;
case 3:
register_nk_gui(c);
break;
case 6:
register_debug(c);
break;
case 7:
register_pawn(c);
break;
case 8:
register_gamepad(c);
break;
case 9:
stacktrace_callee = c;
break;
case 10:
register_draw(c);
break;
}
return JS_UNDEFINED;
}
void gameobject_add_shape_collider(gameobject *go, JSValue fn, struct phys2d_shape *shape) { void gameobject_add_shape_collider(gameobject *go, JSValue fn, struct phys2d_shape *shape) {
struct shape_cb shapecb; struct shape_cb shapecb;
shapecb.shape = shape; shapecb.shape = shape;
@ -2300,7 +2247,6 @@ void ffi_load() {
DUK_FUNC(make_model,2); DUK_FUNC(make_model,2);
DUK_FUNC(cmd_points, 5); DUK_FUNC(cmd_points, 5);
DUK_FUNC(cmd, 6) DUK_FUNC(cmd, 6)
DUK_FUNC(register, 3)
DUK_FUNC(register_collide, 6) DUK_FUNC(register_collide, 6)
DUK_FUNC(ui_text, 8) DUK_FUNC(ui_text, 8)

View file

@ -452,14 +452,13 @@ void full_2d_pass(struct window *window)
sprite_draw_all(); sprite_draw_all();
model_draw_all(); model_draw_all();
call_draw(); script_evalf("prosperon.draw();");
emitters_draw(); emitters_draw();
//// DEBUG //// DEBUG
if (debugDrawPhysics) { if (debugDrawPhysics) {
gameobject_draw_debugs(); gameobject_draw_debugs();
call_debugs(); script_evalf("prosperon.debug();");
} }
debug_flush(&projection); debug_flush(&projection);
@ -467,7 +466,7 @@ void full_2d_pass(struct window *window)
////// TEXT && GUI ////// TEXT && GUI
debug_nextpass(); debug_nextpass();
call_gui(); script_evalf("prosperon.gui();");
debug_flush(&hudproj); debug_flush(&hudproj);
text_flush(&hudproj); text_flush(&hudproj);
sprite_flush(); sprite_flush();

View file

@ -43,7 +43,7 @@ char pathbuf[MAXPATH + 1];
static struct cdb corecdb; static struct cdb corecdb;
static struct cdb game_cdb; static struct cdb game_cdb;
extern int LOADED_GAME = 0; int LOADED_GAME = 0;
uint8_t *gamebuf; uint8_t *gamebuf;
static void response_cb(const sfetch_response_t *r) static void response_cb(const sfetch_response_t *r)

View file

@ -154,7 +154,7 @@ JSValue script_run_bytecode(uint8_t *code, size_t len)
JSValue ret = JS_EvalFunction(js, b); JSValue ret = JS_EvalFunction(js, b);
js_print_exception(ret); js_print_exception(ret);
JS_FreeValue(js,b); JS_FreeValue(js,b);
JS_FreeValue(js,ret); return ret;
} }
struct callee stacktrace_callee; struct callee stacktrace_callee;
@ -167,7 +167,7 @@ time_t file_mod_secs(const char *file) {
void js_stacktrace() { void js_stacktrace() {
#ifndef NDEBUG #ifndef NDEBUG
call_callee(&stacktrace_callee); script_evalf("console.stack();");
#endif #endif
} }
@ -238,7 +238,7 @@ JSValue file_eval_env(const char *file, JSValue env)
JSValue v = JS_EvalThis(js, env, script, len, file, JS_EVAL_FLAGS); JSValue v = JS_EvalThis(js, env, script, len, file, JS_EVAL_FLAGS);
free(script); free(script);
js_print_exception(v); js_print_exception(v);
JS_FreeValue(js,v); return v;
} }
void script_call_sym(JSValue sym) { void script_call_sym(JSValue sym) {
@ -325,35 +325,3 @@ void send_signal(const char *signal, int argc, JSValue *argv)
JS_FreeValue(js, sig); JS_FreeValue(js, sig);
JS_FreeValue(js, fn); JS_FreeValue(js, fn);
} }
static struct callee update_callee;
void register_update(struct callee c) {
update_callee = c;
}
void call_updates(double dt) {
callee_dbl(update_callee, dt);
}
static struct callee gui_callee;
void register_gui(struct callee c) { gui_callee = c; }
void call_gui() { js_callee_exec(&gui_callee, 0, NULL); }
static struct callee nk_gui_callee;
void register_nk_gui(struct callee c) { nk_gui_callee = c; }
void call_nk_gui() { js_callee_exec(&nk_gui_callee, 0, NULL); }
static struct callee physupdate_callee;
void register_physics(struct callee c) { physupdate_callee = c; }
void call_physics(double dt) {
callee_dbl(physupdate_callee, dt);
}
struct callee debug_callee;
void register_debug(struct callee c) { debug_callee = c; }
void call_debugs() { call_callee(&debug_callee); }
static struct callee draw_callee;
void register_draw(struct callee c) { draw_callee = c; }
void call_draw() { call_callee(&draw_callee); }

View file

@ -52,27 +52,9 @@ JSValue file_eval_env(const char *file, JSValue env);
time_t file_mod_secs(const char *file); time_t file_mod_secs(const char *file);
void register_update(struct callee c);
void call_updates(double dt);
void call_debugs();
void unregister_gui(struct callee c);
void register_gui(struct callee c);
void register_debug(struct callee c);
void register_nk_gui(struct callee c);
void call_gui();
void call_nk_gui();
void unregister_obj(JSValue obj);
void send_signal(const char *signal, int argc, JSValue *argv); void send_signal(const char *signal, int argc, JSValue *argv);
void script_gc(); void script_gc();
void register_physics(struct callee c);
void call_physics(double dt);
void register_draw(struct callee c);
void call_draw();
JSValue script_run_bytecode(uint8_t *code, size_t len); JSValue script_run_bytecode(uint8_t *code, size_t len);
uint8_t *script_compile(const char *file, size_t *len); uint8_t *script_compile(const char *file, size_t *len);

View file

@ -23,12 +23,9 @@ struct Texture *icon = NULL;
void window_resize(int width, int height) void window_resize(int width, int height)
{ {
width = sapp_width();
height = sapp_height();
mainwin.dpi = sapp_dpi_scale(); mainwin.dpi = sapp_dpi_scale();
mainwin.width = sapp_width(); mainwin.width = width;
mainwin.height = sapp_height(); mainwin.height = height;
float aspect = mainwin.width/mainwin.height; float aspect = mainwin.width/mainwin.height;
float raspect = mainwin.rwidth/mainwin.rheight; float raspect = mainwin.rwidth/mainwin.rheight;
mainwin.pheight = mainwin.rheight; mainwin.pheight = mainwin.rheight;

View file

@ -11,11 +11,12 @@
#include <stdio.h> #include <stdio.h>
#include "particle.h" #include "particle.h"
#include "simplex.h" #include "simplex.h"
#include "wchar.h"
#include "locale.h"
#include "datastream.h" #include "datastream.h"
#include "timer.h" #include "timer.h"
#include "quickjs/quickjs.h" #include "quickjs/quickjs.h"
#include "jsffi.h" #include "jsffi.h"
@ -96,7 +97,6 @@ static JSValue c_init_fn;
void c_init() { void c_init() {
SAPP_STARTED = 1; SAPP_STARTED = 1;
input_init();
script_evalf("world_start();"); script_evalf("world_start();");
render_init(); render_init();
window_set_icon("icons/moon.gif"); window_set_icon("icons/moon.gif");
@ -112,8 +112,7 @@ int frame_fps() { return 1.0/sapp_frame_duration(); }
static void process_frame() static void process_frame()
{ {
double elapsed = stm_sec(stm_laptime(&frame_t)); double elapsed = stm_sec(stm_laptime(&frame_t));
script_evalf("Register.appupdate.broadcast(%g);", elapsed); script_evalf("prosperon.appupdate(%g);", elapsed);
input_poll(0);
/* Timers all update every frame - once per monitor refresh */ /* Timers all update every frame - once per monitor refresh */
timer_update(elapsed, timescale); timer_update(elapsed, timescale);
@ -125,7 +124,7 @@ static void process_frame()
updatelast = frame_t; updatelast = frame_t;
// prof_start(&prof_update); // prof_start(&prof_update);
call_updates(dt * timescale); script_evalf("prosperon.update(%g);", dt*timescale);
// prof_lap(&prof_update); // prof_lap(&prof_update);
if (sim_play == SIM_STEP) if (sim_play == SIM_STEP)
@ -138,7 +137,7 @@ static void process_frame()
// prof_start(&prof_physics); // prof_start(&prof_physics);
phys_step = 1; phys_step = 1;
phys2d_update(physMS * timescale); phys2d_update(physMS * timescale);
call_physics(physMS * timescale); script_evalf("prosperon.physupdate(%g);", physMS*timescale);
phys_step = 0; phys_step = 0;
// prof_lap(&prof_physics); // prof_lap(&prof_physics);
} }
@ -171,33 +170,37 @@ void c_clean() {
void c_event(const sapp_event *e) void c_event(const sapp_event *e)
{ {
char utf8str[6] = {0};
wchar_t wcode;
switch (e->type) { switch (e->type) {
case SAPP_EVENTTYPE_MOUSE_MOVE: case SAPP_EVENTTYPE_MOUSE_MOVE:
input_mouse_move(e->mouse_x, e->mouse_y, e->mouse_dx, e->mouse_dy, e->modifiers); script_evalf("prosperon.mousemove([%g, %g], [%g, %g]);", e->mouse_x, mainwin.height -e->mouse_y, e->mouse_dx, -e->mouse_dy);
break; break;
case SAPP_EVENTTYPE_MOUSE_SCROLL: case SAPP_EVENTTYPE_MOUSE_SCROLL:
input_mouse_scroll(e->scroll_x, e->scroll_y, e->modifiers); script_evalf("prosperon.mousescroll([%g, %g]);", e->scroll_x, e->scroll_y);
break; break;
case SAPP_EVENTTYPE_KEY_DOWN: case SAPP_EVENTTYPE_KEY_DOWN:
input_btn(e->key_code, e->key_repeat ? INPUT_REPEAT : INPUT_DOWN, e->modifiers); script_evalf("prosperon.keydown(%d, %d);", e->key_code, e->key_repeat);
break; break;
case SAPP_EVENTTYPE_KEY_UP: case SAPP_EVENTTYPE_KEY_UP:
input_btn(e->key_code, INPUT_UP, e->modifiers); script_evalf("prosperon.keyup(%d);", e->key_code);
break; break;
case SAPP_EVENTTYPE_MOUSE_UP: case SAPP_EVENTTYPE_MOUSE_UP:
input_mouse(e->mouse_button, INPUT_UP, e->modifiers); script_evalf("prosperon.mouseup(%d);", e->mouse_button);
break; break;
case SAPP_EVENTTYPE_MOUSE_DOWN: case SAPP_EVENTTYPE_MOUSE_DOWN:
input_mouse(e->mouse_button, INPUT_DOWN, e->modifiers); script_evalf("prosperon.mousedown(%d);", e->mouse_button);
break; break;
case SAPP_EVENTTYPE_CHAR: case SAPP_EVENTTYPE_CHAR:
input_key(e->char_code, e->modifiers); if (e->char_code > 127) break; /* only dealing with ascii now */
wctomb(utf8str, wcode);
script_evalf("prosperon.textinput(`%ls`);", utf8str);
break; break;
case SAPP_EVENTTYPE_RESIZED: case SAPP_EVENTTYPE_RESIZED:
@ -229,7 +232,7 @@ void c_event(const sapp_event *e)
break; break;
case SAPP_EVENTTYPE_FILES_DROPPED: case SAPP_EVENTTYPE_FILES_DROPPED:
input_mouse_move(e->mouse_x, e->mouse_y, e->mouse_dx, e->mouse_dy, e->modifiers); // input_mouse_move(e->mouse_x, e->mouse_y, e->mouse_dx, e->mouse_dy, e->modifiers);
input_dropped_files(sapp_get_num_dropped_files()); input_dropped_files(sapp_get_num_dropped_files());
break; break;
default: default:
@ -274,6 +277,7 @@ void app_name(const char *name) {
} }
int main(int argc, char **argv) { int main(int argc, char **argv) {
setlocale(LC_ALL, "en_US.utf8");
#ifndef NDEBUG #ifndef NDEBUG
log_init(); log_init();
int logout = 0; int logout = 0;