33
33
#include "tls.h"
34
34
#include "types.h"
35
35
#include "url.h"
36
+ #include "util.h"
36
37
#include "wasm.h"
37
38
#include "window.h"
38
39
@@ -50,6 +51,13 @@ static NWindow *win = NULL;
50
51
static Framebuffer * framebuffer = NULL ;
51
52
static uint8_t * js_framebuffer = NULL ;
52
53
54
+ void nx_console_init (nx_context_t * nx_ctx ) {
55
+ nx_ctx -> rendering_mode = NX_RENDERING_MODE_CONSOLE ;
56
+ if (print_console == NULL ) {
57
+ print_console = consoleInit (NULL );
58
+ }
59
+ }
60
+
53
61
void nx_console_exit () {
54
62
if (print_console != NULL ) {
55
63
consoleExit (print_console );
@@ -166,10 +174,7 @@ static JSValue js_print(JSContext *ctx, JSValueConst this_val, int argc,
166
174
nx_context_t * nx_ctx = JS_GetContextOpaque (ctx );
167
175
if (nx_ctx -> rendering_mode != NX_RENDERING_MODE_CONSOLE ) {
168
176
nx_framebuffer_exit ();
169
- if (print_console == NULL ) {
170
- print_console = consoleInit (NULL );
171
- }
172
- nx_ctx -> rendering_mode = NX_RENDERING_MODE_CONSOLE ;
177
+ nx_console_init (nx_ctx );
173
178
}
174
179
const char * str = JS_ToCString (ctx , argv [0 ]);
175
180
printf ("%s" , str );
@@ -514,6 +519,47 @@ void nx_process_pending_jobs(JSContext *ctx, nx_context_t *nx_ctx,
514
519
}
515
520
}
516
521
522
+ void nx_render_loading_image (nx_context_t * nx_ctx , const char * nro_path ) {
523
+ // Check if there is a `loading.jpg` file on the RomFS
524
+ // and render that to the screen if present.
525
+ size_t loading_image_size ;
526
+ const char * loading_image_path = "romfs:/loading.jpg" ;
527
+ uint8_t * loading_image = (uint8_t * )read_file (loading_image_path , & loading_image_size );
528
+ if (!loading_image && nro_path ) {
529
+ // RomFS loading_image image not found.
530
+ // Try to load from SD card, relative to the path of the NRO.
531
+ char * temp_loading_image_path = strdup (nro_path );
532
+ if (temp_loading_image_path ) {
533
+ replace_file_extension (temp_loading_image_path , ".jpg" );
534
+ loading_image = (uint8_t * )read_file (temp_loading_image_path , & loading_image_size );
535
+ free (temp_loading_image_path );
536
+ }
537
+ }
538
+ if (loading_image != NULL ) {
539
+ win = nwindowGetDefault ();
540
+ int width = 1280 ;
541
+ int height = 720 ;
542
+ js_framebuffer = malloc (width * height * 4 );
543
+ framebuffer = malloc (sizeof (Framebuffer ));
544
+ framebufferCreate (framebuffer , win , width , height , PIXEL_FORMAT_BGRA_8888 ,
545
+ 2 );
546
+ framebufferMakeLinear (framebuffer );
547
+
548
+ decode_jpeg (loading_image , loading_image_size , & js_framebuffer , & width , & height );
549
+ // TODO: ensure decompression was successful
550
+ // TODO: ensure width and height are correct
551
+
552
+ u32 stride ;
553
+ u8 * framebuf = (u8 * )framebufferBegin (framebuffer , & stride );
554
+ memcpy (framebuf , js_framebuffer , 1280 * 720 * 4 );
555
+ framebufferEnd (framebuffer );
556
+
557
+ free (js_framebuffer );
558
+ free (loading_image );
559
+ js_framebuffer = NULL ;
560
+ }
561
+ }
562
+
517
563
static SocketInitConfig const s_socketInitConfig = {
518
564
.tcp_tx_buf_size = 1 * 1024 * 1024 ,
519
565
.tcp_rx_buf_size = 1 * 1024 * 1024 ,
@@ -533,14 +579,17 @@ static SocketInitConfig const s_socketInitConfig = {
533
579
int main (int argc , char * argv []) {
534
580
Result rc ;
535
581
536
- print_console = consoleInit (NULL );
582
+ nx_context_t * nx_ctx = malloc (sizeof (nx_context_t ));
583
+ memset (nx_ctx , 0 , sizeof (nx_context_t ));
537
584
538
- rc = socketInitialize ( & s_socketInitConfig );
585
+ rc = romfsInit ( );
539
586
if (R_FAILED (rc )) {
540
587
diagAbortWithResult (rc );
541
588
}
542
589
543
- rc = romfsInit ();
590
+ nx_render_loading_image (nx_ctx , argc > 0 ? argv [0 ] : NULL );
591
+
592
+ rc = socketInitialize (& s_socketInitConfig );
544
593
if (R_FAILED (rc )) {
545
594
diagAbortWithResult (rc );
546
595
}
@@ -555,9 +604,7 @@ int main(int argc, char *argv[]) {
555
604
JSRuntime * rt = JS_NewRuntime ();
556
605
JSContext * ctx = JS_NewContext (rt );
557
606
558
- nx_context_t * nx_ctx = malloc (sizeof (nx_context_t ));
559
- memset (nx_ctx , 0 , sizeof (nx_context_t ));
560
- nx_ctx -> rendering_mode = NX_RENDERING_MODE_CONSOLE ;
607
+ nx_ctx -> rendering_mode = NX_RENDERING_MODE_INIT ;
561
608
nx_ctx -> thpool = thpool_init (4 );
562
609
nx_ctx -> frame_handler = JS_UNDEFINED ;
563
610
nx_ctx -> exit_handler = JS_UNDEFINED ;
@@ -595,20 +642,18 @@ int main(int argc, char *argv[]) {
595
642
}
596
643
597
644
if (user_code == NULL && errno == ENOENT && argc > 0 ) {
598
- // If no `main.js`, then try the `.js file with the
599
- // matching name as the `.nro` file on the SD card
645
+ // If no `main.js`, then try the `.js` file with the matching name
646
+ // as the `.nro` file on the SD card
600
647
user_path_needs_free = true;
601
648
user_code_path = strdup (argv [0 ]);
602
- size_t js_path_len = strlen (user_code_path );
603
- char * dot_nro = strstr (user_code_path , ".nro" );
604
- if (dot_nro != NULL && (dot_nro - user_code_path ) == js_path_len - 4 ) {
605
- strcpy (dot_nro , ".js" );
649
+ if (user_code_path ) {
650
+ replace_file_extension (user_code_path , ".js" );
651
+ user_code = (char * )read_file (user_code_path , & user_code_size );
606
652
}
607
-
608
- user_code = (char * )read_file (user_code_path , & user_code_size );
609
653
}
610
654
611
655
if (user_code == NULL ) {
656
+ nx_console_init (nx_ctx );
612
657
printf ("%s: %s\n" , strerror (errno ), user_code_path );
613
658
if (user_path_needs_free ) {
614
659
free (user_code_path );
@@ -743,6 +788,7 @@ int main(int argc, char *argv[]) {
743
788
}
744
789
runtime_init_result = JS_EvalFunction (ctx , runtime_init_func );
745
790
if (JS_IsException (runtime_init_result )) {
791
+ nx_console_init (nx_ctx );
746
792
printf ("Runtime initialization failed\n" );
747
793
print_js_error (ctx );
748
794
nx_ctx -> had_error = 1 ;
0 commit comments