naev 0.10.4
gui.c
Go to the documentation of this file.
1/*
2 * See Licensing and Copyright notice in naev.h
3 */
10#include <stdlib.h>
11
12#include "naev.h"
15#include "gui.h"
16
17#include "ai.h"
18#include "camera.h"
19#include "comm.h"
20#include "conf.h"
21#include "dialogue.h"
22#include "economy.h"
23#include "font.h"
24#include "gui_omsg.h"
25#include "gui_osd.h"
26#include "hook.h"
27#include "input.h"
28#include "intro.h"
29#include "land.h"
30#include "log.h"
31#include "map.h"
32#include "map_overlay.h"
33#include "menu.h"
34#include "mission.h"
35#include "music.h"
36#include "ndata.h"
37#include "nebula.h"
38#include "nfile.h"
39#include "nlua.h"
40#include "nlua_gfx.h"
41#include "nlua_gui.h"
42#include "nlua_misn.h"
43#include "nlua_tex.h"
44#include "nlua_tk.h"
45#include "nluadef.h"
46#include "nmath.h"
47#include "nstring.h"
48#include "ntime.h"
49#include "nxml.h"
50#include "opengl.h"
51#include "pause.h"
52#include "pilot.h"
53#include "pilot.h"
54#include "player.h"
55#include "render.h"
56#include "rng.h"
57#include "sound.h"
58#include "space.h"
59#include "spfx.h"
60#include "toolkit.h"
61#include "unidiff.h"
62
63#define XML_GUI_ID "GUIs"
64#define XML_GUI_TAG "gui"
66#define RADAR_BLINK_PILOT 0.5
67#define RADAR_BLINK_SPOB 1.
69/* some blinking stuff. */
70static double blink_pilot = 0.;
71static double blink_spob = 0.;
72static double animation_dt = 0.;
74/* for VBO. */
75static gl_vbo *gui_radar_select_vbo = NULL;
76
77static int gui_getMessage = 1;
78static char *gui_name = NULL;
80extern unsigned int land_wid;
85static nlua_env gui_env = LUA_NOREF;
86static int gui_L_mclick = 0;
87static int gui_L_mmove = 0;
92static double gui_viewport_x = 0.;
93static double gui_viewport_y = 0.;
94static double gui_viewport_w = 0.;
95static double gui_viewport_h = 0.;
102typedef struct Radar_ {
103 double w;
104 double h;
105 double x;
106 double y;
107 RadarShape shape;
108 double res;
109} Radar;
110/* radar resolutions */
111#define RADAR_RES_MAX 300.
112#define RADAR_RES_REF 100.
113#define RADAR_RES_MIN 10.
114#define RADAR_RES_INTERVAL 10.
115static Radar gui_radar;
116
117/* needed to render properly */
118static double gui_xoff = 0.;
119static double gui_yoff = 0.;
121/* messages */
122static const int mesg_max = 128;
123static int mesg_pointer = 0;
124static int mesg_viewpoint = -1;
125static const double mesg_timeout = 15.;
131typedef struct Mesg_ {
132 char *str;
133 double t;
135} Mesg;
136static Mesg* mesg_stack = NULL;
137static int gui_mesg_w = 0;
138static int gui_mesg_x = 0;
139static int gui_mesg_y = 0;
141/* Calculations to speed up borders. */
142static double gui_tr = 0.;
143static double gui_br = 0.;
144static double gui_tl = 0.;
145static double gui_bl = 0.;
147/* Intrinsic graphical stuff. */
148static glTexture *gui_ico_hail = NULL;
152/* Lua Stuff. */
153static int gui_lua_create = LUA_NOREF;
154static int gui_lua_render = LUA_NOREF;
155static int gui_lua_render_cooldown = LUA_NOREF;
156static int gui_lua_cooldown_end = LUA_NOREF;
157static int gui_lua_mouse_move = LUA_NOREF;
158static int gui_lua_mouse_click = LUA_NOREF;
159static int gui_lua_update_cargo = LUA_NOREF;
160static int gui_lua_update_nav = LUA_NOREF;
161static int gui_lua_update_target = LUA_NOREF;
162static int gui_lua_update_ship = LUA_NOREF;
163static int gui_lua_update_system = LUA_NOREF;
164static int gui_lua_update_faction = LUA_NOREF;
165static int gui_lua_update_effects = LUA_NOREF;
166
167/*
168 * prototypes
169 */
170/*
171 * external
172 */
173extern void weapon_minimap( const double res, const double w, const double h,
174 const RadarShape shape, double alpha );
175/*
176 * internal
177 */
178/* gui */
179static void gui_renderTargetReticles( const SimpleShader *shd, double x, double y, double radius, double angle, const glColour* c );
180static void gui_borderIntersection( double *cx, double *cy, double rx, double ry, double hw, double hh );
181/* Render GUI. */
182static void gui_renderPilotTarget (void);
183static void gui_renderSpobTarget (void);
184static void gui_renderBorder( double dt );
185static void gui_renderMessages( double dt );
186static const glColour *gui_getSpobColour( int i );
187static void gui_renderRadarOutOfRange( RadarShape sh, int w, int h, int cx, int cy, const glColour *col );
188static void gui_blink( double cx, double cy, double vr, const glColour *col, double blinkInterval, double blinkVar );
189static const glColour* gui_getPilotColour( const Pilot* p );
190static void gui_calcBorders (void);
191/* Lua GUI. */
192static int gui_doFunc( int func_ref, const char *func_name );
193static int gui_prepFunc( int func_ref, const char *func_name );
194static int gui_runFunc( const char *func, int nargs, int nret );
195
200{
203}
204
212void gui_messageInit( int width, int x, int y )
213{
214 gui_mesg_w = width;
215 gui_mesg_x = x;
216 gui_mesg_y = y;
217}
218
224void gui_messageScrollUp( int lines )
225{
226 int o;
227
228 /* Handle hacks. */
229 if (mesg_viewpoint == -1) {
231 return;
232 }
233
234 /* Get offset. */
236 if (o < 0)
237 o += mesg_max;
238 o = mesg_max - 2*conf.mesg_visible - o;
239
240 /* Calculate max line movement. */
241 if (lines > o)
242 lines = o;
243
244 /* Move viewpoint. */
246}
247
253void gui_messageScrollDown( int lines )
254{
255 int o;
256
257 /* Handle hacks. */
259 mesg_viewpoint = -1;
260 return;
261 }
262 else if (mesg_viewpoint == -1)
263 return;
264
265 /* Get offset. */
267 if (o < 0)
268 o += mesg_max;
269
270 /* Calculate max line movement. */
271 if (lines > o)
272 lines = o;
273
274 /* Move viewpoint. */
276}
277
283void player_messageToggle( int enable )
284{
285 gui_getMessage = enable;
286}
287
293void player_messageRaw( const char *str )
294{
296
297 /* Must be receiving messages. */
298 if (!gui_getMessage)
299 return;
300
301 gl_printLineIteratorInit( &iter, &gl_smallFont, str, gui_mesg_w - ((str[0] == '\t') ? 45 : 15) );
302 while (gl_printLineIteratorNext( &iter )) {
303 /* Move pointer. */
305 if (mesg_viewpoint != -1)
307
308 /* Add the new one */
309 free( mesg_stack[mesg_pointer].str );
310 if (iter.l_begin == 0) {
311 mesg_stack[mesg_pointer].str = strndup( &str[iter.l_begin], iter.l_end - iter.l_begin );
313 }
314 else {
315 mesg_stack[mesg_pointer].str = malloc( iter.l_end - iter.l_begin + 2 );
316 snprintf( mesg_stack[mesg_pointer].str, iter.l_end - iter.l_begin + 2, "\t%s", &str[iter.l_begin] );
317 gl_printStoreMax( &mesg_stack[mesg_pointer].restore, str, iter.l_begin );
318 }
320
321 iter.width = gui_mesg_w - 45; /* Remaining lines are tabbed so it's shorter. */
322 }
323}
324
330void player_message( const char *fmt, ... )
331{
332 va_list ap;
333 char *buf;
334
335 /* Must be receiving messages. */
336 if (!gui_getMessage)
337 return;
338
339 /* Add the new one */
340 va_start( ap, fmt );
341 vasprintf( &buf, fmt, ap );
342 va_end( ap );
343 player_messageRaw( buf );
344 free( buf );
345}
346
350static void gui_renderSpobTarget (void)
351{
352 double x,y, r;
353 const glColour *c;
354
355 /* no need to draw if pilot is dead */
356 if (player_isFlag(PLAYER_DESTROYED) || player_isFlag(PLAYER_CREATING) ||
357 (player.p == NULL) || pilot_isFlag(player.p,PILOT_DEAD))
358 return;
359
360 /* Make sure target exists. */
361 if ((player.p->nav_spob < 0) && (player.p->nav_hyperspace < 0)
362 && (player.p->nav_asteroid < 0))
363 return;
364
365 /* Make sure targets are still in range. */
366#if 0
369 return;
370 }
371#endif
372
373 /* Draw spob and jump point target graphics. */
374 if (player.p->nav_hyperspace >= 0) {
375 JumpPoint *jp = &cur_system->jumps[player.p->nav_hyperspace];
376
377 if (jp_isKnown(jp)) {
378 c = &cGreen;
379 x = jp->pos.x;
380 y = jp->pos.y;
381 r = jumppoint_gfx->sw * 0.5;
382 gui_renderTargetReticles( &shaders.targetspob, x, y, r, 0., c );
383 }
384 }
385 if (player.p->nav_spob >= 0) {
386 Spob *spob = cur_system->spobs[player.p->nav_spob];
387 c = spob_getColour( spob );
388 x = spob->pos.x;
389 y = spob->pos.y;
390 r = spob->radius;
391 gui_renderTargetReticles( &shaders.targetspob, x, y, r, 0., c );
392 }
393 if (player.p->nav_asteroid >= 0) {
394 AsteroidAnchor *field = &cur_system->asteroids[player.p->nav_anchor];
395 Asteroid *ast = &field->asteroids[player.p->nav_asteroid];
396 c = &cWhite;
397
398 x = ast->pos.x;
399 y = ast->pos.y;
400 r = ast->gfx->sw * 0.5;
401 gui_renderTargetReticles( &shaders.targetship, x, y, r, 0., c );
402 }
403}
404
415static void gui_renderTargetReticles( const SimpleShader *shd, double x, double y, double radius, double angle, const glColour* c )
416{
417 double rx, ry, r;
418 /* Must not be NULL. */
419 if (gui_target_spob == NULL)
420 return;
421
422 gl_gameToScreenCoords( &rx, &ry, x, y );
423 r = (double)radius * 1.2 * cam_getZoom();
424
425 glUseProgram(shd->program);
426 glUniform1f(shd->dt, animation_dt);
427 glUniform1f(shd->paramf, radius);
428 gl_renderShader( rx, ry, r, r, angle, shd, c, 1 );
429}
430
434static void gui_renderPilotTarget (void)
435{
436 Pilot *p;
437 const glColour *c;
438
439 /* Player is most likely dead. */
440 if (gui_target_pilot == NULL)
441 return;
442
443 /* Get the target. */
444 if (player.p->target != PLAYER_ID)
445 p = pilot_get(player.p->target);
446 else p = NULL;
447
448 /* Make sure pilot exists and is still alive. */
449 if ((p==NULL) || pilot_isFlag(p,PILOT_DEAD)) {
452 return;
453 }
454
455 /* Make sure target is still valid and in range. */
456 if (!pilot_validTarget( player.p, p )) {
459 return;
460 }
461
462 /* Draw the pilot target. */
463 if (pilot_isDisabled(p))
464 c = &cInert;
465 else if (pilot_isHostile(p))
466 c = &cHostile;
467 else if (pilot_isFriendly(p))
468 c = &cFriend;
469 else
470 c = &cNeutral;
471
472 gui_renderTargetReticles( &shaders.targetship, p->solid->pos.x, p->solid->pos.y, p->ship->gfx_space->sw * 0.5, p->solid->dir, c );
473}
474
487static void gui_borderIntersection( double *cx, double *cy, double rx, double ry, double hw, double hh )
488{
489 double a;
490 double w, h;
491
492 /* Get angle. */
493 a = atan2( ry, rx );
494 if (a < 0.)
495 a += 2.*M_PI;
496
497 /* Helpers. */
498 w = hw-7.;
499 h = hh-7.;
500
501 /* Handle by quadrant. */
502 if ((a > gui_tr) && (a < gui_tl)) { /* Top. */
503 *cx = h * (rx/ry);
504 *cy = h;
505 }
506 else if ((a > gui_tl) && (a < gui_bl)) { /* Left. */
507 *cx = -w;
508 *cy = -w * (ry/rx);
509 }
510 else if ((a > gui_bl) && (a < gui_br)) { /* Bottom. */
511 *cx = -h * (rx/ry);
512 *cy = -h;
513 }
514 else { /* Right. */
515 *cx = w;
516 *cy = w * (ry/rx);
517 }
518
519 /* Translate. */
520 *cx += hw;
521 *cy += hh;
522}
523
529static void gui_renderBorder( double dt )
530{
531 (void) dt;
532 int hw, hh;
533 double rx,ry;
534 double cx,cy;
535 const glColour *col;
536 Pilot *const* pilot_stack;
537
538 /* Get player position. */
539 hw = SCREEN_W/2;
540 hh = SCREEN_H/2;
541
542 /* Render borders to enhance contrast. */
543 gl_renderRect( 0., 0., 15., SCREEN_H, &cBlackHilight );
544 gl_renderRect( SCREEN_W - 15., 0., 15., SCREEN_H, &cBlackHilight );
545 gl_renderRect( 15., 0., SCREEN_W - 30., 15., &cBlackHilight );
546 gl_renderRect( 15., SCREEN_H - 15., SCREEN_W - 30., 15., &cBlackHilight );
547
548 /* Draw spobs. */
549 for (int i=0; i<array_size(cur_system->spobs); i++) {
550 Spob *pnt = cur_system->spobs[i];
551
552 /* Skip if unknown. */
553 if (!spob_isKnown( pnt ))
554 continue;
555
556 /* Check if out of range. */
557 if (!gui_onScreenSpob( &rx, &ry, NULL, pnt )) {
558
559 /* Get border intersection. */
560 gui_borderIntersection( &cx, &cy, rx, ry, hw, hh );
561
562 col = gui_getSpobColour(i);
563 gl_renderCircle(cx, cy, 5, col, 0);
564 }
565 }
566
567 /* Draw jump routes. */
568 for (int i=0; i<array_size(cur_system->jumps); i++) {
569 JumpPoint *jp = &cur_system->jumps[i];
570
571 /* Skip if unknown or exit-only. */
572 if (!jp_isUsable( jp ))
573 continue;
574
575 /* Check if out of range. */
576 if (!gui_onScreenSpob( &rx, &ry, jp, NULL )) {
577
578 /* Get border intersection. */
579 gui_borderIntersection( &cx, &cy, rx, ry, hw, hh );
580
581 if (i==player.p->nav_hyperspace)
582 col = &cGreen;
583 else
584 col = &cWhite;
585
586 gl_renderTriangleEmpty( cx, cy, -jp->angle, 10., 1., col );
587 }
588 }
589
590 /* Draw pilots. */
592 for (int i=1; i<array_size(pilot_stack); i++) { /* skip the player */
593 Pilot *plt = pilot_stack[i];
594
595 /* See if in sensor range. */
596 if (!pilot_inRangePilot(player.p, plt, NULL))
597 continue;
598
599 /* Check if out of range. */
600 if (!gui_onScreenPilot( &rx, &ry, plt )) {
601
602 /* Get border intersection. */
603 gui_borderIntersection( &cx, &cy, rx, ry, hw, hh );
604
605 col = gui_getPilotColour(plt);
606 gl_renderRectEmpty(cx-5, cy-5, 10, 10, col);
607 }
608 }
609}
610
619int gui_onScreenPilot( double *rx, double *ry, const Pilot *pilot )
620{
621 double z;
622 int cw, ch;
623 glTexture *tex;
624
625 z = cam_getZoom();
626
627 tex = pilot->ship->gfx_space;
628
629 /* Get relative positions. */
630 *rx = (pilot->solid->pos.x - player.p->solid->pos.x)*z;
631 *ry = (pilot->solid->pos.y - player.p->solid->pos.y)*z;
632
633 /* Correct for offset. */
634 *rx -= gui_xoff;
635 *ry -= gui_yoff;
636
637 /* Compare dimensions. */
638 cw = SCREEN_W/2 + tex->sw/2;
639 ch = SCREEN_H/2 + tex->sh/2;
640
641 if ((ABS(*rx) > cw) || (ABS(*ry) > ch))
642 return 0;
643
644 return 1;
645}
646
656int gui_onScreenSpob( double *rx, double *ry, const JumpPoint *jp, const Spob *pnt )
657{
658 double z;
659 int cw, ch;
660 glTexture *tex;
661
662 z = cam_getZoom();
663
664 if (jp == NULL) {
665 tex = pnt->gfx_space;
666 *rx = (pnt->pos.x - player.p->solid->pos.x)*z;
667 *ry = (pnt->pos.y - player.p->solid->pos.y)*z;
668 }
669 else {
670 tex = jumppoint_gfx;
671 *rx = (jp->pos.x - player.p->solid->pos.x)*z;
672 *ry = (jp->pos.y - player.p->solid->pos.y)*z;
673 }
674
675 /* Correct for offset. */
676 *rx -= gui_xoff;
677 *ry -= gui_yoff;
678
679 /* Compare dimensions. */
680 cw = SCREEN_W/2;
681 ch = SCREEN_H/2;
682 if (tex != NULL) {
683 cw += tex->sw/2;
684 ch += tex->sh/2;
685 }
686
687 if ((ABS(*rx) > cw) || (ABS(*ry) > ch))
688 return 0;
689
690 return 1;
691}
692
698void gui_renderReticles( double dt )
699{
700 (void) dt;
701
702 /* Player must be alive. */
703 if (player.p == NULL)
704 return;
705
706 /* Disable in cinematics. */
707 if (player_isFlag(PLAYER_CINEMATICS))
708 return;
709
712}
713
714static int can_jump = 0;
720void gui_render( double dt )
721{
722 double fade, direction;
723
724 /* If player is dead just render the cinematic mode. */
725 if (!menu_isOpen(MENU_MAIN) &&
726 (player_isFlag(PLAYER_DESTROYED) || player_isFlag(PLAYER_CREATING) ||
727 ((player.p != NULL) && pilot_isFlag(player.p,PILOT_DEAD)))) {
728 gl_viewport( 0., 0., SCREEN_W, SCREEN_H );
731 return;
732 }
733
734 /* Make sure player is valid. */
735 if (player.p == NULL)
736 return;
737
738 /* Cinematics mode. */
739 if (player_isFlag( PLAYER_CINEMATICS_GUI ))
740 return;
741
742 /*
743 * Countdown timers.
744 */
745 animation_dt += dt / dt_mod;
746 blink_pilot -= dt / dt_mod;
747 if (blink_pilot < 0.)
749 blink_spob -= dt / dt_mod;
750 if (blink_spob < 0.)
752
753 /* Render the border ships and targets. */
755
756 /* Set viewport. */
757 gl_viewport( 0., 0., gl_screen.rw, gl_screen.rh );
758
759 /* Run Lua. */
760 if (gui_env != LUA_NOREF) {
761 if (gui_prepFunc( gui_lua_render, "render" )==0) {
762 lua_pushnumber( naevL, dt );
763 lua_pushnumber( naevL, dt_mod );
764 gui_runFunc( "render", 2, 0 );
765 }
766 if (pilot_isFlag(player.p, PILOT_COOLDOWN)) {
767 if (gui_prepFunc( gui_lua_render_cooldown, "render_cooldown" )==0) {
768 lua_pushnumber( naevL, player.p->ctimer / player.p->cdelay );
769 lua_pushnumber( naevL, player.p->ctimer );
770 gui_runFunc( "render_cooldown", 2, 0 );
771 }
772 }
773 }
774
775 /* Messages. */
777
778 /* OSD. */
779 osd_render();
780
781 /* Noise when getting near a jump. */
782 if (player.p->nav_hyperspace >= 0) { /* hyperspace target */
783 /* Determine if we have to play the "enter hyperspace range" sound. */
785 if ((i != 0) && (i != can_jump))
786 if (!pilot_isFlag(player.p, PILOT_HYPERSPACE))
788 can_jump = i;
789 }
790
791 /* Determine if we need to fade in/out. */
792 fade = direction = 0.;
793 if (pilot_isFlag(player.p, PILOT_HYPERSPACE) &&
794 (player.p->ptimer < HYPERSPACE_FADEOUT)) {
795 fade = (HYPERSPACE_FADEOUT-player.p->ptimer) / HYPERSPACE_FADEOUT;
796 direction = VANGLE(player.p->solid->vel);
797 }
798 else if (pilot_isFlag(player.p, PILOT_HYP_END) &&
799 player.p->ptimer > 0.) {
800 fade = player.p->ptimer / HYPERSPACE_FADEIN;
801 direction = VANGLE(player.p->solid->vel) + M_PI;
802 }
803 /* Perform the fade. */
804 if (fade > 0.) {
805 mat4 projection = gl_view_matrix;
806
807 /* Set up the program. */
808 glUseProgram( shaders.jump.program );
809 glEnableVertexAttribArray( shaders.jump.vertex );
810 gl_vboActivateAttribOffset( gl_squareVBO, shaders.jump.vertex, 0, 2, GL_FLOAT, 0 );
811
812 /* Set up the projection. */
813 mat4_scale( &projection, gl_screen.nw, gl_screen.nh, 1. );
814
815 /* Pass stuff over. */
816 gl_uniformMat4( shaders.jump.projection, &projection );
817 glUniform1f( shaders.jump.progress, fade );
818 glUniform1f( shaders.jump.direction, direction );
819 glUniform2f( shaders.jump.dimensions, gl_screen.nw, gl_screen.nh );
820 glUniform1f( shaders.jump.brightness, conf.jump_brightness );
821
822 /* Set the subroutine. */
823 if (gl_has( OPENGL_SUBROUTINES )) {
824 if (cur_system->nebu_density > 0.)
825 glUniformSubroutinesuiv( GL_FRAGMENT_SHADER, 1, &shaders.jump.jump_func.jump_nebula );
826 else
827 glUniformSubroutinesuiv( GL_FRAGMENT_SHADER, 1, &shaders.jump.jump_func.jump_wind );
828 }
829
830 /* Draw. */
831 glDrawArrays( GL_TRIANGLE_STRIP, 0, 4 );
832
833 /* Clear state. */
834 glDisableVertexAttribArray( shaders.jump.vertex );
835 glUseProgram(0);
836
837 /* Check errors. */
838 gl_checkErr();
839 }
840
841 /* Reset viewport. */
843
844 /* Render messages. */
845 omsg_render( dt );
846}
847
852{
853 gui_doFunc( gui_lua_cooldown_end, "cooldown_end" );
854}
855
863int gui_radarInit( int circle, int w, int h )
864{
865 gui_radar.shape = circle ? RADAR_CIRCLE : RADAR_RECT;
866 gui_radar.w = w;
867 gui_radar.h = h;
869 return 0;
870}
871
878void gui_radarRender( double x, double y )
879{
880 int f;
881 Radar *radar;
882 mat4 view_matrix_prev;
883 Pilot *const* pilot_stack;
884
885 if (!conf.always_radar && ovr_isOpen())
886 return;
887
888 /* The global radar. */
889 radar = &gui_radar;
890 gui_radar.x = x;
891 gui_radar.y = y;
892
893 /* TODO: modifying gl_view_matrix like this is a bit of a hack */
894 /* TODO: use stensil test for RADAR_CIRCLE */
895 view_matrix_prev = gl_view_matrix;
896 if (radar->shape==RADAR_RECT) {
897 gl_clipRect( x, y, radar->w, radar->h );
898 mat4_translate( &gl_view_matrix,
899 x + radar->w/2., y + radar->h/2., 0 );
900 }
901 else if (radar->shape==RADAR_CIRCLE)
902 mat4_translate( &gl_view_matrix,
903 x, y, 0 );
904
905 /*
906 * spobs
907 */
908 for (int i=0; i<array_size(cur_system->spobs); i++)
909 if (i != player.p->nav_spob)
910 gui_renderSpob( i, radar->shape, radar->w, radar->h, radar->res, 1., 0 );
911 if (player.p->nav_spob > -1)
912 gui_renderSpob( player.p->nav_spob, radar->shape, radar->w, radar->h, radar->res, 1., 0 );
913
914 /*
915 * Jump points.
916 */
917 for (int i=0; i<array_size(cur_system->jumps); i++) {
918 JumpPoint *jp = &cur_system->jumps[i];
919 if (i != player.p->nav_hyperspace && jp_isUsable(jp))
920 gui_renderJumpPoint( i, radar->shape, radar->w, radar->h, radar->res, 1., 0 );
921 }
922 if (player.p->nav_hyperspace > -1)
923 gui_renderJumpPoint( player.p->nav_hyperspace, radar->shape, radar->w, radar->h, radar->res, 1., 0 );
924
925 /*
926 * weapons
927 */
928 weapon_minimap( radar->res, radar->w, radar->h,
929 radar->shape, 1. );
930
931 /* render the pilot */
933 f = 0;
934 for (int i=1; i<array_size(pilot_stack); i++) { /* skip the player */
935 if (pilot_stack[i]->id == player.p->target)
936 f = i;
937 else
938 gui_renderPilot( pilot_stack[i], radar->shape, radar->w, radar->h, radar->res, 0 );
939 }
940 /* render the targeted pilot */
941 if (f != 0)
942 gui_renderPilot( pilot_stack[f], radar->shape, radar->w, radar->h, radar->res, 0 );
943
944 /* render the asteroids */
945 for (int i=0; i<array_size(cur_system->asteroids); i++) {
946 AsteroidAnchor *ast = &cur_system->asteroids[i];
947 for (int j=0; j<ast->nb; j++)
948 gui_renderAsteroid( &ast->asteroids[j], radar->w, radar->h, radar->res, 0 );
949 }
950
951 /* Render the player. */
952 gui_renderPlayer( radar->res, 0 );
953
954 /* Undo the horrible hack. */
955 gl_view_matrix = view_matrix_prev;
956 if (radar->shape==RADAR_RECT)
958}
959
965void gui_radarGetRes( double* res )
966{
967 *res = gui_radar.res;
968}
969
974{
975 for (int i=0; i < mesg_max; i++)
976 free( mesg_stack[i].str );
977 memset( mesg_stack, 0, sizeof(Mesg)*mesg_max );
978}
979
985static void gui_renderMessages( double dt )
986{
987 double x, y, h, hs, vx, vy, dy;
988 int v, o;
989 glColour c = {.r=1., .g=1., .b=1.};
990 const glColour msgc = {.r=0., .g=0., .b=0., .a=0.6};
991
992 /* Coordinate translation. */
993 x = gui_mesg_x;
994 y = gui_mesg_y;
995
996 /* Handle viewpoint hacks. */
997 v = mesg_viewpoint;
998 if (v == -1)
999 v = mesg_pointer;
1000
1001 /* Render background. */
1002 h = 0;
1003
1004 /* Set up position. */
1005 vx = x;
1006 vy = y;
1007
1008 /* Must be run here. */
1009 hs = 0.;
1010 o = 0;
1011 if (mesg_viewpoint != -1) {
1012 /* Data. */
1013 hs = h*(double)conf.mesg_visible/(double)mesg_max;
1015 if (o < 0)
1016 o += mesg_max;
1017 }
1018
1019 /* Render text. */
1020 for (int i=0; i<conf.mesg_visible; i++) {
1021 /* Reference translation. */
1022 int m = (v - i) % mesg_max;
1023 if (m < 0)
1024 m += mesg_max;
1025
1026 /* Timer handling. */
1027 if ((mesg_viewpoint != -1) || (mesg_stack[m].t >= 0.)) {
1028 /* Decrement timer. */
1029 if (mesg_viewpoint == -1)
1030 mesg_stack[m].t -= dt / dt_mod;
1031
1032 /* Only handle non-NULL messages. */
1033 if (mesg_stack[m].str != NULL) {
1034 if (mesg_stack[m].str[0] == '\t') {
1035 gl_printRestore( &mesg_stack[m].restore );
1036 dy = gl_printHeightRaw( &gl_smallFont, gui_mesg_w, &mesg_stack[m].str[1]) + 6;
1037 gl_renderRect( x-4., y-1., gui_mesg_w-13., dy, &msgc );
1038 gl_printMaxRaw( &gl_smallFont, gui_mesg_w - 45., x + 30, y + 3, &cFontWhite, -1., &mesg_stack[m].str[1] );
1039 } else {
1041 gl_renderRect( x-4., y-1., gui_mesg_w-13., dy, &msgc );
1042 gl_printMaxRaw( &gl_smallFont, gui_mesg_w - 15., x, y + 3, &cFontWhite, -1., mesg_stack[m].str );
1043 }
1044 h += dy;
1045 y += dy;
1046 }
1047 }
1048
1049 /* Increase position. */
1050 }
1051
1052 /* Render position. */
1053 if (mesg_viewpoint != -1) {
1054 /* Border. */
1055 c.a = 0.2;
1056 gl_renderRect( vx + gui_mesg_w-10., vy, 10, h, &c );
1057
1058 /* Inside. */
1059 c.a = 0.5;
1060 gl_renderRect( vx + gui_mesg_w-10., vy + hs/2. + (h-hs)*((double)o/(double)(mesg_max-conf.mesg_visible)), 10, hs, &c );
1061 }
1062}
1063
1072static const glColour* gui_getPilotColour( const Pilot* p )
1073{
1074 const glColour *col;
1075
1076 if (p->id == player.p->target)
1077 col = &cRadar_tPilot;
1078 else
1079 col = pilot_getColour(p);
1080
1081 return col;
1082}
1083
1094void gui_renderPilot( const Pilot* p, RadarShape shape, double w, double h, double res, int overlay )
1095{
1096 double x, y, scale, ssize;
1097 const glColour *col;
1098
1099 /* Make sure is in range. */
1100 if (!pilot_validTarget( player.p, p ))
1101 return;
1102
1103 /* Get position. */
1104 if (overlay) {
1105 x = (p->solid->pos.x / res);
1106 y = (p->solid->pos.y / res);
1107 }
1108 else {
1109 x = ((p->solid->pos.x - player.p->solid->pos.x) / res);
1110 y = ((p->solid->pos.y - player.p->solid->pos.y) / res);
1111 }
1112 /* Get size. */
1113 ssize = sqrt( (double)ship_size( p->ship ) );
1114 scale = (ssize + 1.)/2. * (1. + RADAR_RES_REF / res );
1115
1116 /* Check if pilot in range. */
1117 if ( ((shape==RADAR_RECT) &&
1118 ((ABS(x) > (w+scale)/2.) || (ABS(y) > (h+scale)/2.)) ) ||
1119 ((shape==RADAR_CIRCLE) &&
1120 ((pow2(x)+pow2(y)) > pow2(w))) ) {
1121
1122 /* Draw little targeted symbol. */
1123 if (p->id == player.p->target && !overlay)
1124 gui_renderRadarOutOfRange( shape, w, h, x, y, &cRadar_tPilot );
1125 return;
1126 }
1127
1128 /* Transform coordinates into the 0,0 -> SCREEN_W, SCREEN_H range. */
1129 if (overlay) {
1130 double ox, oy;
1131 ovr_center( &ox, &oy );
1132 x += ox;
1133 y += oy;
1134 }
1135
1136 if (p->id == player.p->target)
1137 col = &cRadar_hilight;
1138 else
1139 col = gui_getPilotColour(p);
1140
1141 scale = MAX(scale+2.0, 3.5+ssize); /* Compensate for outline. */
1142
1143 if (pilot_isFlag(p, PILOT_HILIGHT)) {
1144 glColour highlighted = cRadar_hilight;
1145 highlighted.a = 0.3;
1146 glUseProgram( shaders.hilight.program );
1147 glUniform1f( shaders.hilight.dt, animation_dt );
1148 gl_renderShader( x, y, scale*2.0, scale*2.0, 0., &shaders.hilight, &highlighted, 1 );
1149 }
1150
1151 glUseProgram(shaders.pilotmarker.program);
1152 gl_renderShader( x, y, scale, scale, p->solid->dir, &shaders.pilotmarker, col, 1 );
1153
1154 /* Draw selection if targeted. */
1155 if (p->id == player.p->target)
1156 gui_blink( x, y, MAX(scale*2.,10.0), &cRadar_hilight, RADAR_BLINK_PILOT, blink_pilot);
1157
1158 /* Draw name. */
1159 if (overlay && pilot_isFlag(p, PILOT_HILIGHT))
1160 gl_printMarkerRaw( &gl_smallFont, x+scale+5., y-gl_smallFont.h/2., col, p->name );
1161}
1162
1172void gui_renderAsteroid( const Asteroid* a, double w, double h, double res, int overlay )
1173{
1174 int i, j, targeted;
1175 double x, y, r, sx, sy;
1176 double px, py;
1177 const glColour *col;
1178
1179 /* Skip invisible asteroids */
1180 if (a->state != ASTEROID_FG)
1181 return;
1182
1183 /* Recover the asteroid and field IDs. */
1184 i = a->id;
1185 j = a->parent;
1186
1187 /* Make sure is in range. */
1188 if (!pilot_inRangeAsteroid( player.p, i, j ))
1189 return;
1190
1191 /* Get position. */
1192 if (overlay) {
1193 x = (a->pos.x / res);
1194 y = (a->pos.y / res);
1195 }
1196 else {
1197 x = ((a->pos.x - player.p->solid->pos.x) / res);
1198 y = ((a->pos.y - player.p->solid->pos.y) / res);
1199 }
1200
1201 /* Get size. */
1202 sx = 1.;
1203 sy = 1.;
1204
1205 /* Transform coordinates into the 0,0 -> SCREEN_W, SCREEN_H range. */
1206 if (overlay) {
1207 double ox, oy;
1208 ovr_center( &ox, &oy );
1209 x += ox;
1210 y += oy;
1211 w *= 2.;
1212 h *= 2.;
1213 }
1214
1215 /* Draw square. */
1216 px = MAX(x-sx, -w);
1217 py = MAX(y-sy, -h);
1218
1219 targeted = ((i==player.p->nav_asteroid) && (j==player.p->nav_anchor));
1220
1221 /* Colour depends if the asteroid is selected. */
1222 if (targeted)
1223 col = &cWhite;
1224 else
1225 col = &cGrey70;
1226
1227 //gl_renderRect( px, py, MIN( 2*sx, w-px ), MIN( 2*sy, h-py ), col );
1228 r = (sx+sy)/2.0+1.5;
1229 glUseProgram(shaders.asteroidmarker.program);
1230 gl_renderShader( px, py, r, r, 0., &shaders.asteroidmarker, col, 1 );
1231
1232 if (targeted)
1233 gui_blink( px, py, MAX(7., 2.0*r), col, RADAR_BLINK_PILOT, blink_pilot );
1234}
1235
1239void gui_renderPlayer( double res, int overlay )
1240{
1241 double x, y, r;
1242
1243 /* Based on gui_renderPilot but with larger fixed size (4x normal ship, but
1244 * the shader is actually quite smaller so it ends up being just a bit
1245 * larger than a capital ship.. */
1246 r = (sqrt(24.) + 1.)/2. * (1. + RADAR_RES_REF / res );
1247 if (overlay) {
1248 double ox, oy;
1249 ovr_center( &ox, &oy );
1250 x = player.p->solid->pos.x / res + ox;
1251 y = player.p->solid->pos.y / res + oy;
1252 r = MAX( 17., r );
1253 } else {
1254 x = y = 0.;
1255 r = MAX( 11., r );
1256 }
1257
1258 glUseProgram(shaders.playermarker.program);
1259 gl_renderShader( x, y, r, r, player.p->solid->dir, &shaders.playermarker, &cRadar_player, 1 );
1260}
1261
1268static const glColour *gui_getSpobColour( int i )
1269{
1270 const glColour *col;
1271 Spob *spob = cur_system->spobs[i];
1272
1273 if (i == player.p->nav_spob)
1274 col = &cRadar_tSpob;
1275 else
1276 col = spob_getColour( spob );
1277
1278 return col;
1279}
1280
1285{
1286 blink_pilot = 0.;
1287 blink_spob = 0.;
1288}
1289
1293static void gui_blink( double cx, double cy, double vr, const glColour *col, double blinkInterval, double blinkVar )
1294{
1295 if (blinkVar > blinkInterval/2.)
1296 return;
1297 glUseProgram(shaders.blinkmarker.program);
1298 gl_renderShader( cx, cy, vr, vr, 0., &shaders.blinkmarker, col, 1 );
1299}
1300
1304static void gui_renderRadarOutOfRange( RadarShape sh, int w, int h, int cx, int cy, const glColour *col )
1305{
1306 double a, x, y, x2, y2;
1307
1308 /* Draw a line like for pilots. */
1309 a = ANGLE(cx,cy);
1310 if (sh == RADAR_CIRCLE) {
1311 x = w * cos(a);
1312 y = w * sin(a);
1313 }
1314 else {
1315 int cxa, cya;
1316 cxa = ABS(cx);
1317 cya = ABS(cy);
1318 /* Determine position. */
1319 if (cy >= cxa) { /* Bottom */
1320 x = w/2. * (cx*1./cy);
1321 y = h/2.;
1322 } else if (cx >= cya) { /* Left */
1323 x = w/2.;
1324 y = h/2. * (cy*1./cx);
1325 } else if (cya >= cxa) { /* Top */
1326 x = -w/2. * (cx*1./cy);
1327 y = -h/2.;
1328 } else { /* Right */
1329 x = -w/2.;
1330 y = -h/2. * (cy*1./cx);
1331 }
1332 }
1333 x2 = x - .15 * w * cos(a);
1334 y2 = y - .15 * w * sin(a);
1335
1336 gl_renderLine( x, y, x2, y2, col );
1337}
1338
1344void gui_renderSpob( int ind, RadarShape shape, double w, double h, double res, double alpha, int overlay )
1345{
1346 GLfloat cx, cy, x, y, r, vr;
1347 glColour col;
1348 Spob *spob;
1349 const SimpleShader *shd;
1350 char buf[STRMAX_SHORT];
1351
1352 /* Make sure is known. */
1353 if (!spob_isKnown( cur_system->spobs[ind] ))
1354 return;
1355
1356 /* Default values. */
1357 spob = cur_system->spobs[ind];
1358 r = spob->radius / res;
1359 vr = overlay ? spob->mo.radius : MAX( r, 7.5 );
1360
1361 if (overlay) {
1362 cx = spob->pos.x / res;
1363 cy = spob->pos.y / res;
1364 }
1365 else {
1366 cx = (spob->pos.x - player.p->solid->pos.x) / res;
1367 cy = (spob->pos.y - player.p->solid->pos.y) / res;
1368 }
1369
1370 /* Check if in range. */
1371 if (shape == RADAR_CIRCLE) {
1372 x = ABS(cx)-r;
1373 y = ABS(cy)-r;
1374 /* Out of range. */
1375 if (x*x + y*y > pow2(w-2*r)) {
1376 if ((player.p->nav_spob == ind) && !overlay)
1377 gui_renderRadarOutOfRange( RADAR_CIRCLE, w, w, cx, cy, &cRadar_tSpob );
1378 return;
1379 }
1380 }
1381 else {
1382 if (shape == RADAR_RECT) {
1383 /* Out of range. */
1384 if ((ABS(cx) - r > w/2.) || (ABS(cy) - r > h/2.)) {
1385 if ((player.p->nav_spob == ind) && !overlay)
1386 gui_renderRadarOutOfRange( RADAR_RECT, w, h, cx, cy, &cRadar_tSpob );
1387 return;
1388 }
1389 }
1390 }
1391
1392 if (overlay) {
1393 double ox, oy;
1394 ovr_center( &ox, &oy );
1395 /* Transform coordinates. */
1396 cx += ox;
1397 cy += oy;
1398 w *= 2.;
1399 h *= 2.;
1400 }
1401
1402 /* Is marked. */
1403 if (spob_isKnown( spob ) && spob_isFlag( spob, SPOB_MARKED )) {
1404 glColour highlighted = cRadar_hilight;
1405 highlighted.a = 0.3;
1406 glUseProgram( shaders.hilight.program );
1407 glUniform1f( shaders.hilight.dt, animation_dt );
1408 gl_renderShader( cx, cy, vr*3.0, vr*3.0, 0., &shaders.hilight, &highlighted, 1 );
1409 }
1410
1411 /* Get the colour. */
1412 col = *gui_getSpobColour(ind);
1413 col.a *= alpha;
1414
1415 /* Do the blink. */
1416 if (ind == player.p->nav_spob)
1417 gui_blink( cx, cy, vr*2., &col, RADAR_BLINK_SPOB, blink_spob);
1418
1419 if (spob->marker != NULL)
1420 shd = spob->marker;
1421 else if (spob_hasService(spob,SPOB_SERVICE_LAND))
1422 shd = &shaders.spobmarker_earth;
1423 else
1424 shd = &shaders.spobmarker_empty;
1425
1426 glUseProgram(shd->program);
1427 gl_renderShader( cx, cy, vr, vr, 0., shd, &col, 1 );
1428
1429 if (overlay) {
1430 snprintf( buf, sizeof(buf), "%s%s", spob_getSymbol(spob), spob_name(spob) );
1431 gl_printMarkerRaw( &gl_smallFont, cx+spob->mo.text_offx, cy+spob->mo.text_offy, &col, buf );
1432 }
1433}
1434
1446void gui_renderJumpPoint( int ind, RadarShape shape, double w, double h, double res, double alpha, int overlay )
1447{
1448 GLfloat cx, cy, x, y, r, vr;
1449 glColour col;
1450 char buf[STRMAX_SHORT];
1451 StarSystem *s;
1452 JumpPoint *jp = &cur_system->jumps[ind];
1453
1454 /* Check if known */
1455 if (!jp_isUsable(jp))
1456 return;
1457
1458 /* Default values. */
1459 r = jumppoint_gfx->sw/2. / res;
1460 vr = overlay ? jp->mo.radius : MAX( r, 5. );
1461 if (overlay) {
1462 cx = jp->pos.x / res;
1463 cy = jp->pos.y / res;
1464 }
1465 else {
1466 cx = (jp->pos.x - player.p->solid->pos.x) / res;
1467 cy = (jp->pos.y - player.p->solid->pos.y) / res;
1468 }
1469
1470 /* Check if in range. */
1471 if (shape == RADAR_RECT) {
1472 /* Out of range. */
1473 if ((ABS(cx) - r > w/2.) || (ABS(cy) - r > h/2.)) {
1474 if ((player.p->nav_hyperspace == ind) && !overlay)
1475 gui_renderRadarOutOfRange( RADAR_RECT, w, h, cx, cy, &cRadar_tSpob );
1476 return;
1477 }
1478 }
1479 else if (shape == RADAR_CIRCLE) {
1480 x = ABS(cx)-r;
1481 y = ABS(cy)-r;
1482 /* Out of range. */
1483 if (x*x + y*y > pow2(w-2*r)) {
1484 if ((player.p->nav_hyperspace == ind) && !overlay)
1485 gui_renderRadarOutOfRange( RADAR_CIRCLE, w, w, cx, cy, &cRadar_tSpob );
1486 return;
1487 }
1488 }
1489
1490 if (overlay) {
1491 double ox, oy;
1492 ovr_center( &ox, &oy );
1493 /* Transform coordinates. */
1494 cx += ox;
1495 cy += oy;
1496 }
1497
1498 /* See if far side is marked. */
1499 s = jp->target;
1500 if (sys_isMarked(s)) {
1501 glColour highlighted = cRadar_hilight;
1502 highlighted.a = 0.3;
1503 glUseProgram( shaders.hilight.program );
1504 glUniform1f( shaders.hilight.dt, animation_dt );
1505 gl_renderShader( cx, cy, vr*3.0, vr*3.0, 0., &shaders.hilight, &highlighted, 1 );
1506 }
1507
1508 if (ind == player.p->nav_hyperspace)
1509 col = cWhite;
1510 else if (jp_isFlag(jp, JP_HIDDEN))
1511 col = cRed;
1512 else
1513 col = cGreen;
1514 col.a *= alpha;
1515
1516 glUseProgram(shaders.jumpmarker.program);
1517 gl_renderShader( cx, cy, vr*1.5, vr*1.5, M_PI-jp->angle, &shaders.jumpmarker, &col, 1 );
1518
1519 /* Blink ontop. */
1520 if (ind == player.p->nav_hyperspace)
1521 gui_blink( cx, cy, vr*3., &col, RADAR_BLINK_SPOB, blink_spob );
1522
1523 /* Render name. */
1524 if (overlay) {
1525 snprintf(
1526 buf, sizeof(buf), "%s%s", jump_getSymbol(jp),
1527 sys_isKnown(jp->target) ? _(jp->target->name) : _("Unknown") );
1528 gl_printMarkerRaw( &gl_smallFont, cx+jp->mo.text_offx, cy+jp->mo.text_offy, &col, buf );
1529 }
1530}
1531
1535void gui_setViewport( double x, double y, double w, double h )
1536{
1537 gui_viewport_x = x;
1538 gui_viewport_y = y;
1539 gui_viewport_w = w;
1540 gui_viewport_h = h;
1541
1542 /* We now set the viewport. */
1545
1546 /* Run border calculations. */
1548}
1549
1554{
1557}
1558
1562static void gui_calcBorders (void)
1563{
1564 double w,h;
1565
1566 /* Precalculations. */
1567 w = SCREEN_W/2.;
1568 h = SCREEN_H/2.;
1569
1570 /*
1571 * Borders.
1572 */
1573 gui_tl = atan2( +h, -w );
1574 if (gui_tl < 0.)
1575 gui_tl += 2*M_PI;
1576 gui_tr = atan2( +h, +w );
1577 if (gui_tr < 0.)
1578 gui_tr += 2*M_PI;
1579 gui_bl = atan2( -h, -w );
1580 if (gui_bl < 0.)
1581 gui_bl += 2*M_PI;
1582 gui_br = atan2( -h, +w );
1583 if (gui_br < 0.)
1584 gui_br += 2*M_PI;
1585}
1586
1592int gui_init (void)
1593{
1594 GLfloat vertex[16];
1595
1596 /*
1597 * radar
1598 */
1600
1601 /*
1602 * messages
1603 */
1604 gui_mesg_x = 20;
1605 gui_mesg_y = 30;
1606 gui_mesg_w = SCREEN_W - 400;
1607 if (mesg_stack == NULL) {
1608 mesg_stack = calloc(mesg_max, sizeof(Mesg));
1609 if (mesg_stack == NULL) {
1610 ERR(_("Out of Memory"));
1611 return -1;
1612 }
1613 }
1614
1615 /*
1616 * VBO.
1617 */
1618
1619 if (gui_radar_select_vbo == NULL) {
1620 vertex[0] = -1.5;
1621 vertex[1] = 1.5;
1622 vertex[2] = -3.3;
1623 vertex[3] = 3.3;
1624 vertex[4] = 1.5;
1625 vertex[5] = 1.5;
1626 vertex[6] = 3.3;
1627 vertex[7] = 3.3;
1628 vertex[8] = 1.5;
1629 vertex[9] = -1.5;
1630 vertex[10] = 3.3;
1631 vertex[11] = -3.3;
1632 vertex[12] = -1.5;
1633 vertex[13] = -1.5;
1634 vertex[14] = -3.3;
1635 vertex[15] = -3.3;
1636 gui_radar_select_vbo = gl_vboCreateStatic( sizeof(GLfloat) * 16, vertex );
1637 }
1638
1639 /*
1640 * OSD
1641 */
1642 osd_setup( 30., SCREEN_H-90., 150., 300. );
1643
1644 /*
1645 * Set viewport.
1646 */
1648
1649 /*
1650 * Icons.
1651 */
1652 gui_ico_hail = gl_newSprite( GUI_GFX_PATH"hail.webp", 5, 2, 0 );
1653
1654 return 0;
1655}
1656
1664static int gui_doFunc( int func_ref, const char *func_name )
1665{
1666 int ret;
1667 if (gui_env == LUA_NOREF)
1668 return -1;
1669
1670 ret = gui_prepFunc( func_ref, func_name );
1671 if (ret)
1672 return ret;
1673 return gui_runFunc( func_name, 0, 0 );
1674}
1675
1683static int gui_prepFunc( int func_ref, const char *func_name )
1684{
1685 (void) func_name;
1686#if DEBUGGING
1687 if (gui_env == LUA_NOREF) {
1688 WARN( _("GUI '%s': Trying to run GUI func '%s' but no GUI is loaded!"), gui_name, func_name );
1689 return -1;
1690 }
1691#endif /* DEBUGGING */
1692
1693 /* Set up function. */
1694 lua_rawgeti( naevL, LUA_REGISTRYINDEX, func_ref );
1695#if DEBUGGING
1696 if (lua_isnil( naevL, -1 )) {
1697 WARN(_("GUI '%s': no function '%s' defined!"), gui_name, func_name );
1698 lua_pop(naevL,1);
1699 return -1;
1700 }
1701#endif /* DEBUGGING */
1702 return 0;
1703}
1704
1712static int gui_runFunc( const char* func, int nargs, int nret )
1713{
1714 /* Run the function. */
1715 int ret = nlua_pcall( gui_env, nargs, nret );
1716 if (ret != 0) { /* error has occurred */
1717 const char *err = (lua_isstring(naevL,-1)) ? lua_tostring(naevL,-1) : NULL;
1718 WARN(_("GUI '%s' Lua -> '%s': %s"), gui_name,
1719 func, (err) ? err : _("unknown error"));
1720 lua_pop(naevL,1);
1721 return ret;
1722 }
1723
1724 return ret;
1725}
1726
1730void gui_reload (void)
1731{
1732 if (gui_env == LUA_NOREF)
1733 return;
1734
1735 gui_load( gui_pick() );
1736}
1737
1741void gui_setCargo (void)
1742{
1743 gui_doFunc( gui_lua_update_cargo, "update_cargo" );
1744}
1745
1749void gui_setNav (void)
1750{
1751 gui_doFunc( gui_lua_update_nav, "update_nav" );
1752}
1753
1757void gui_setTarget (void)
1758{
1759 gui_doFunc( gui_lua_update_target, "update_target" );
1760}
1761
1765void gui_setShip (void)
1766{
1767 gui_doFunc( gui_lua_update_ship, "update_ship" );
1768}
1769
1773void gui_setSystem (void)
1774{
1775 gui_doFunc( gui_lua_update_system, "update_system" );
1776}
1777
1782{
1783 if (player.p != NULL && player.p->nav_spob != -1)
1784 gui_doFunc( gui_lua_update_faction, "update_faction" );
1785}
1786
1787void gui_updateEffects (void)
1788{
1789 if (player.p != NULL)
1790 gui_doFunc( gui_lua_update_effects, "update_effects" );
1791}
1792
1798void gui_setGeneric( const Pilot* pilot )
1799{
1800 if (gui_env == LUA_NOREF)
1801 return;
1802
1803 if (player_isFlag(PLAYER_DESTROYED) || player_isFlag(PLAYER_CREATING) ||
1804 (player.p == NULL) || pilot_isFlag(player.p,PILOT_DEAD))
1805 return;
1806
1807 if ((player.p->target != PLAYER_ID) && (pilot->id == player.p->target))
1808 gui_setTarget();
1809 else if (pilot_isPlayer(pilot)) {
1810 gui_setCargo();
1811 gui_setShip();
1812 }
1813}
1814
1818char* gui_pick (void)
1819{
1820 char* gui;
1821
1822 /* Don't do set a gui if player is dead. This can be triggered through
1823 * naev_resize and can cause an issue if player is dead. */
1824 if ((player.p == NULL) || pilot_isFlag(player.p,PILOT_DEAD))
1825 gui = NULL;
1826 else if (player.gui != NULL)
1827 gui = player.gui;
1828 else
1829 gui = player.p->ship->gui;
1830 return gui;
1831}
1832
1839int gui_load( const char* name )
1840{
1841 char *buf, path[PATH_MAX];
1842 size_t bufsize;
1843
1844 /* Set defaults. */
1845 gui_cleanup();
1846 if (name==NULL)
1847 return 0;
1848 gui_name = strdup(name);
1849
1850 /* Open file. */
1851 snprintf( path, sizeof(path), GUI_PATH"%s.lua", name );
1852 buf = ndata_read( path, &bufsize );
1853 if (buf == NULL) {
1854 WARN(_("Unable to find GUI '%s'."), path );
1855 return -1;
1856 }
1857
1858 /* Clean up. */
1859 nlua_freeEnv(gui_env);
1860 gui_env = LUA_NOREF;
1861
1862 /* Create Lua state. */
1863 gui_env = nlua_newEnv();
1864 if (nlua_dobufenv( gui_env, buf, bufsize, path ) != 0) {
1865 WARN(_("Failed to load GUI Lua: %s\n"
1866 "%s\n"
1867 "Most likely Lua file has improper syntax, please check"),
1868 path, lua_tostring(naevL,-1));
1869 nlua_freeEnv( gui_env );
1870 gui_env = LUA_NOREF;
1871 free(buf);
1872 return -1;
1873 }
1874 free(buf);
1879
1880 /* Load references. */
1881#define LUA_FUNC(funcname) gui_lua_##funcname = nlua_refenvtype( gui_env, #funcname, LUA_TFUNCTION );
1882 LUA_FUNC( create );
1883 LUA_FUNC( render );
1884 LUA_FUNC( render_cooldown );
1885 LUA_FUNC( cooldown_end );
1886 LUA_FUNC( mouse_move );
1887 LUA_FUNC( mouse_click );
1888 LUA_FUNC( update_cargo );
1889 LUA_FUNC( update_nav );
1890 LUA_FUNC( update_target );
1891 LUA_FUNC( update_ship );
1892 LUA_FUNC( update_system );
1893 LUA_FUNC( update_faction );
1894 LUA_FUNC( update_effects );
1895#undef LUA_FUNC
1896
1897 /* Run create function. */
1898 if (gui_doFunc( gui_lua_create, "create" )) {
1899 nlua_freeEnv( gui_env );
1900 gui_env = LUA_NOREF;
1901 }
1902
1903 /* Recreate land window if landed. */
1904 if (landed) {
1905 land_genWindows( 0, 1 );
1907 }
1908
1909 return 0;
1910}
1911
1915void gui_cleanup (void)
1916{
1917 /* Disable mouse voodoo. */
1920
1921 /* Set the viewport. */
1923
1924 /* Set overlay bounds. */
1925 ovr_boundsSet( 0, 0, 0, 0 );
1926
1927 /* Reset FPS. */
1928 fps_setPos( 15., (double)(gl_screen.h-15-gl_defFontMono.h) );
1929
1930 /* Destroy offset. */
1931 gui_xoff = 0.;
1932 gui_yoff = 0.;
1933
1934 /* Destroy lua. */
1935 nlua_freeEnv( gui_env );
1936 gui_env = LUA_NOREF;
1937
1938 /* OMSG */
1939 omsg_position( SCREEN_W/2., SCREEN_H*2./3., SCREEN_W*2./3. );
1940
1941 /* Delete the name. */
1942 free(gui_name);
1943 gui_name = NULL;
1944
1945 /* Clear timers. */
1946 animation_dt = 0.;
1947
1948 /* Lua stuff. */
1949#define LUA_CLEANUP( varname ) if (varname!=LUA_NOREF) luaL_unref(naevL, LUA_REGISTRYINDEX, varname ); varname = LUA_NOREF
1950 LUA_CLEANUP( gui_lua_create );
1951 LUA_CLEANUP( gui_lua_render );
1952 LUA_CLEANUP( gui_lua_render_cooldown );
1953 LUA_CLEANUP( gui_lua_cooldown_end );
1954 LUA_CLEANUP( gui_lua_mouse_move );
1955 LUA_CLEANUP( gui_lua_mouse_click );
1956 LUA_CLEANUP( gui_lua_update_cargo );
1957 LUA_CLEANUP( gui_lua_update_nav );
1958 LUA_CLEANUP( gui_lua_update_target );
1959 LUA_CLEANUP( gui_lua_update_ship );
1960 LUA_CLEANUP( gui_lua_update_system );
1961 LUA_CLEANUP( gui_lua_update_faction );
1962 LUA_CLEANUP( gui_lua_update_effects );
1963#undef LUA_CLEANUP
1964}
1965
1969void gui_free (void)
1970{
1971 gui_cleanup();
1972
1973 for (int i = 0; i < mesg_max; i++)
1974 free( mesg_stack[i].str );
1975 free(mesg_stack);
1976 mesg_stack = NULL;
1977
1978 gl_vboDestroy( gui_radar_select_vbo );
1979 gui_radar_select_vbo = NULL;
1980
1981 osd_exit();
1982
1984 gui_ico_hail = NULL;
1986 gui_target_spob = NULL;
1988 gui_target_pilot = NULL;
1989
1990 omsg_cleanup();
1991}
1992
1998void gui_setRadarResolution( double res )
1999{
2000 gui_radar.res = CLAMP( RADAR_RES_MIN, RADAR_RES_MAX, res );
2001}
2002
2008void gui_setRadarRel( int mod )
2009{
2010 gui_radar.res += mod * RADAR_RES_INTERVAL;
2011 gui_setRadarResolution( gui_radar.res );
2012 player_message( _("#oRadar set to %.0fx.#0"), round(gui_radar.res) );
2013}
2014
2021void gui_getOffset( double *x, double *y )
2022{
2023 *x = gui_xoff;
2024 *y = gui_yoff;
2025}
2026
2031{
2032 return gui_ico_hail;
2033}
2034
2039{
2042}
2043
2048{
2051}
2052
2056static void gui_eventToScreenPos( int* sx, int* sy, int ex, int ey )
2057{
2058 gl_windowToScreenPos( sx, sy, ex, ey );
2059}
2060
2067int gui_radarClickEvent( SDL_Event* event )
2068{
2069 int mxr, myr, in_bounds;
2070 double x, y, cx, cy;
2071
2072 gui_eventToScreenPos( &mxr, &myr, event->button.x, event->button.y );
2073 if (gui_radar.shape == RADAR_RECT) {
2074 cx = gui_radar.x + gui_radar.w / 2.;
2075 cy = gui_radar.y + gui_radar.h / 2.;
2076 in_bounds = (2*ABS( mxr-cx ) <= gui_radar.w && 2*ABS( myr-cy ) <= gui_radar.h);
2077 }
2078 else {
2079 cx = gui_radar.x;
2080 cy = gui_radar.y;
2081 in_bounds = (pow2( mxr-cx ) + pow2( myr-cy ) <= pow2( gui_radar.w ));
2082 }
2083 if (!in_bounds)
2084 return 0;
2085 x = (mxr - cx) * gui_radar.res + player.p->solid->pos.x;
2086 y = (myr - cy) * gui_radar.res + player.p->solid->pos.y;
2087 return input_clickPos( event, x, y, 1., 10. * gui_radar.res, 15. * gui_radar.res );
2088}
2089
2096int gui_borderClickEvent( SDL_Event *event )
2097{
2098 unsigned int pid;
2099 double ang, angp, mouseang;
2100 int mx, my;
2101 int pntid, jpid, astid, fieid;
2102 double x, y;
2103 int autonav = (event->button.button == SDL_BUTTON_RIGHT) ? 1 : 0;
2104 double px = player.p->solid->pos.x;
2105 double py = player.p->solid->pos.y;
2106 gui_eventToScreenPos( &mx, &my, event->button.x, event->button.y );
2107 mx -= gui_viewport_x;
2108 my -= gui_viewport_y;
2109
2110 /* No intersection with border. */
2111 if (!((mx <= 15 || my <= 15 ) || (my >= gl_screen.h-15 || mx >= gl_screen.w-15)))
2112 return 0;
2113
2114 /* Border targeting is handled as a special case, as it uses angles,
2115 * not coordinates. */
2116 x = (mx - (gl_screen.w / 2.)) + px;
2117 y = (my - (gl_screen.h / 2.)) + py;
2118 mouseang = atan2(py - y, px - x);
2119 angp = pilot_getNearestAng( player.p, &pid, mouseang, 1 );
2120 ang = system_getClosestAng( cur_system, &pntid, &jpid, &astid, &fieid, x, y, mouseang );
2121
2122 if ((ABS(angle_diff(mouseang, angp)) > M_PI / 64) ||
2123 ABS(angle_diff(mouseang, ang)) < ABS(angle_diff(mouseang, angp)))
2124 pid = PLAYER_ID; /* Pilot angle is too great, or spob/jump is closer. */
2125 if (ABS(angle_diff(mouseang, ang)) > M_PI / 64 )
2126 jpid = pntid = astid = fieid = -1; /* Spob angle difference is too great. */
2127
2128 if (pid != PLAYER_ID) {
2129 if (input_clickedPilot(pid, autonav))
2130 return 1;
2131 }
2132 else if (pntid >= 0) { /* Spob is closest. */
2133 if (input_clickedSpob(pntid, autonav))
2134 return 1;
2135 }
2136 else if (jpid >= 0) { /* Jump point is closest. */
2137 if (input_clickedJump(jpid, autonav))
2138 return 1;
2139 }
2140 else if (astid >= 0) { /* Asteroid is closest. */
2141 if (input_clickedAsteroid(fieid, astid))
2142 return 1;
2143 }
2144
2145 return 0;
2146}
2147
2151int gui_handleEvent( SDL_Event *evt )
2152{
2153 int ret;
2154 int x, y;
2155
2156 if (player.p == NULL)
2157 return 0;
2158 if ((evt->type == SDL_MOUSEBUTTONDOWN) &&
2159 (pilot_isFlag(player.p,PILOT_HYP_PREP) ||
2160 pilot_isFlag(player.p,PILOT_HYP_BEGIN) ||
2161 pilot_isFlag(player.p,PILOT_HYPERSPACE)))
2162 return 0;
2163
2164 ret = 0;
2165 switch (evt->type) {
2166 /* Mouse motion. */
2167 case SDL_MOUSEMOTION:
2168 if (!gui_L_mmove)
2169 break;
2170 gui_prepFunc( gui_lua_mouse_move, "mouse_move" );
2171 gui_eventToScreenPos( &x, &y, evt->motion.x, evt->motion.y );
2172 lua_pushnumber( naevL, x );
2173 lua_pushnumber( naevL, y );
2174 gui_runFunc( "mouse_move", 2, 0 );
2175 break;
2176
2177 /* Mouse click. */
2178 case SDL_MOUSEBUTTONDOWN:
2179 case SDL_MOUSEBUTTONUP:
2180 if (!gui_L_mclick)
2181 break;
2182 gui_prepFunc( gui_lua_mouse_click, "mouse_click" );
2183 lua_pushnumber( naevL, evt->button.button+1 );
2184 gui_eventToScreenPos( &x, &y, evt->button.x, evt->button.y );
2185 lua_pushnumber( naevL, x );
2186 lua_pushnumber( naevL, y );
2187 lua_pushboolean( naevL, (evt->type==SDL_MOUSEBUTTONDOWN) );
2188 gui_runFunc( "mouse_click", 4, 1 );
2189 ret = lua_toboolean( naevL, -1 );
2190 lua_pop( naevL, 1 );
2191 break;
2192
2193 /* Not interested in the rest. */
2194 default:
2195 break;
2196 }
2197 return ret;
2198}
2199
2203void gui_mouseClickEnable( int enable )
2204{
2205 gui_L_mclick = enable;
2206}
2207
2211void gui_mouseMoveEnable( int enable )
2212{
2213 gui_L_mmove = enable;
2214}
static ALWAYS_INLINE int array_size(const void *array)
Returns number of elements in the array.
Definition: array.h:168
double cam_getZoom(void)
Gets the camera zoom.
Definition: camera.c:97
int gl_printHeightRaw(const glFont *ft_font, const int width, const char *text)
Gets the height of a non-formatted string.
Definition: font.c:1026
void gl_printRestoreInit(glFontRestore *restore)
Initializes a restore structure.
Definition: font.c:395
int gl_printLineIteratorNext(glPrintLineIterator *iter)
Updates iter with the next line's information.
Definition: font.c:525
glFont gl_smallFont
Definition: font.c:154
void gl_printRestore(const glFontRestore *restore)
Restores last colour from a restore structure.
Definition: font.c:404
void gl_printLineIteratorInit(glPrintLineIterator *iter, const glFont *ft_font, const char *text, int width)
Initialize an iterator object for breaking text into lines.
Definition: font.c:505
int gl_printMaxRaw(const glFont *ft_font, const int max, double x, double y, const glColour *c, double outlineR, const char *text)
Behaves like gl_printRaw but stops displaying text after a certain distance.
Definition: font.c:720
glFont gl_defFontMono
Definition: font.c:155
void gl_printStoreMax(glFontRestore *restore, const char *text, int max)
Stores the colour information from a piece of text limited to max characters.
Definition: font.c:418
void gl_printMarkerRaw(const glFont *ft_font, double x, double y, const glColour *c, const char *text)
Wrapper for gl_printRaw for map overlay markers.
Definition: font.c:672
static void gui_borderIntersection(double *cx, double *cy, double rx, double ry, double hw, double hh)
Gets the intersection with the border.
Definition: gui.c:487
#define RADAR_BLINK_PILOT
Definition: gui.c:66
static const int mesg_max
Definition: gui.c:122
static int gui_mesg_w
Definition: gui.c:137
static void gui_renderSpobTarget(void)
Sets up rendering of spob and jump point targeting reticles.
Definition: gui.c:350
void gui_renderSpob(int ind, RadarShape shape, double w, double h, double res, double alpha, int overlay)
Draws the spobs in the minimap.
Definition: gui.c:1344
int gui_radarClickEvent(SDL_Event *event)
Handles a click at a position in the current system.
Definition: gui.c:2067
void gui_clearMessages(void)
Clears the GUI messages.
Definition: gui.c:973
int gui_init(void)
Initializes the GUI system.
Definition: gui.c:1592
static int gui_L_mmove
Definition: gui.c:87
static double gui_yoff
Definition: gui.c:119
static glTexture * gui_ico_hail
Definition: gui.c:148
int gui_radarInit(int circle, int w, int h)
Initializes the radar.
Definition: gui.c:863
void gui_setTarget(void)
Player just changed their pilot target.
Definition: gui.c:1757
void gui_renderPlayer(double res, int overlay)
Renders the player cross on the radar or whatever.
Definition: gui.c:1239
int gui_handleEvent(SDL_Event *evt)
Handles GUI events.
Definition: gui.c:2151
static void gui_renderBorder(double dt)
Renders the ships/spobs in the border.
Definition: gui.c:529
void gui_messageScrollDown(int lines)
Scrolls up the message box.
Definition: gui.c:253
static int gui_prepFunc(int func_ref, const char *func_name)
Prepares to run a function.
Definition: gui.c:1683
static Mesg * mesg_stack
Definition: gui.c:136
glTexture * gui_hailIcon(void)
Gets the hail icon texture.
Definition: gui.c:2030
void gui_setDefaults(void)
Definition: gui.c:199
int gui_borderClickEvent(SDL_Event *event)
Handles clicks on the GUI border icons.
Definition: gui.c:2096
unsigned int land_wid
Definition: land.c:78
void gui_setSystem(void)
Player just changed their system.
Definition: gui.c:1773
static int gui_mesg_x
Definition: gui.c:138
void gui_radarRender(double x, double y)
Renders the GUI radar.
Definition: gui.c:878
void gui_setRadarRel(int mod)
Modifies the radar resolution.
Definition: gui.c:2008
static void gui_eventToScreenPos(int *sx, int *sy, int ex, int ey)
Translates a mouse position from an SDL_Event to GUI coordinates.
Definition: gui.c:2056
static void gui_renderRadarOutOfRange(RadarShape sh, int w, int h, int cx, int cy, const glColour *col)
Renders an out of range marker for the spob.
Definition: gui.c:1304
void gui_renderAsteroid(const Asteroid *a, double w, double h, double res, int overlay)
Renders an asteroid in the GUI radar.
Definition: gui.c:1172
#define RADAR_RES_INTERVAL
Definition: gui.c:114
static int can_jump
Definition: gui.c:714
static double gui_br
Definition: gui.c:143
static double gui_tl
Definition: gui.c:144
void gui_mouseMoveEnable(int enable)
Enables the mouse movement callback.
Definition: gui.c:2211
void gui_messageScrollUp(int lines)
Scrolls up the message box.
Definition: gui.c:224
static int mesg_viewpoint
Definition: gui.c:124
void gui_mouseClickEnable(int enable)
Enables the mouse click callback.
Definition: gui.c:2203
static const double mesg_timeout
Definition: gui.c:125
static char * gui_name
Definition: gui.c:78
void gui_updateFaction(void)
Player's relationship with a faction was modified.
Definition: gui.c:1781
static void gui_renderMessages(double dt)
Renders the player's messages on screen.
Definition: gui.c:985
int gui_load(const char *name)
Attempts to load the actual GUI.
Definition: gui.c:1839
char * gui_pick(void)
Determines which GUI should be used.
Definition: gui.c:1818
void gui_getOffset(double *x, double *y)
Gets the GUI offset.
Definition: gui.c:2021
void weapon_minimap(const double res, const double w, const double h, const RadarShape shape, double alpha)
Draws the minimap weapons (used in player.c).
Definition: weapon.c:172
static const glColour * gui_getSpobColour(int i)
Gets the colour of a spob.
Definition: gui.c:1268
static double gui_xoff
Definition: gui.c:118
void gui_targetPilotGFX(glTexture *gfx)
Sets the pilot target GFX.
Definition: gui.c:2047
void gui_setShip(void)
Player just upgraded their ship or modified it.
Definition: gui.c:1765
#define RADAR_RES_MAX
Definition: gui.c:111
void gui_free(void)
Frees the gui stuff.
Definition: gui.c:1969
void gui_messageInit(int width, int x, int y)
Initializes the message system.
Definition: gui.c:212
void gui_clearViewport(void)
Resets the viewport.
Definition: gui.c:1553
void gui_radarGetRes(double *res)
Outputs the radar's resolution.
Definition: gui.c:965
void gui_reload(void)
Reloads the GUI.
Definition: gui.c:1730
static double gui_tr
Definition: gui.c:142
void gui_forceBlink(void)
Force sets the spob and pilot radar blink.
Definition: gui.c:1284
int gui_onScreenPilot(double *rx, double *ry, const Pilot *pilot)
Takes a pilot and returns whether it's on screen, plus its relative position.
Definition: gui.c:619
static double blink_pilot
Definition: gui.c:70
static int gui_doFunc(int func_ref, const char *func_name)
Runs a GUI Lua function.
Definition: gui.c:1664
static void gui_renderPilotTarget(void)
Renders the players pilot target.
Definition: gui.c:434
void gui_cooldownEnd(void)
Notifies GUI scripts that the player broke out of cooldown.
Definition: gui.c:851
static int gui_mesg_y
Definition: gui.c:139
static const glColour * gui_getPilotColour(const Pilot *p)
Gets a pilot's colour, with a special colour for targets.
Definition: gui.c:1072
void gui_renderJumpPoint(int ind, RadarShape shape, double w, double h, double res, double alpha, int overlay)
Renders a jump point on the minimap.
Definition: gui.c:1446
int gui_onScreenSpob(double *rx, double *ry, const JumpPoint *jp, const Spob *pnt)
Takes a spob or jump point and returns whether it's on screen, plus its relative position.
Definition: gui.c:656
void gui_cleanup(void)
Cleans up the GUI.
Definition: gui.c:1915
void gui_renderPilot(const Pilot *p, RadarShape shape, double w, double h, double res, int overlay)
Renders a pilot in the GUI radar.
Definition: gui.c:1094
static void gui_calcBorders(void)
Calculates and sets the GUI borders.
Definition: gui.c:1562
static int mesg_pointer
Definition: gui.c:123
static double gui_bl
Definition: gui.c:145
static double gui_viewport_y
Definition: gui.c:93
static int gui_runFunc(const char *func, int nargs, int nret)
Runs a function.
Definition: gui.c:1712
#define RADAR_RES_MIN
Definition: gui.c:113
void player_messageRaw(const char *str)
Adds a mesg to the queue to be displayed on screen.
Definition: gui.c:293
#define RADAR_BLINK_SPOB
Definition: gui.c:67
static int gui_getMessage
Definition: gui.c:77
static double blink_spob
Definition: gui.c:71
static void gui_blink(double cx, double cy, double vr, const glColour *col, double blinkInterval, double blinkVar)
Renders the spob blink around a position on the minimap.
Definition: gui.c:1293
void gui_setNav(void)
Player just changed their nav computer target.
Definition: gui.c:1749
void gui_renderReticles(double dt)
Renders the gui targeting reticles.
Definition: gui.c:698
void gui_render(double dt)
Renders the player's GUI.
Definition: gui.c:720
#define RADAR_RES_REF
Definition: gui.c:112
void gui_setGeneric(const Pilot *pilot)
Calls trigger functions depending on who the pilot is.
Definition: gui.c:1798
static glTexture * gui_target_spob
Definition: gui.c:149
void gui_targetSpobGFX(glTexture *gfx)
Sets the spob target GFX.
Definition: gui.c:2038
static double gui_viewport_w
Definition: gui.c:94
void gui_setViewport(double x, double y, double w, double h)
Sets the viewport.
Definition: gui.c:1535
static void gui_renderTargetReticles(const SimpleShader *shd, double x, double y, double radius, double angle, const glColour *c)
Renders spob and jump point targeting reticles.
Definition: gui.c:415
static nlua_env gui_env
Definition: gui.c:85
void player_message(const char *fmt,...)
Adds a mesg to the queue to be displayed on screen.
Definition: gui.c:330
static int gui_L_mclick
Definition: gui.c:86
void gui_setRadarResolution(double res)
Sets the radar resolution.
Definition: gui.c:1998
static double gui_viewport_x
Definition: gui.c:92
static double animation_dt
Definition: gui.c:72
void gui_setCargo(void)
Player just changed their cargo.
Definition: gui.c:1741
static double gui_viewport_h
Definition: gui.c:95
void player_messageToggle(int enable)
Toggles if player should receive messages.
Definition: gui.c:283
static glTexture * gui_target_pilot
Definition: gui.c:150
int input_clickedPilot(unsigned int pilot, int autonav)
Performs an appropriate action when a pilot is clicked.
Definition: input.c:1420
int input_clickPos(SDL_Event *event, double x, double y, double zoom, double minpr, double minr)
Handles a click at a position in the current system.
Definition: input.c:1237
int input_clickedAsteroid(int field, int asteroid)
Performs an appropriate action when an asteroid is clicked.
Definition: input.c:1404
int input_clickedSpob(int spob, int autonav)
Performs an appropriate action when a spob is clicked.
Definition: input.c:1361
int input_clickedJump(int jump, int autonav)
Performs an appropriate action when a jump point is clicked.
Definition: input.c:1326
void land_genWindows(int load, int changetab)
Recreates the land windows.
Definition: land.c:1032
int landed
Definition: land.c:74
void mat4_translate(mat4 *m, double x, double y, double z)
Translates a homogenous transformation matrix.
Definition: mat4.c:99
void mat4_scale(mat4 *m, double x, double y, double z)
Scales a homogeneous transformation matrix.
Definition: mat4.c:82
Handles the important game menus.
#define MENU_MAIN
Definition: menu.h:9
#define menu_isOpen(f)
Definition: menu.h:16
void fps_setPos(double x, double y)
Sets the position to display the FPS.
Definition: naev.c:904
Header file with generic functions and naev-specifics.
#define CLAMP(a, b, x)
Definition: naev.h:41
#define ABS(x)
Definition: naev.h:36
#define pow2(x)
Definition: naev.h:46
#define MAX(x, y)
Definition: naev.h:39
#define PATH_MAX
Definition: naev.h:50
void * ndata_read(const char *path, size_t *filesize)
Reads a file from the ndata (will be NUL terminated).
Definition: ndata.c:154
static char buf[NEWS_MAX_LENGTH]
Definition: news.c:45
int nlua_loadStandard(nlua_env env)
Loads the standard Naev Lua API.
Definition: nlua.c:760
int nlua_loadGFX(nlua_env env)
Loads the graphics library.
Definition: nlua_gfx.c:97
int nlua_loadGUI(nlua_env env)
Loads the GUI library.
Definition: nlua_gui.c:60
int nlua_loadTk(nlua_env env)
Loads the Toolkit Lua library.
Definition: nlua_tk.c:90
int vasprintf(char **strp, const char *fmt, va_list ap)
Like vsprintf(), but it allocates a large-enough string and returns the pointer in the first argument...
Definition: nstring.c:132
char * strndup(const char *s, size_t n)
Return a pointer to a new string, which is a duplicate of the string s (or, if necessary,...
Definition: nstring.c:94
void gl_setDefViewport(int x, int y, int w, int h)
Sets the default viewport.
Definition: opengl.c:597
void gl_defViewport(void)
Resets viewport to default.
Definition: opengl.c:608
void gl_viewport(int x, int y, int w, int h)
Sets the opengl viewport.
Definition: opengl.c:569
void gl_windowToScreenPos(int *sx, int *sy, int wx, int wy)
Translates the window position to screen position.
Definition: opengl.c:616
glInfo gl_screen
Definition: opengl.c:51
void gl_renderShader(double x, double y, double w, double h, double r, const SimpleShader *shd, const glColour *c, int center)
Renders a simple shader.
void gl_renderRect(double x, double y, double w, double h, const glColour *c)
Renders a rectangle.
Definition: opengl_render.c:90
void gl_renderLine(double x1, double y1, double x2, double y2, const glColour *c)
Draws a line.
void gl_gameToScreenCoords(double *nx, double *ny, double bx, double by)
Converts in-game coordinates to screen coordinates.
void gl_renderTriangleEmpty(double x, double y, double a, double s, double length, const glColour *c)
Renders a triangle at a given position.
void gl_unclipRect(void)
Clears the 2d clipping planes.
void gl_renderRectEmpty(double x, double y, double w, double h, const glColour *c)
Renders a rectangle.
void gl_clipRect(int x, int y, int w, int h)
Sets up 2d clipping planes around a rectangle.
void gl_renderCircle(double cx, double cy, double r, const glColour *c, int filled)
Draws a circle.
glTexture * gl_dupTexture(const glTexture *texture)
Duplicates a texture.
Definition: opengl_tex.c:809
glTexture * gl_newSprite(const char *path, const int sx, const int sy, const unsigned int flags)
Loads the texture immediately, but also sets it as a sprite.
Definition: opengl_tex.c:684
void gl_freeTexture(glTexture *texture)
Frees a texture.
Definition: opengl_tex.c:755
void gl_vboDestroy(gl_vbo *vbo)
Destroys a VBO.
Definition: opengl_vbo.c:248
void gl_vboActivateAttribOffset(gl_vbo *vbo, GLuint index, GLuint offset, GLint size, GLenum type, GLsizei stride)
Activates a VBO's offset.
Definition: opengl_vbo.c:228
gl_vbo * gl_vboCreateStatic(GLsizei size, const void *data)
Creates a stream vbo.
Definition: opengl_vbo.c:181
double dt_mod
Definition: pause.c:23
int pilot_isHostile(const Pilot *p)
Checks to see if pilot is hostile to the player.
Definition: pilot.c:651
int pilot_validTarget(const Pilot *p, const Pilot *target)
Checks to see if a pilot is a valid target for another pilot.
Definition: pilot.c:226
int pilot_isFriendly(const Pilot *p)
Checks to see if pilot is friendly to the player.
Definition: pilot.c:681
Pilot * pilot_get(unsigned int id)
Pulls a pilot out of the pilot_stack based on ID.
Definition: pilot.c:589
const glColour * pilot_getColour(const Pilot *p)
Gets a pilot's colour.
Definition: pilot.c:1327
static Pilot ** pilot_stack
Definition: pilot.c:57
Pilot *const * pilot_getAll(void)
Gets the pilot stack.
Definition: pilot.c:83
double pilot_getNearestAng(const Pilot *p, unsigned int *tp, double ang, int disabled)
Get the pilot closest to an angle extending from another pilot.
Definition: pilot.c:536
void pilot_setTarget(Pilot *p, unsigned int id)
Sets the target of the pilot.
Definition: pilot.c:1351
int pilot_inRangePilot(const Pilot *p, const Pilot *target, double *dist2)
Check to see if a pilot is in sensor range of another.
Definition: pilot_ew.c:242
int pilot_inRangeSpob(const Pilot *p, int target)
Check to see if a spob is in sensor range of the pilot.
Definition: pilot_ew.c:277
int pilot_inRangeAsteroid(const Pilot *p, int ast, int fie)
Check to see if an asteroid is in sensor range of the pilot.
Definition: pilot_ew.c:307
int snd_jump
Definition: player.c:97
void player_targetSpobSet(int id)
Sets the player's target spob.
Definition: player.c:1453
Player_t player
Definition: player.c:73
void player_soundPlayGUI(int sound, int once)
Plays a GUI sound (unaffected by time accel).
Definition: player.c:847
static const double c[]
Definition: rng.c:264
static const double a[]
Definition: rng.c:247
int ship_size(const Ship *s)
Gets the size of the ship.
Definition: ship.c:302
double system_getClosestAng(const StarSystem *sys, int *pnt, int *jp, int *ast, int *fie, double x, double y, double ang)
Gets the feature nearest to directly ahead of a position in the system.
Definition: space.c:734
int space_canHyperspace(const Pilot *p)
Checks to make sure if pilot is far enough away to hyperspace.
Definition: space.c:437
const glColour * spob_getColour(const Spob *p)
Gets the spob colour.
Definition: space.c:1875
const char * jump_getSymbol(const JumpPoint *jp)
Gets the jump point symbol.
Definition: space.c:1212
const char * spob_getSymbol(const Spob *p)
Gets the spob symbol.
Definition: space.c:1853
StarSystem * cur_system
Definition: space.c:105
const char * spob_name(const Spob *p)
Gets the translated name of a spob.
Definition: space.c:1705
glTexture * jumppoint_gfx
Definition: space.c:106
void spfx_cinematic(void)
Sets the cinematic mode.
Definition: spfx.c:991
Represents an asteroid field anchor.
Definition: asteroid.h:100
Asteroid * asteroids
Definition: asteroid.h:105
Represents a single asteroid.
Definition: asteroid.h:76
const glTexture * gfx
Definition: asteroid.h:82
vec2 pos
Definition: asteroid.h:86
float text_offx
Definition: space.h:58
float radius
Definition: space.h:57
float text_offy
Definition: space.h:59
On screen player message.
Definition: gui.c:131
glFontRestore restore
Definition: gui.c:134
char * str
Definition: gui.c:132
double t
Definition: gui.c:133
The representation of an in-game pilot.
Definition: pilot.h:210
Solid * solid
Definition: pilot.h:220
unsigned int id
Definition: pilot.h:211
int nav_hyperspace
Definition: pilot.h:337
const Ship * ship
Definition: pilot.h:219
int nav_anchor
Definition: pilot.h:338
double ptimer
Definition: pilot.h:356
double cdelay
Definition: pilot.h:280
double ctimer
Definition: pilot.h:281
unsigned int target
Definition: pilot.h:334
int nav_spob
Definition: pilot.h:336
int nav_asteroid
Definition: pilot.h:339
double jump_brightness
Definition: conf.h:101
int always_radar
Definition: conf.h:127
int mesg_visible
Definition: conf.h:124
Pilot * p
Definition: player.h:101
double radar_res
Definition: player.h:125
char * gui
Definition: player.h:124
Represents the player's radar.
Definition: gui.c:102
double y
Definition: gui.c:106
double res
Definition: gui.c:108
double w
Definition: gui.c:103
double h
Definition: gui.c:104
RadarShape shape
Definition: gui.c:107
double x
Definition: gui.c:105
glTexture * gfx_space
Definition: ship.h:137
char * gui
Definition: ship.h:149
vec2 vel
Definition: physics.h:21
double dir
Definition: physics.h:19
vec2 pos
Definition: physics.h:22
Represents a Space Object (SPOB), including and not limited to planets, stations, wormholes,...
Definition: space.h:88
glTexture * gfx_space
Definition: space.h:119
double radius
Definition: space.h:94
const SimpleShader * marker
Definition: space.h:95
vec2 pos
Definition: space.h:93
MapOverlayPos mo
Definition: space.h:128
Evil hack to allow restoring, yes it makes me cry myself to sleep.
Definition: font.h:27
int h
Definition: font.h:18
int w
Definition: opengl.h:40
int rh
Definition: opengl.h:47
int rw
Definition: opengl.h:46
int h
Definition: opengl.h:41
int nw
Definition: opengl.h:43
int nh
Definition: opengl.h:44
The state of a line iteration. This matches the process of rendering text into an on-screen box: An e...
Definition: font.h:40
size_t l_end
Definition: font.h:45
Abstraction for rendering sprite sheets.
Definition: opengl_tex.h:34
double sw
Definition: opengl_tex.h:44
double sh
Definition: opengl_tex.h:45
Definition: mat4.h:10
double y
Definition: vec2.h:34
double x
Definition: vec2.h:33
void window_lower(unsigned int wid)
Lowers a window (causes all other windows to appear above it).
Definition: toolkit.c:2548