Emscripten support

This commit is contained in:
Heath Mitchell 2021-12-04 19:02:46 +00:00
parent f2874694ce
commit a4ebf7a253
No known key found for this signature in database
GPG Key ID: B0A6B2B65D23D27B
11 changed files with 761 additions and 1 deletions

2
.gitignore vendored
View File

@ -22,3 +22,5 @@
!.vscode/*.code-snippets
# End of https://www.toptal.com/developers/gitignore/api/visualstudiocode
build
html

View File

@ -104,13 +104,20 @@ export OUTPUT := $(CURDIR)/$(TARGET)
.PHONY: all clean
#---------------------------------------------------------------------------------
all: $(BUILD) generated_lut.cpp
all: $(BUILD) /usr/local/bin/http-server
@make --no-print-directory -C $(BUILD) -f $(CURDIR)/Makefile
# Don't know what I'm doing here
generated_lut.cpp: /home/heath/ti-mario-kart-py/compress.py lookup_gen_config.yaml
/usr/bin/env /bin/python3.10 /home/heath/ti-mario-kart-py/compress.py > generated_lut.cpp
# Still not really sure what I'm doing here
html/index.html: generated_lut.cpp
emcc -D FXCG_MOCK -Ifxcg-mock/include -g src/main.c ./fxcg-mock/include/fxcg/*.c -o html/index.html
browser: html/index.html
emrun --browser=chromium --browser_args=--auto-open-devtools-for-tabs html/index.html
$(BUILD):
@mkdir $@

Binary file not shown.

View File

@ -0,0 +1,66 @@
#include <emscripten.h>
#include <stdio.h>
unsigned short screen[384 * 216];
#define false 0
#define true 0
#define byte unsigned char
void Copy_ToCanvas(uint32_t* ptr, int w, int h) {
EM_ASM_({
let data = Module.HEAPU8.slice($0, $0 + $1 * $2 * 4);
let context = Module['canvas'].getContext('2d');
let imageData = context.getImageData(0, 0, $1, $2);
imageData.data.set(data);
context.putImageData(imageData, 0, 0);
}, ptr, w, h);
}
/* static void main_loop()
{
// memset(screen, 0, 320*320*4); // Clear screen
int screen[320*320],idx=0;
for (int x=0; x<320*320; x++)
screen[idx++] = 0xff000000;
for (int x=0; x<320; x++)
for (int y=0; y<320; y++)
screen[320*(x|y) + (x&y)]= 0xffffffff; // set pixel(x or y, x and y) to white... (will draw a serpinsky triangle)
Copy_ToCanvas(screen, 320, 320);
} */
void* GetVRAMAddress(void) {
emscripten_set_canvas_size(384, 216);
return &screen;
}
void PrintXY(int x, int y, const char *string, int mode, int color) {
printf("%s\n", string + 2);
}
void Bdisp_EnableColor(int n) {}
void Bdisp_PutDisp_DD(void) {
unsigned int screencopy[384 * 216];
for (int i = 0; i < (384 * 216); i++) {
int c = screen[i];
// https://gist.github.com/companje/11deb82e807f2cf927b3a0da1646e795#file-rgb565-pde-L8
byte r = (byte)(((c & 0xF800) >> 11) << 3);
byte g = (byte)(((c & 0x7E0) >> 5) << 2);
byte b = (byte)(((c & 0x1F)) << 3);
unsigned int argb = 0xff000000 | ((int)b << 16) | ((int)g << 8) | (int)r;
screencopy[i] = argb;
}
Copy_ToCanvas(screencopy, 384, 216);
}
void Bdisp_PutDisp_DD_stripe(int y1, int y2) {
Bdisp_PutDisp_DD();
}
void Bdisp_AllClr_VRAM(void) {
for (int i = 0; i < (384 * 216); i++) {
screen[i] = 0xffffffff;
}
}

View File

@ -0,0 +1,376 @@
#ifndef __FXCG_DISPLAY_H
#define __FXCG_DISPLAY_H
#ifdef __cplusplus
extern "C" {
#endif
#define LCD_WIDTH_PX 384
#define LCD_HEIGHT_PX 216
typedef unsigned short color_t;
//General display manipulating syscalls:
struct display_fill {
int x1;
int y1;
int x2;
int y2;
unsigned char mode;
};
void Bdisp_AreaClr( struct display_fill *area, unsigned char P2, unsigned short color );
void Bdisp_EnableColor( int n );
//Frame control:
void DrawFrame( int color );
unsigned short FrameColor( int mode, unsigned short color );
void DrawFrameWorkbench( int, int, int, int, int );
//VRAM general display manipulating syscalls:
void* GetVRAMAddress(void); // Return a pointer to the system's video memory.
void* GetSecondaryVRAMAddress(void); // Return a pointer the system's secondary video memory.
void Bdisp_AllClr_VRAM( void );
void Bdisp_SetPoint_VRAM( int x, int y, int color );
void Bdisp_SetPointWB_VRAM( int x, int y, int color );
unsigned short Bdisp_GetPoint_VRAM( int x, int y );
void SaveVRAM_1( void );
void LoadVRAM_1( void );
void Bdisp_Fill_VRAM( int color, int mode );
//DD display manipulating syscalls:
void Bdisp_AreaClr_DD_x3( void*p1 );
void Bdisp_DDRegisterSelect( int registerno );
void Bdisp_PutDisp_DD( void );
void Bdisp_PutDisp_DD_stripe( int y1, int y2 );
void Bdisp_SetPoint_DD( int x, int y, int color );
unsigned short Bdisp_GetPoint_DD_Workbench( int x, int y );
unsigned short Bdisp_GetPoint_DD( int x, int y );
void DirectDrawRectangle( int x1, int y1, int x2, int y2, unsigned short color );
void HourGlass( void );
void Bdisp_DefineDMARange(int x1, int x2, int y1, int y2);
unsigned short Bdisp_WriteDDRegister3_bit7(int value);
// Graphic writing:
struct display_graph {
int x;
int y;
int xofs;
int yofs;
int width;
int height;
char colormode;
char zero4;
char P20_1;
char P20_2;
int bitmap;
char color_idx1;
char color_idx2;
char color_idx3;
char P20_3;
char writemodify;
char writekind;
char zero6;
char one1;
int transparency;
};
void Bdisp_WriteGraphVRAM(struct display_graph* gd);
void Bdisp_WriteGraphDD_WB(struct display_graph* gd);
//Shape drawing:
struct display_shape {
int dx;
int dy;
int wx;
int wy;
int color;
struct display_fill saved;
};
void Bdisp_ShapeBase3XVRAM( void*shape );
void Bdisp_ShapeBase( unsigned char*work, struct display_shape *shape, int color, int line_width, int zero1, int zero2 );
void Bdisp_ShapeToVRAM16C( void*, int color );
void Bdisp_ShapeToDD( void*shape, int color );
//Background-related syscalls
void SetBackGround( int );
void WriteBackground( void*target, int width, int height, void*source, int, int, int );
//Message boxes, error messages, dialogs and the like:
void Box( int, int, int, int, int );
void BoxInnerClear( int );
void Box2( int, int );
void BoxYLimits( int lines, int*top, int*bottom );
void AUX_DisplayErrorMessage( int msgno );
void MsgBoxPush( int lines );
void MsgBoxPop( void );
void DisplayMessageBox( unsigned char*message );
short CharacterSelectDialog( void );
unsigned char ColorIndexDialog1( unsigned char initial_index, unsigned short disable_mask );
void MsgBoxMoveWB( void*buffer, int x0, int y0, int x1, int y1, int direction ); //it's more general purpose, works not only for MsgBoxes but for any VRAM contents.
//Cursor manipulating syscalls:
void locate_OS( int X, int y );
void Cursor_SetFlashOn( unsigned char cursor_type );
void Cursor_SetFlashOff( void );
int SetCursorFlashToggle( int );
void Keyboard_CursorFlash( void );
//Character printing syscalls:
enum
{
TEXT_COLOR_BLACK = 0,
TEXT_COLOR_BLUE = 1,
TEXT_COLOR_GREEN = 2,
TEXT_COLOR_CYAN = 3,
TEXT_COLOR_RED = 4,
TEXT_COLOR_PURPLE = 5,
TEXT_COLOR_YELLOW = 6,
TEXT_COLOR_WHITE = 7
};
enum
{
TEXT_MODE_NORMAL = 0x00,
TEXT_MODE_INVERT = 0x01,
TEXT_MODE_TRANSPARENT_BACKGROUND = 0x20,
TEXT_MODE_AND = 0x21
};
void PrintLine(const char *msg, int imax);
void PrintLine2(int, int, const char *, int, int, int, int, int);
void PrintXY_2( int mode, int x, int y, int msgno, int color );
void PrintXY( int x, int y, const char *string, int mode, int color );
void PrintCXY( int, int, const char *, int, int, int, int, int, int );
void PrintGlyph( int, int, unsigned char*glyph, int, int color, int back_color, int );
void*GetMiniGlyphPtr( unsigned short mb_glyph_no, unsigned short*glyph_info );
void PrintMiniGlyph(int x, int y, void*glyph, int mode_flags, int glyph_width, int, int, int, int, int color, int back_color, int );
void PrintMini( int *x, int *y, const char *MB_string, int mode_flags, unsigned int xlimit, int P6, int P7, int color, int back_color, int writeflag, int P11 );
void PrintMiniMini( int *x, int *y, const char *MB_string, int mode1, char color, int mode2 );
void Print_OS( const char*msg, int mode, int zero2 );
void Bdisp_WriteSystemMessage( int x, int y, int msgno, int mode, char color3 );
//Progressbars and scrollbars:
struct scrollbar
{
unsigned int I1; // unknown changes indicator height, set to 0
unsigned int indicatormaximum; // max logical indicator range
unsigned int indicatorheight; // height of the indicator in units
unsigned int indicatorpos; // indicator position in units of max
unsigned int I5; // unknown, set to 0
unsigned short barleft; // x position of bar
unsigned short bartop; // y position of bar
unsigned short barheight; // height of bar
unsigned short barwidth; // width of bar
} ;
void Scrollbar(struct scrollbar *scrollbar);
void StandardScrollbar( void* );
void ProgressBar(int, int );
void ProgressBar0(int P1, int P2, int P3, int current, int max);
void ProgressBar2(unsigned char *heading, int current, int max);
//Status area/header related syscalls:
// define status area
#define DSA_CLEAR 0
#define DSA_SETDEFAULT 1
// status area flags
#define SAF_BATTERY 0x0001
#define SAF_ALPHA_SHIFT 0x0002
#define SAF_SETUP_INPUT_OUTPUT 0x0004
#define SAF_SETUP_FRAC_RESULT 0x0008
#define SAF_SETUP_ANGLE 0x0010
#define SAF_SETUP_COMPLEX_MODE 0x0020
#define SAF_SETUP_DISPLAY 0x0040
#define SAF_TEXT 0x0100
#define SAF_GLYPH 0x0200
int DefineStatusAreaFlags( int, int, void*, void* );
void DefineStatusGlyph( int, void* );
void DefineStatusMessage( char*msg, short P2, char P3, char P4 );
void DisplayStatusArea( void );
void DrawHeaderLine( void );
void EnableStatusArea( int );
void Bdisp_HeaderFill( unsigned char color_idx1, unsigned char color_idx2 );
void Bdisp_HeaderFill2( unsigned int, unsigned int, unsigned char, unsigned char );
void Bdisp_HeaderText( void );
void Bdisp_HeaderText2( void );
void EnableDisplayHeader( int, int );
//Status area icon syscalls: (it may be more appropriate to use the status area flags)
void APP_EACT_StatusIcon( int ); //not sure what this is exactly for, if it displays something on screen it's here, otherwise in app.h. will test some day (gbl08ma)
void SetupMode_StatusIcon( void ); //not sure what this does, doesn't seem to be documented anywhere. will test some day (gbl08ma)
void d_c_Icon( unsigned int );
void BatteryIcon( unsigned int );
void KeyboardIcon( unsigned int );
void LineIcon( unsigned int );
void NormIcon( unsigned int );
void RadIcon( unsigned int );
void RealIcon( unsigned int );
//Other:
void FKey_Display( int, void* );
void GetFKeyPtr( int, void* );
void DispInt( int, int ); //not sure what this does, doesn't seem to be documented anywhere. will test some day (gbl08ma)
int LocalizeMessage1( int msgno, char*result );
int SMEM_MapIconToExt( unsigned char*filename, unsigned short*foldername, unsigned int*msgno, unsigned short*iconbuffer ); // despite starting with SMEM, this is mostly a graphical function used to get icons for different file types.
//Not syscalls (defined within libfxcg):
void VRAM_CopySprite(const color_t* data, int x, int y, int width, int height);
void VRAM_XORSprite(const color_t* data, int x, int y, int width, int height);
// Original Author, Shaun McFall (Merthsoft)
// Used with permission
#define COLOR_ALICEBLUE (color_t)0xF7DF
#define COLOR_ANTIQUEWHITE (color_t)0xFF5A
#define COLOR_AQUA (color_t)0x07FF
#define COLOR_AQUAMARINE (color_t)0x7FFA
#define COLOR_AZURE (color_t)0xF7FF
#define COLOR_BEIGE (color_t)0xF7BB
#define COLOR_BISQUE (color_t)0xFF38
#define COLOR_BLACK (color_t)0x0000
#define COLOR_BLANCHEDALMOND (color_t)0xFF59
#define COLOR_BLUE (color_t)0x001F
#define COLOR_BLUEVIOLET (color_t)0x895C
#define COLOR_BROWN (color_t)0xA145
#define COLOR_BURLYWOOD (color_t)0xDDD0
#define COLOR_CADETBLUE (color_t)0x5CF4
#define COLOR_CHARTREUSE (color_t)0x7FE0
#define COLOR_CHOCOLATE (color_t)0xD343
#define COLOR_CORAL (color_t)0xFBEA
#define COLOR_CORNFLOWERBLUE (color_t)0x64BD
#define COLOR_CORNSILK (color_t)0xFFDB
#define COLOR_CRIMSON (color_t)0xD8A7
#define COLOR_CYAN (color_t)0x07FF
#define COLOR_DARKBLUE (color_t)0x0011
#define COLOR_DARKCYAN (color_t)0x0451
#define COLOR_DARKGOLDENROD (color_t)0xBC21
#define COLOR_DARKGRAY (color_t)0xAD55
#define COLOR_DARKGREEN (color_t)0x0320
#define COLOR_DARKKHAKI (color_t)0xBDAD
#define COLOR_DARKMAGENTA (color_t)0x8811
#define COLOR_DARKOLIVEGREEN (color_t)0x5345
#define COLOR_DARKORANGE (color_t)0xFC60
#define COLOR_DARKORCHID (color_t)0x9999
#define COLOR_DARKRED (color_t)0x8800
#define COLOR_DARKSALMON (color_t)0xECAF
#define COLOR_DARKSEAGREEN (color_t)0x8DF1
#define COLOR_DARKSLATEBLUE (color_t)0x49F1
#define COLOR_DARKSLATEGRAY (color_t)0x2A69
#define COLOR_DARKTURQUOISE (color_t)0x067A
#define COLOR_DARKVIOLET (color_t)0x901A
#define COLOR_DEEPPINK (color_t)0xF8B2
#define COLOR_DEEPSKYBLUE (color_t)0x05FF
#define COLOR_DIMGRAY (color_t)0x6B4D
#define COLOR_DODGERBLUE (color_t)0x1C9F
#define COLOR_FIREBRICK (color_t)0xB104
#define COLOR_FLORALWHITE (color_t)0xFFDE
#define COLOR_FORESTGREEN (color_t)0x2444
#define COLOR_FUCHSIA (color_t)0xF81F
#define COLOR_GAINSBORO (color_t)0xDEFB
#define COLOR_GHOSTWHITE (color_t)0xFFDF
#define COLOR_GOLD (color_t)0xFEA0
#define COLOR_GOLDENROD (color_t)0xDD24
#define COLOR_GRAY (color_t)0x8410
#define COLOR_GREEN (color_t)0x0400
#define COLOR_GREENYELLOW (color_t)0xAFE5
#define COLOR_HONEYDEW (color_t)0xF7FE
#define COLOR_HOTPINK (color_t)0xFB56
#define COLOR_INDIANRED (color_t)0xCAEB
#define COLOR_INDIGO (color_t)0x4810
#define COLOR_IVORY (color_t)0xFFFE
#define COLOR_KHAKI (color_t)0xF731
#define COLOR_LAVENDER (color_t)0xE73F
#define COLOR_LAVENDERBLUSH (color_t)0xFF9E
#define COLOR_LAWNGREEN (color_t)0x7FE0
#define COLOR_LEMONCHIFFON (color_t)0xFFD9
#define COLOR_LIGHTBLUE (color_t)0xAEDC
#define COLOR_LIGHTCORAL (color_t)0xF410
#define COLOR_LIGHTCYAN (color_t)0xE7FF
#define COLOR_LIGHTGOLDENRODYELLOW (color_t)0xFFDA
#define COLOR_LIGHTGRAY (color_t)0xD69A
#define COLOR_LIGHTGREEN (color_t)0x9772
#define COLOR_LIGHTPINK (color_t)0xFDB8
#define COLOR_LIGHTSALMON (color_t)0xFD0F
#define COLOR_LIGHTSEAGREEN (color_t)0x2595
#define COLOR_LIGHTSKYBLUE (color_t)0x867F
#define COLOR_LIGHTSLATEGRAY (color_t)0x7453
#define COLOR_LIGHTSTEELBLUE (color_t)0xB63B
#define COLOR_LIGHTYELLOW (color_t)0xFFFC
#define COLOR_LIME (color_t)0x07E0
#define COLOR_LIMEGREEN (color_t)0x3666
#define COLOR_LINEN (color_t)0xFF9C
#define COLOR_MAGENTA (color_t)0xF81F
#define COLOR_MAROON (color_t)0x8000
#define COLOR_MEDIUMAQUAMARINE (color_t)0x6675
#define COLOR_MEDIUMBLUE (color_t)0x0019
#define COLOR_MEDIUMORCHID (color_t)0xBABA
#define COLOR_MEDIUMPURPLE (color_t)0x939B
#define COLOR_MEDIUMSEAGREEN (color_t)0x3D8E
#define COLOR_MEDIUMSLATEBLUE (color_t)0x7B5D
#define COLOR_MEDIUMSPRINGGREEN (color_t)0x07D3
#define COLOR_MEDIUMTURQUOISE (color_t)0x4E99
#define COLOR_MEDIUMVIOLETRED (color_t)0xC0B0
#define COLOR_MIDNIGHTBLUE (color_t)0x18CE
#define COLOR_MINTCREAM (color_t)0xF7FF
#define COLOR_MISTYROSE (color_t)0xFF3C
#define COLOR_MOCCASIN (color_t)0xFF36
#define COLOR_NAVAJOWHITE (color_t)0xFEF5
#define COLOR_NAVY (color_t)0x0010
#define COLOR_OLDLACE (color_t)0xFFBC
#define COLOR_OLIVE (color_t)0x8400
#define COLOR_OLIVEDRAB (color_t)0x6C64
#define COLOR_ORANGE (color_t)0xFD20
#define COLOR_ORANGERED (color_t)0xFA20
#define COLOR_ORCHID (color_t)0xDB9A
#define COLOR_PALEGOLDENROD (color_t)0xEF55
#define COLOR_PALEGREEN (color_t)0x9FD3
#define COLOR_PALETURQUOISE (color_t)0xAF7D
#define COLOR_PALEVIOLETRED (color_t)0xDB92
#define COLOR_PAPAYAWHIP (color_t)0xFF7A
#define COLOR_PEACHPUFF (color_t)0xFED7
#define COLOR_PERU (color_t)0xCC27
#define COLOR_PINK (color_t)0xFE19
#define COLOR_PLUM (color_t)0xDD1B
#define COLOR_POWDERBLUE (color_t)0xB71C
#define COLOR_PURPLE (color_t)0x8010
#define COLOR_RED (color_t)0xF800
#define COLOR_ROSYBROWN (color_t)0xBC71
#define COLOR_ROYALBLUE (color_t)0x435C
#define COLOR_SADDLEBROWN (color_t)0x8A22
#define COLOR_SALMON (color_t)0xFC0E
#define COLOR_SANDYBROWN (color_t)0xF52C
#define COLOR_SEAGREEN (color_t)0x2C4A
#define COLOR_SEASHELL (color_t)0xFFBD
#define COLOR_SIENNA (color_t)0xA285
#define COLOR_SILVER (color_t)0xC618
#define COLOR_SKYBLUE (color_t)0x867D
#define COLOR_SLATEBLUE (color_t)0x6AD9
#define COLOR_SLATEGRAY (color_t)0x7412
#define COLOR_SNOW (color_t)0xFFDF
#define COLOR_SPRINGGREEN (color_t)0x07EF
#define COLOR_STEELBLUE (color_t)0x4416
#define COLOR_TAN (color_t)0xD5B1
#define COLOR_TEAL (color_t)0x0410
#define COLOR_THISTLE (color_t)0xDDFB
#define COLOR_TOMATO (color_t)0xFB08
#define COLOR_TURQUOISE (color_t)0x471A
#define COLOR_VIOLET (color_t)0xEC1D
#define COLOR_WHEAT (color_t)0xF6F6
#define COLOR_WHITE (color_t)0xFFFF
#define COLOR_WHITESMOKE (color_t)0xF7BE
#define COLOR_YELLOW (color_t)0xFFE0
#define COLOR_YELLOWGREEN (color_t)0x9E66
// TW : So far this appears to be the most reliable way to determine model
typedef enum {
DT_CG20, // or CG10
DT_CG50,
DT_Winsim
} DeviceType;
inline DeviceType getDeviceType() {
#if TARGET_PRIZM
return (unsigned int)GetVRAMAddress() == 0xAC000000 ? DT_CG50 : DT_CG20;
#else
return DT_Winsim;
#endif
}
#ifdef __cplusplus
}
#endif
#endif /* __FXCG_DISPLAY_H */

View File

@ -0,0 +1,44 @@
#include <emscripten.h>
#include <emscripten/html5.h>
#include <stdio.h>
// Listen to EMSCRIPTEN_EVENT_KEYDOWN and EMSCRIPTEN_EVENT_KEYUP
// and print the key code to the console.
unsigned char keysPressed[256] = {0};
int setKeyState(unsigned char key, unsigned char state) {
switch (key) {
case 37: // left arrow
keysPressed[38] = state;
break;
case 39: // right arrow
keysPressed[27] = state;
break;
case 88: // x
keysPressed[78] = state;
break;
}
return 0;
}
int keyDownEvent(int eventType, const EmscriptenKeyboardEvent *keyEvent, void *userData) {
printf("keyDownEvent: %d\n", keyEvent->keyCode);
setKeyState(keyEvent->keyCode, 1);
return 0;
}
int keyUpEvent(int eventType, const EmscriptenKeyboardEvent *keyEvent, void *userData) {
printf("keyUpEvent: %d\n", keyEvent->keyCode);
setKeyState(keyEvent->keyCode, 0);
return 0;
}
int keydown(int basic_keycode) {
return keysPressed[basic_keycode];
}
void setupKeyboard() {
emscripten_set_keydown_callback("html", 0, 0, keyDownEvent);
emscripten_set_keyup_callback("html", 0, 0, keyUpEvent);
}

View File

@ -0,0 +1,235 @@
#ifndef __KEYBOARD_H__
#define __KEYBOARD_H__
// Character codes
#define KEY_CHAR_0 0x30
#define KEY_CHAR_1 0x31
#define KEY_CHAR_2 0x32
#define KEY_CHAR_3 0x33
#define KEY_CHAR_4 0x34
#define KEY_CHAR_5 0x35
#define KEY_CHAR_6 0x36
#define KEY_CHAR_7 0x37
#define KEY_CHAR_8 0x38
#define KEY_CHAR_9 0x39
#define KEY_CHAR_DP 0x2e
#define KEY_CHAR_EXP 0x0f
#define KEY_CHAR_PMINUS 0x87
#define KEY_CHAR_PLUS 0x89
#define KEY_CHAR_MINUS 0x99
#define KEY_CHAR_MULT 0xa9
#define KEY_CHAR_DIV 0xb9
#define KEY_CHAR_FRAC 0xbb
#define KEY_CHAR_LPAR 0x28
#define KEY_CHAR_RPAR 0x29
#define KEY_CHAR_COMMA 0x2c
#define KEY_CHAR_STORE 0x0e
#define KEY_CHAR_LOG 0x95
#define KEY_CHAR_LN 0x85
#define KEY_CHAR_SIN 0x81
#define KEY_CHAR_COS 0x82
#define KEY_CHAR_TAN 0x83
#define KEY_CHAR_SQUARE 0x8b
#define KEY_CHAR_POW 0xa8
#define KEY_CHAR_IMGNRY 0x7f50
#define KEY_CHAR_LIST 0x7f51
#define KEY_CHAR_MAT 0x7f40
#define KEY_CHAR_EQUAL 0x3d
#define KEY_CHAR_PI 0xd0
#define KEY_CHAR_ANS 0xc0
#define KEY_CHAR_LBRCKT 0x5b
#define KEY_CHAR_RBRCKT 0x5d
#define KEY_CHAR_LBRACE 0x7b
#define KEY_CHAR_RBRACE 0x7d
#define KEY_CHAR_CR 0x0d
#define KEY_CHAR_CUBEROOT 0x96
#define KEY_CHAR_RECIP 0x9b
#define KEY_CHAR_ANGLE 0x7f54
#define KEY_CHAR_EXPN10 0xb5
#define KEY_CHAR_EXPN 0xa5
#define KEY_CHAR_ASIN 0x91
#define KEY_CHAR_ACOS 0x92
#define KEY_CHAR_ATAN 0x93
#define KEY_CHAR_ROOT 0x86
#define KEY_CHAR_POWROOT 0xb8
#define KEY_CHAR_SPACE 0x20
#define KEY_CHAR_DQUATE 0x22
#define KEY_CHAR_VALR 0xcd
#define KEY_CHAR_THETA 0xce
#define KEY_CHAR_A 0x41
#define KEY_CHAR_B 0x42
#define KEY_CHAR_C 0x43
#define KEY_CHAR_D 0x44
#define KEY_CHAR_E 0x45
#define KEY_CHAR_F 0x46
#define KEY_CHAR_G 0x47
#define KEY_CHAR_H 0x48
#define KEY_CHAR_I 0x49
#define KEY_CHAR_J 0x4a
#define KEY_CHAR_K 0x4b
#define KEY_CHAR_L 0x4c
#define KEY_CHAR_M 0x4d
#define KEY_CHAR_N 0x4e
#define KEY_CHAR_O 0x4f
#define KEY_CHAR_P 0x50
#define KEY_CHAR_Q 0x51
#define KEY_CHAR_R 0x52
#define KEY_CHAR_S 0x53
#define KEY_CHAR_T 0x54
#define KEY_CHAR_U 0x55
#define KEY_CHAR_V 0x56
#define KEY_CHAR_W 0x57
#define KEY_CHAR_X 0x58
#define KEY_CHAR_Y 0x59
#define KEY_CHAR_Z 0x5a
/* non-capital char keys, possible in the emulator when writing with the computer keyboard
and eventually in some text-entry modes. Note that one only needs to add 0x20 to the
uppercase char key codes to get the codes for the lowercase keys.
*/
#define KEY_CHAR_LOWER_A 0x61
#define KEY_CHAR_LOWER_B 0x62
#define KEY_CHAR_LOWER_C 0x63
#define KEY_CHAR_LOWER_D 0x64
#define KEY_CHAR_LOWER_E 0x65
#define KEY_CHAR_LOWER_F 0x66
#define KEY_CHAR_LOWER_G 0x67
#define KEY_CHAR_LOWER_H 0x68
#define KEY_CHAR_LOWER_I 0x69
#define KEY_CHAR_LOWER_J 0x6A
#define KEY_CHAR_LOWER_K 0x6B
#define KEY_CHAR_LOWER_L 0x6C
#define KEY_CHAR_LOWER_M 0x6D
#define KEY_CHAR_LOWER_N 0x6E
#define KEY_CHAR_LOWER_O 0x6F
#define KEY_CHAR_LOWER_P 0x70
#define KEY_CHAR_LOWER_Q 0x71
#define KEY_CHAR_LOWER_R 0x72
#define KEY_CHAR_LOWER_S 0x73
#define KEY_CHAR_LOWER_T 0x74
#define KEY_CHAR_LOWER_U 0x75
#define KEY_CHAR_LOWER_V 0x76
#define KEY_CHAR_LOWER_W 0x77
#define KEY_CHAR_LOWER_X 0x78
#define KEY_CHAR_LOWER_Y 0x79
#define KEY_CHAR_LOWER_Z 0x7A
// Control codes
#define KEY_CTRL_NOP 0
#define KEY_CTRL_EXE 30004
#define KEY_CTRL_DEL 30025
#define KEY_CTRL_AC 30015
#define KEY_CTRL_FD 30046
#define KEY_CTRL_UNDO 30045
#define KEY_CTRL_XTT 30001
#define KEY_CTRL_EXIT 30002
#define KEY_CTRL_SHIFT 30006
#define KEY_CTRL_ALPHA 30007
#define KEY_CTRL_OPTN 30008
#define KEY_CTRL_VARS 30016
#define KEY_CTRL_UP 30018
#define KEY_CTRL_DOWN 30023
#define KEY_CTRL_LEFT 30020
#define KEY_CTRL_RIGHT 30021
#define KEY_CTRL_F1 30009
#define KEY_CTRL_F2 30010
#define KEY_CTRL_F3 30011
#define KEY_CTRL_F4 30012
#define KEY_CTRL_F5 30013
#define KEY_CTRL_F6 30014
#define KEY_CTRL_CATALOG 30100
#define KEY_CTRL_FORMAT 30101
#define KEY_CTRL_CAPTURE 30055
#define KEY_CTRL_CLIP 30050
#define KEY_CTRL_PASTE 30036
#define KEY_CTRL_INS 30033
#define KEY_CTRL_MIXEDFRAC 30054
#define KEY_CTRL_FRACCNVRT 30026
#define KEY_CTRL_QUIT 30029
#define KEY_CTRL_PRGM 30028
#define KEY_CTRL_SETUP 30037
#define KEY_CTRL_PAGEUP 30052
#define KEY_CTRL_PAGEDOWN 30053
#define KEY_CTRL_MENU 30003
#define KEY_SHIFT_OPTN 30059
#define KEY_CTRL_RESERVE1 30060
#define KEY_CTRL_RESERVE2 30061
#define KEY_SHIFT_LEFT 30062
#define KEY_SHIFT_RIGHT 30063
#define KEY_PRGM_ACON 10
#define KEY_PRGM_DOWN 37
#define KEY_PRGM_EXIT 47
#define KEY_PRGM_F1 79
#define KEY_PRGM_F2 69
#define KEY_PRGM_F3 59
#define KEY_PRGM_F4 49
#define KEY_PRGM_F5 39
#define KEY_PRGM_F6 29
#define KEY_PRGM_LEFT 38
#define KEY_PRGM_NONE 0
#define KEY_PRGM_RETURN 31
#define KEY_PRGM_RIGHT 27
#define KEY_PRGM_UP 28
#define KEY_PRGM_0 71
#define KEY_PRGM_1 72
#define KEY_PRGM_2 62
#define KEY_PRGM_3 52
#define KEY_PRGM_4 73
#define KEY_PRGM_5 63
#define KEY_PRGM_6 53
#define KEY_PRGM_7 74
#define KEY_PRGM_8 64
#define KEY_PRGM_9 54
#define KEY_PRGM_A 76
#define KEY_PRGM_F 26
#define KEY_PRGM_ALPHA 77
#define KEY_PRGM_SHIFT 78
#define KEY_PRGM_OPTN 68
#define KEY_PRGM_MENU 48
// in Bkey_GetKeyWait function
#define KEYWAIT_HALTON_TIMEROFF 0
#define KEYWAIT_HALTOFF_TIMEROFF 1
#define KEYWAIT_HALTON_TIMERON 2
#define KEYREP_NOEVENT 0
#define KEYREP_KEYEVENT 1
#define KEYREP_TIMEREVENT 2
#ifdef __cplusplus
extern "C" {
#endif
void Set_FKeys2( unsigned int p1 );
void Set_FKeys1( unsigned int p1, unsigned int*P2 );
void PRGM_GetKey_OS( unsigned char*p );
int GetKey(int*key);
int GetKeyWait_OS(int*column, int*row, int type_of_waiting, int timeout_period, int menu, unsigned short*keycode );
int PRGM_GetKey();
void DisplayMBString(unsigned char *MB_string, int start, int xpos, int x, int y);
void DisplayMBString2( int P1, unsigned char*MB_string, int start, int xpos, int x, int y, int pos_to_clear, int P8, int P9 );
void EditMBStringCtrl(unsigned char *MB_string, int posmax, int *start, int *xpos, int *key, int x, int y);
void EditMBStringCtrl2( unsigned char*MB_string, int xposmax, int*P3, int*xpos, int*key, int x, int y, int enable_pos_to_clear, int pos_to_clear );
void EditMBStringCtrl3( unsigned char*, int xposmax, void*, void*, void*, int, int, int, int, int );
void EditMBStringCtrl4( unsigned char*, int xposmax, void*, void*, void*, int, int, int, int, int, int );
int EditMBStringChar(unsigned char *MB_string, int posmax, int xpos, int char_to_insert);
void Bkey_ClrAllFlags( void );
void Bkey_SetFlag(short flagpattern);
int Keyboard_PutKeycode( int X, int Y, int Keycode);
int Keyboard_SpyMatrixCode(char*column, char*row);
void Bkey_SetAllFlags(short flags);
short Bkey_GetAllFlags( void );
// Mock functions
int keydown(int basic_keycode);
void setupKeyboard( void );
/* whether user can get into Main Menu with GetKey. 1=menu enabled, 0=menu locked.
* "Set" syscall doesn't exist, must be done through address trickery. */
int GetGetkeyToMainFunctionReturnFlag( void );
#ifdef __cplusplus
}
#endif
#endif

View File

@ -0,0 +1,6 @@
#include <emscripten.h>
#include "keyboard.h"
void initMock() {
setupKeyboard();
}

View File

@ -0,0 +1 @@
void initMock(void);

Binary file not shown.

View File

@ -1,8 +1,13 @@
#include <fxcg/display.h>
#include <fxcg/keyboard.h>
#ifndef FXCG_MOCK
#include <fxcg/misc.h>
#include <fxcg/rtc.h>
#include <fxcg/system.h>
#else
#include <fxcg/mock.h>
#include <emscripten.h>
#endif
#include "../generated_lut.cpp"
@ -226,6 +231,7 @@ float cos(int angle) {
#define PI 3.14159265358979323846
// https://www.cemetech.net/forum/viewtopic.php?p=173836&sid=9eabb0dbeddeeb6507c19c8a65dbe249
#ifndef FXCG_MOCK
int keydown(int basic_keycode) {
const unsigned short* keyboard_register = (unsigned short*)0xA44B0000;
int row, col, word, bit;
@ -235,6 +241,7 @@ int keydown(int basic_keycode) {
bit = col + 8 * (row & 1);
return (0 != (keyboard_register[word] & 1 << bit));
}
#endif
void cameraBehind(short x, short y, short objectAngle, short distance) {
// objectAngle = 90 - objectAngle;
@ -306,6 +313,7 @@ int frameCount = 0;
void main_loop() {
// Main game loop
#ifndef FXCG_MOCK
int currentTime = RTC_GetTicks();
// If 1 second has passed, print framerate
if (currentTime - lastTime >= 128) {
@ -324,6 +332,7 @@ void main_loop() {
frameCount = 0;
}
#endif
// Grass or sand = more friction
unsigned char currentTile = getTileType(kartX / scale, kartY / scale);
@ -401,6 +410,7 @@ void main_loop() {
}
exeWasPressed = exePressed;
#ifndef FXCG_MOCK
if (keydown(KEY_PRGM_MENU)) {
// Allow the OS to handle exiting to the menu
int key;
@ -408,9 +418,12 @@ void main_loop() {
Bdisp_EnableColor(1);
fillSky(0, LCD_HEIGHT_PX);
}
#endif
if (keydown(KEY_PRGM_ACON)) {
#ifndef FXCG_MOCK
PowerOff(1);
#endif
fillSky(0, LCD_HEIGHT_PX);
}
@ -439,15 +452,25 @@ void main_loop() {
}
int main() {
#ifdef FXCG_MOCK
initMock();
#endif
VRAM = (color_t*)GetVRAMAddress();
Bdisp_EnableColor(1);
fillSky(0, LCD_HEIGHT_PX);
#ifndef FXCG_MOCK
lastTime = RTC_GetTicks();
#endif
#ifdef FXCG_MOCK
emscripten_set_main_loop(main_loop, 30, 1);
#else
while (1) {
main_loop();
}
#endif
/* color_t* VRAM = (color_t*)0xA8000000; // emu address of VRAM
VRAM += (LCD_WIDTH_PX*y + x);