2021-09-24 10:15:43 -04:00
# include "engine.h"
2023-10-02 15:55:45 -04:00
# include <iostream>
# include <chrono>
# include <thread>
# include <queue>
// Define a structure to represent notifications
struct Notification {
std : : string message ;
float displayStartTime = 0.0f ;
} ;
// Use a queue to manage notifications
//std::queue<Notification> notificationQueue;
// Use a vector to manage notifications
std : : vector < Notification > notifications ;
2023-09-15 11:24:43 -04:00
Engine : : Engine ( ) { }
2021-09-24 10:15:43 -04:00
2023-09-15 11:24:43 -04:00
Engine : : ~ Engine ( ) {
2021-12-06 21:41:50 -05:00
m_world . CleanUpWorld ( m_renderCount , true ) ;
2021-12-07 18:59:50 -05:00
for ( int x = 0 ; x < WORLD_SIZE_X ; + + x )
2021-12-06 21:41:50 -05:00
for ( int y = 0 ; y < WORLD_SIZE_Y ; + + y )
if ( m_world . GetChunks ( ) . Get ( x , y ) )
m_world . GetChunks ( ) . Get ( x , y ) - > ~ Chunk ( ) ;
}
2021-09-24 10:15:43 -04:00
2023-10-23 16:57:19 -04:00
void Engine : : DrawSplachScreen ( )
{
glDisable ( GL_LIGHTING ) ;
glDisable ( GL_DEPTH_TEST ) ;
glDisable ( GL_STENCIL_TEST ) ;
// Définir la matrice de projection en mode orthographique
glMatrixMode ( GL_PROJECTION ) ;
glPushMatrix ( ) ;
glLoadIdentity ( ) ;
glOrtho ( - Width ( ) / 2 , Width ( ) / 2 , - Height ( ) / 2 , Height ( ) / 2 , - 1 , 1 ) ;
// Définir la matrice de modèle-vue
glMatrixMode ( GL_MODELVIEW ) ;
glPushMatrix ( ) ;
glLoadIdentity ( ) ;
// L'image sera centrée autour de l'origine (0, 0, 0)
int imageWidth = Width ( ) ; // Remplacez par la largeur de votre image
int imageHeight = Height ( ) ; // Remplacez par la hauteur de votre image
// Texture
SplachScreenTexture . Bind ( ) ;
// Dessiner un quadrilatère centré
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( - imageWidth / 2 , - imageHeight / 2 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( imageWidth / 2 , - imageHeight / 2 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( imageWidth / 2 , imageHeight / 2 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( - imageWidth / 2 , imageHeight / 2 ) ;
glEnd ( ) ;
// Activer la transparence
glBlendFunc ( GL_SRC_ALPHA , GL_ONE_MINUS_SRC_ALPHA ) ;
glBlendEquation ( GL_FUNC_ADD ) ;
glEnable ( GL_BLEND ) ;
// Restaurer les matrices précédentes
glMatrixMode ( GL_PROJECTION ) ;
glPopMatrix ( ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPopMatrix ( ) ;
}
2023-10-02 17:09:03 -04:00
void Engine : : DrawMenu ( )
{
static const int sTitle = 400 ;
static const int sButton = 225 ;
glDisable ( GL_LIGHTING ) ;
2023-10-16 17:36:04 -04:00
2023-10-02 17:09:03 -04:00
glDisable ( GL_DEPTH_TEST ) ;
2023-10-16 17:36:04 -04:00
glDisable ( GL_STENCIL_TEST ) ;
2023-10-02 17:09:03 -04:00
glMatrixMode ( GL_PROJECTION ) ;
glPushMatrix ( ) ;
glLoadIdentity ( ) ;
glOrtho ( 0 , Width ( ) , 0 , Height ( ) , - 1 , 1 ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPushMatrix ( ) ;
MenuBGTexture . Bind ( ) ;
glLoadIdentity ( ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 0 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( 800 , 0 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( 800 , 600 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 600 ) ;
glEnd ( ) ;
2023-10-16 17:36:04 -04:00
glBlendFunc ( GL_SRC_ALPHA , GL_ONE_MINUS_SRC_ALPHA ) ;
glBlendEquation ( GL_FUNC_ADD ) ;
glEnable ( GL_BLEND ) ;
2023-10-02 17:09:03 -04:00
if ( m_gamestate ! = GameState : : OPTIONS )
{
MenuTitleTexture . Bind ( ) ;
glTranslated ( 200 , 300 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 200 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sTitle , 200 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sTitle , 300 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 300 ) ;
glEnd ( ) ;
MenuStartTexture . Bind ( ) ;
glTranslated ( 80 , - 225 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 100 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 100 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ;
/*MenuResumeTexture.Bind();
glTranslated ( 0 , - 100 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 125 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 125 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ; */
/*MenuOptionsTexture.Bind();
glTranslated ( 0 , - 100 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 125 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 125 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ; */
MenuQuitTexture . Bind ( ) ;
glTranslated ( 0 , - 100 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 100 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 100 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ;
}
else
{
/*MenuOptionsTexture.Bind();
glTranslated ( 200 , 0 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 0 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sTitle , 0 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sTitle , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ;
WireFrameTexture . Bind ( ) ;
glTranslated ( 0 , 300 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 125 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 125 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ;
OnOffBtnTexture . Bind ( ) ;
glTranslated ( 200 , 0 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 125 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 125 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ;
glTranslated ( - 400 , - 300 , 0 ) ;
MusicTexture . Bind ( ) ;
glTranslated ( 200 , 200 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 125 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 125 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ;
OnOffBtnTexture . Bind ( ) ;
glTranslated ( 200 , 0 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 125 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 125 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ;
BackBtnTexture . Bind ( ) ;
glTranslated ( - 375 , 175 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 140 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( sButton , 140 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( sButton , 200 ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , 200 ) ;
glEnd ( ) ; */
}
2023-10-16 17:36:04 -04:00
//glEnable(GL_LIGHTING);
2023-10-02 17:09:03 -04:00
glDisable ( GL_BLEND ) ;
glEnable ( GL_DEPTH_TEST ) ;
glMatrixMode ( GL_PROJECTION ) ;
glPopMatrix ( ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPopMatrix ( ) ;
ShowCursor ( ) ;
}
2021-11-30 19:55:11 -05:00
void Engine : : Init ( ) {
2023-10-23 16:57:19 -04:00
2021-10-11 11:37:58 -04:00
GLenum glewErr = glewInit ( ) ;
2021-10-12 15:58:54 -04:00
if ( glewErr ! = GLEW_OK ) {
2021-10-11 11:37:58 -04:00
std : : cerr < < " ERREUR GLEW : " < < glewGetErrorString ( glewErr ) < < std : : endl ;
abort ( ) ;
}
2023-09-30 14:46:54 -04:00
glDisable ( GL_FRAMEBUFFER_SRGB ) ;
2023-10-25 02:06:29 -04:00
glEnable ( GL_DEPTH_TEST ) ;
2023-09-30 14:46:54 -04:00
glEnable ( GL_STENCIL_TEST ) ;
glEnable ( GL_POINT_SMOOTH ) ;
glEnable ( GL_BLEND ) ;
2023-09-15 20:28:20 -04:00
glEnable ( GL_CULL_FACE ) ;
2021-09-27 10:20:58 -04:00
glEnable ( GL_TEXTURE_2D ) ;
2023-09-15 11:24:43 -04:00
2021-09-27 10:20:58 -04:00
glMatrixMode ( GL_PROJECTION ) ;
glLoadIdentity ( ) ;
2021-10-06 21:32:12 -04:00
2023-09-15 11:24:43 -04:00
gluPerspective ( 45.0f , ( float ) Width ( ) / ( float ) Height ( ) , 0.1f , VIEW_DISTANCE ) ;
2023-09-15 20:28:20 -04:00
glShadeModel ( GL_SMOOTH ) ;
2021-11-30 19:55:11 -05:00
2023-09-30 14:46:54 -04:00
glHint ( GL_PERSPECTIVE_CORRECTION_HINT , GL_NICEST ) ;
glDisable ( GL_BLEND ) ;
glBlendFunc ( GL_SRC_ALPHA , GL_ONE_MINUS_SRC_ALPHA ) ;
glBlendEquation ( GL_FUNC_SUBTRACT ) ;
2023-10-16 17:36:04 -04:00
2023-09-15 20:28:20 -04:00
//
2021-10-12 15:58:54 -04:00
// Objet de skybox avec sa propre texture et son propre shader!
2021-12-06 09:45:51 -05:00
m_skybox . Init ( 0.2f ) ;
2021-10-04 12:29:10 -04:00
2021-10-19 10:27:59 -04:00
// Objet de musique!
2023-09-27 11:24:41 -04:00
//m_audio.ToggleMusicState();
2021-11-15 20:58:13 -05:00
2021-12-07 18:59:50 -05:00
// Array pour les balles.
2023-10-16 12:02:37 -04:00
for ( int x = 0 ; x < MAX_BULLETS ; + + x ) {
2021-12-07 18:59:50 -05:00
m_bullets [ x ] = nullptr ;
2023-10-16 12:02:37 -04:00
m_whoosh [ x ] = nullptr ; // = m_audio.m_engine.m_audio.m_engine->addSoundSourceFromFile(AUDIO_PATH "noise.ogg", irrklang::ESM_AUTO_DETECT, false);
}
2021-12-07 18:59:50 -05:00
2023-09-29 12:04:08 -04:00
uint64_t seed = SEED ;
2023-10-16 16:35:26 -04:00
std : : string playname = " La Chienne <20> Jacques " ;
if ( NETWORK_TEST ) { // Test connexion r<> seau.
2023-09-25 17:17:17 -04:00
if ( ! m_conn . Init ( ) ) {
2023-09-27 11:24:41 -04:00
if ( ! m_conn . Connect ( SRV_ADDR , playname ) ) {
2023-10-16 16:35:26 -04:00
// setup jeu en r<> seau.
std : : cout < < " ID re<72> u du serveur: " < < std : : to_string ( m_conn . getId ( ) ) < < " ! " < < std : : endl ;
std : : cout < < " Seed re<72> u du serveur: " < < std : : to_string ( m_conn . getSeed ( ) ) < < " ! " < < std : : endl ;
2023-09-27 17:34:25 -04:00
seed = m_conn . getSeed ( ) ;
2023-09-25 08:23:52 -04:00
}
else std : : cout < < " Erreur de connexion. " < < std : : endl ;
}
2023-10-16 16:35:26 -04:00
else std : : cout < < " Erreur de cr<63> ation de socket. " < < std : : endl ;
2023-09-25 08:23:52 -04:00
}
m_world . SetSeed ( seed ) ;
2021-11-16 20:48:52 -05:00
// Init Chunks
2021-11-19 11:11:08 -05:00
m_world . GetChunks ( ) . Reset ( nullptr ) ;
2021-11-02 18:01:06 -04:00
2023-10-16 12:02:37 -04:00
2021-10-31 00:31:08 -04:00
// Gestion de souris.
2021-09-27 10:20:58 -04:00
CenterMouse ( ) ;
HideCursor ( ) ;
2021-09-24 10:15:43 -04:00
}
2023-09-15 11:24:43 -04:00
void Engine : : DeInit ( ) { }
2021-09-24 10:15:43 -04:00
2021-09-27 11:30:18 -04:00
void Engine : : LoadResource ( ) {
2023-09-16 00:12:14 -04:00
LoadTexture ( m_skybox . GetTexture ( ) , TEXTURE_PATH " skybox.png " , true ) ;
LoadTexture ( m_textureCrosshair , TEXTURE_PATH " cross.bmp " , true ) ;
LoadTexture ( m_textureFont , TEXTURE_PATH " font.bmp " , true ) ;
LoadTexture ( m_textureGun , TEXTURE_PATH " gun01.png " , false ) ;
2023-10-15 23:36:26 -04:00
LoadTexture ( m_texturePovGun , TEXTURE_PATH " GUN.png " , false ) ;
2023-10-25 01:01:25 -04:00
LoadTexture ( m_textureSoloMultiMenu , TEXTURE_PATH " single_multi.png " , false ) ;
LoadTexture ( m_textureTitle , TEXTURE_PATH " title.png " , false ) ;
2023-09-16 00:12:14 -04:00
2023-10-02 17:09:03 -04:00
LoadTexture ( MenuTitleTexture , MENU_ITEM_PATH " test.png " ) ;
LoadTexture ( MenuBGTexture , MENU_ITEM_PATH " test.png " ) ;
2023-10-23 16:57:19 -04:00
LoadTexture ( SplachScreenTexture , TEXTURE_PATH " sc2.png " ) ;
2023-10-02 17:09:03 -04:00
LoadTexture ( MenuQuitTexture , MENU_ITEM_PATH " BasicQuit.png " ) ;
LoadTexture ( MenuOptionsTexture , MENU_ITEM_PATH " test.png " ) ;
LoadTexture ( MenuStartTexture , MENU_ITEM_PATH " BasicPlay.png " ) ;
2021-10-31 00:31:08 -04:00
TextureAtlas : : TextureIndex texDirtIndex = m_textureAtlas . AddTexture ( TEXTURE_PATH " metal3.png " ) ;
2021-12-04 09:55:43 -05:00
TextureAtlas : : TextureIndex texIceIndex = m_textureAtlas . AddTexture ( TEXTURE_PATH " metal2.png " ) ;
2021-10-31 00:31:08 -04:00
TextureAtlas : : TextureIndex texGrassIndex = m_textureAtlas . AddTexture ( TEXTURE_PATH " grass.png " ) ;
2021-12-06 09:45:51 -05:00
TextureAtlas : : TextureIndex texMetalIndex = m_textureAtlas . AddTexture ( TEXTURE_PATH " dirt.png " ) ;
2021-10-26 17:28:37 -04:00
2021-12-06 10:58:40 -05:00
if ( ! m_textureAtlas . Generate ( TEXTURE_SIZE , false ) ) {
2021-10-26 17:28:37 -04:00
std : : cout < < " Unable to generate texture atlas ... " < < std : : endl ;
abort ( ) ;
}
2021-10-11 11:37:58 -04:00
2021-10-31 00:31:08 -04:00
float u , v , s ;
m_textureAtlas . TextureIndexToCoord ( texDirtIndex , u , v , s , s ) ;
m_blockinfo [ BTYPE_DIRT ] = new BlockInfo ( BTYPE_DIRT , " Dirt " , u , v , s , 1 ) ;
m_textureAtlas . TextureIndexToCoord ( texGrassIndex , u , v , s , s ) ;
m_blockinfo [ BTYPE_GRASS ] = new BlockInfo ( BTYPE_GRASS , " Grass " , u , v , s , 1 ) ;
m_textureAtlas . TextureIndexToCoord ( texMetalIndex , u , v , s , s ) ;
m_blockinfo [ BTYPE_METAL ] = new BlockInfo ( BTYPE_METAL , " Metal " , u , v , s , 1 ) ;
m_textureAtlas . TextureIndexToCoord ( texIceIndex , u , v , s , s ) ;
m_blockinfo [ BTYPE_ICE ] = new BlockInfo ( BTYPE_ICE , " Ice " , u , v , s , 1 ) ;
2021-10-11 11:37:58 -04:00
std : : cout < < " Loading and compiling shaders ... " < < std : : endl ;
2021-10-12 15:58:54 -04:00
if ( ! m_shader01 . Load ( SHADER_PATH " shader01.vert " , SHADER_PATH " shader01.frag " , true ) ) {
2021-10-11 11:37:58 -04:00
std : : cout < < " Failed to load shader " < < std : : endl ;
exit ( 1 ) ;
}
2021-09-24 10:15:43 -04:00
2021-10-12 15:58:54 -04:00
if ( ! m_skybox . GetShader ( ) . Load ( SHADER_PATH " skybox.vert " , SHADER_PATH " skybox.frag " , true ) ) {
std : : cout < < " Failed to load shader " < < std : : endl ;
exit ( 1 ) ;
}
2021-09-24 10:15:43 -04:00
}
2021-11-15 20:58:13 -05:00
void Engine : : UnloadResource ( ) { }
2021-10-12 15:58:54 -04:00
2023-10-23 15:43:55 -04:00
void Engine : : InstantDamage ( )
{
2023-10-30 14:36:44 -04:00
m_player . InflictDamage ( 0.10f ) ;
2023-10-23 15:43:55 -04:00
m_damage = false ;
}
2023-10-02 15:55:45 -04:00
void Engine : : SystemNotification ( std : : string systemLog ) {
std : : string message = " " ;
message = systemLog ;
DisplayNotification ( message ) ;
}
void Engine : : KillNotification ( Player killer , Player killed ) {
std : : string message = " " ;
message = killed . GetUsername ( ) + " killed by -> " + killer . GetUsername ( ) ;
DisplayNotification ( message ) ;
}
void Engine : : DisplayNotification ( std : : string message ) {
if ( message . length ( ) > 45 ) {
message = message . substr ( 0 , 45 ) ;
}
// Create a new notification and add it to the queue
Notification newNotification ;
newNotification . message = message ;
newNotification . displayStartTime = m_time ;
2023-10-23 16:11:35 -04:00
2023-10-02 15:55:45 -04:00
notifications . push_back ( newNotification ) ;
}
// Add a method to process the notification queue
void Engine : : ProcessNotificationQueue ( ) {
2023-10-23 16:11:35 -04:00
//PrintText(fPosX, fUsernamePosY, ss.str(), 1.5f);
//float fPosX = (Width() / 100.0f) * scaleX;
//float fPosY = Height() - (Height() * 0.05) * scaleY;
2023-10-02 15:55:45 -04:00
m_textureFont . Bind ( ) ;
2023-10-15 23:36:26 -04:00
auto [ scaleX , scaleY ] = GetScale ( ) ;
2023-10-23 16:11:35 -04:00
float xOffset = ( Width ( ) / 1.5f ) * scaleX ;
float yOffset = ( Height ( ) / 1.2f ) * scaleY ;
2023-10-15 23:36:26 -04:00
2023-10-02 15:55:45 -04:00
for ( auto it = notifications . begin ( ) ; it ! = notifications . end ( ) ; ) {
float timeSinceDisplay = m_time - it - > displayStartTime ;
2023-10-23 16:11:35 -04:00
float y = yOffset - ( 20.0f * scaleX * ( it - notifications . begin ( ) ) ) ;
2023-10-15 23:36:26 -04:00
2023-10-02 15:55:45 -04:00
glDisable ( GL_STENCIL_TEST ) ;
glDisable ( GL_DEPTH_TEST ) ;
glBlendFunc ( GL_SRC_ALPHA , GL_ONE ) ;
glBlendEquation ( GL_FUNC_ADD ) ;
glMatrixMode ( GL_PROJECTION ) ;
glPushMatrix ( ) ;
glLoadIdentity ( ) ;
glOrtho ( 0 , Width ( ) , 0 , Height ( ) , - 1 , 1 ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPushMatrix ( ) ;
2023-10-15 23:36:26 -04:00
PrintText ( xOffset , y , it - > message ) ;
2023-10-02 15:55:45 -04:00
glBlendFunc ( GL_CONSTANT_COLOR , GL_ONE_MINUS_CONSTANT_COLOR ) ;
glBlendEquation ( GL_FUNC_SUBTRACT ) ;
glEnable ( GL_STENCIL_TEST ) ;
glEnable ( GL_DEPTH_TEST ) ;
glMatrixMode ( GL_PROJECTION ) ;
glPopMatrix ( ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPopMatrix ( ) ;
2023-10-15 23:36:26 -04:00
2023-10-02 15:55:45 -04:00
if ( timeSinceDisplay > = 4.0f ) {
2023-10-15 23:36:26 -04:00
it = notifications . erase ( it ) ;
2023-10-02 15:55:45 -04:00
}
else {
+ + it ;
}
}
}
2023-09-15 20:28:20 -04:00
void Engine : : DisplayCrosshair ( ) {
m_textureCrosshair . Bind ( ) ;
static const int crossSize = 32 ;
2023-09-15 11:24:43 -04:00
glLoadIdentity ( ) ;
2023-09-15 20:28:20 -04:00
glTranslated ( Width ( ) / 2 - crossSize / 2 , Height ( ) / 2 - crossSize / 2 , 0 ) ;
glBegin ( GL_QUADS ) ;
2023-10-23 16:11:35 -04:00
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 0 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( crossSize , 0 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( crossSize , crossSize ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , crossSize ) ;
2023-09-15 20:28:20 -04:00
glEnd ( ) ;
}
2023-09-15 11:24:43 -04:00
2023-10-15 23:36:26 -04:00
void Engine : : DisplayPovGun ( ) {
// Setter le blend function, tout ce qui sera noir sera transparent
glDisable ( GL_STENCIL_TEST ) ;
glDisable ( GL_DEPTH_TEST ) ;
glBlendFunc ( GL_SRC_ALPHA , GL_ONE_MINUS_SRC_ALPHA ) ;
glBlendEquation ( GL_FUNC_ADD ) ;
glMatrixMode ( GL_PROJECTION ) ;
glPushMatrix ( ) ;
glLoadIdentity ( ) ;
glOrtho ( 0 , Width ( ) , 0 , Height ( ) , - 1 , 1 ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPushMatrix ( ) ;
2023-10-23 16:11:35 -04:00
float scaleX = ( Width ( ) ) / BASE_WIDTH ;
float scaleY = ( Height ( ) ) / BASE_HEIGHT ;
2023-10-15 23:36:26 -04:00
float baseXOffset = 0.4958 * BASE_WIDTH ;
float baseWidth = 0.4688 * BASE_WIDTH ;
float baseHeight = 0.5787 * BASE_HEIGHT ;
float xTranslation = baseXOffset * scaleX ;
float quadWidth = baseWidth * scaleX ;
float quadHeight = baseHeight * scaleY ;
m_texturePovGun . Bind ( ) ;
glLoadIdentity ( ) ;
glTranslated ( xTranslation , 0 , 0 ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0 , 0 ) ;
glVertex2i ( 0 , 0 ) ;
glTexCoord2f ( 1 , 0 ) ;
glVertex2i ( quadWidth , 0 ) ;
glTexCoord2f ( 1 , 1 ) ;
glVertex2i ( quadWidth , quadHeight ) ;
glTexCoord2f ( 0 , 1 ) ;
glVertex2i ( 0 , quadHeight ) ;
2023-09-15 20:28:20 -04:00
glEnd ( ) ;
2023-10-15 23:36:26 -04:00
// Reset du blend function
glBlendFunc ( GL_CONSTANT_COLOR , GL_ONE_MINUS_CONSTANT_COLOR ) ;
glBlendEquation ( GL_FUNC_SUBTRACT ) ;
glEnable ( GL_STENCIL_TEST ) ;
glEnable ( GL_DEPTH_TEST ) ;
glMatrixMode ( GL_PROJECTION ) ;
glPopMatrix ( ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPopMatrix ( ) ;
2023-09-15 20:28:20 -04:00
}
2023-09-15 11:24:43 -04:00
2023-09-16 00:12:14 -04:00
void Engine : : DisplayCurrentItem ( ) {
}
2023-10-16 17:36:04 -04:00
2023-09-23 17:15:35 -04:00
void Engine : : DisplayHud ( int timer ) {
2023-09-15 20:28:20 -04:00
glBindTexture ( GL_TEXTURE_2D , 0 ) ;
glLoadIdentity ( ) ;
2023-10-15 23:36:26 -04:00
glBlendFunc ( GL_SRC_ALPHA , GL_ONE_MINUS_SRC_ALPHA ) ;
auto [ scaleX , scaleY ] = GetScale ( ) ;
float fBackPosX = ( Width ( ) / 25.0f ) * scaleX ;
float fBackPosY = ( Height ( ) - ( Height ( ) * 0.815 ) * scaleY ) ;
float fBackWidth = ( Width ( ) / 4.0f ) * scaleX ;
float fBackHeight = ( Height ( ) / 5.5f ) * scaleY ;
glColor4f ( 1.0f , 1.0f , 1.0f , 0.2f ) ;
glBegin ( GL_QUADS ) ;
glVertex2f ( fBackPosX , fBackPosY ) ;
glVertex2f ( fBackPosX + fBackWidth , fBackPosY ) ;
glVertex2f ( fBackPosX + fBackWidth , fBackPosY + fBackHeight ) ;
glVertex2f ( fBackPosX , fBackPosY + fBackHeight ) ;
glEnd ( ) ;
// HP Bar
float fBarWidth = ( Width ( ) / 4.0f ) * scaleX ;
float fBarHeight = ( Height ( ) / 25.0f ) * scaleY ;
float fPosX = ( Width ( ) / 25.0f ) * scaleX ;
float fBarPosY = ( Height ( ) - ( Height ( ) * 0.775 ) * scaleY ) ;
2023-09-16 00:12:14 -04:00
2023-09-15 11:24:43 -04:00
float playerHp = m_player . GetHP ( ) ;
2023-09-16 00:12:14 -04:00
float facteurOmbrage = m_displayInfo ? 0.5f : 1.0f ;
2023-09-15 11:24:43 -04:00
2023-10-15 23:36:26 -04:00
// HP Bar Background
2023-09-16 00:12:14 -04:00
glColor3f ( 1.0f * facteurOmbrage , 1.0f * facteurOmbrage , 1.0f * facteurOmbrage ) ;
2023-09-15 11:24:43 -04:00
glBegin ( GL_QUADS ) ;
2023-10-15 23:36:26 -04:00
glVertex2f ( fPosX , fBarPosY - fBarHeight ) ;
glVertex2f ( fPosX + fBarWidth , fBarPosY - fBarHeight ) ;
glVertex2f ( fPosX + fBarWidth , fBarPosY ) ;
glVertex2f ( fPosX , fBarPosY ) ;
2023-09-15 11:24:43 -04:00
glEnd ( ) ;
2023-10-15 23:36:26 -04:00
// Current HP
2023-09-16 00:12:14 -04:00
glColor3f ( 0.0f * facteurOmbrage , 1.0f * facteurOmbrage , 0.0f * facteurOmbrage ) ;
2023-09-15 11:24:43 -04:00
glBegin ( GL_QUADS ) ;
2023-10-15 23:36:26 -04:00
glVertex2f ( fPosX , fBarPosY - fBarHeight ) ;
glVertex2f ( fPosX + fBarWidth * playerHp , fBarPosY - fBarHeight ) ;
glVertex2f ( fPosX + fBarWidth * playerHp , fBarPosY ) ;
glVertex2f ( fPosX , fBarPosY ) ;
2023-09-15 11:24:43 -04:00
glEnd ( ) ;
2023-09-16 00:12:14 -04:00
2023-10-15 23:36:26 -04:00
// Equip Bar
2023-09-15 11:24:43 -04:00
glEnable ( GL_BLEND ) ;
2023-09-16 00:12:14 -04:00
glBlendFunc ( GL_SRC_ALPHA , GL_ONE_MINUS_SRC_ALPHA ) ;
glColor3f ( 1.0f * facteurOmbrage , 1.0f * facteurOmbrage , 1.0f * facteurOmbrage ) ;
2023-10-15 23:36:26 -04:00
float fEquipWidth = ( Width ( ) * 0.175f ) * scaleX ;
float fEquipHeight = ( fEquipWidth / 2.5 ) * scaleY ;
float fEquipPosY = ( Height ( ) - ( Height ( ) * 0.765 ) * scaleY ) ;
2023-09-16 00:12:14 -04:00
2023-10-15 23:36:26 -04:00
glTranslatef ( fPosX , fEquipPosY , 0 ) ;
2023-09-16 00:12:14 -04:00
2023-10-15 23:36:26 -04:00
m_textureGun . Bind ( ) ;
2023-09-16 00:12:14 -04:00
glBegin ( GL_QUADS ) ;
2023-10-15 23:36:26 -04:00
glTexCoord2f ( 0 , 0 ) ; glVertex2i ( 0 , 0 ) ;
glTexCoord2f ( 1 , 0 ) ; glVertex2i ( fEquipWidth , 0 ) ;
glTexCoord2f ( 1 , 1 ) ; glVertex2i ( fEquipWidth , fEquipHeight ) ;
glTexCoord2f ( 0 , 1 ) ; glVertex2i ( 0 , fEquipHeight ) ;
2023-09-16 00:12:14 -04:00
glEnd ( ) ;
2023-10-16 17:36:04 -04:00
//glDisable(GL_BLEND);
2023-09-16 00:12:14 -04:00
// Username
glEnable ( GL_BLEND ) ;
glBlendFunc ( GL_SRC_ALPHA , GL_ONE ) ;
2023-09-15 20:28:20 -04:00
glColor3f ( 1.0f , 1.0f , 1.0f ) ;
2023-10-15 23:36:26 -04:00
2023-09-16 00:12:14 -04:00
m_textureFont . Bind ( ) ;
std : : ostringstream ss ;
2023-10-25 01:01:25 -04:00
float fUsernamePosY = fBarPosY - ( fBarHeight * 2 ) * scaleY ;
ss . str ( " " ) ;
2023-09-15 20:28:20 -04:00
ss < < m_player . GetUsername ( ) ;
2023-10-15 23:36:26 -04:00
PrintText ( fPosX , fUsernamePosY , ss . str ( ) , 1.5f ) ;
2023-09-23 17:15:35 -04:00
2023-10-25 01:01:25 -04:00
ss . str ( " " ) ;
2023-10-15 23:36:26 -04:00
ss < < m_player . GetHP ( ) * 100 < < " % " ;
PrintText ( fPosX * 6.25 , fUsernamePosY , ss . str ( ) , 1.5f ) ;
2023-09-23 17:15:35 -04:00
2023-10-15 23:36:26 -04:00
// Countdown
2023-09-23 17:15:35 -04:00
ss . str ( " " ) ;
ss < < " Time: " < < ( int ) ( timer / 60 ) < < " : " < < std : : setw ( 2 ) < < std : : setfill ( ' 0 ' ) < < timer % 60 ;
2023-10-15 23:36:26 -04:00
PrintText ( Width ( ) - ( Width ( ) * 0.2f ) * scaleX , Height ( ) - ( Height ( ) * 0.1 ) * scaleY , ss . str ( ) , 2.0f ) ;
2023-09-15 11:24:43 -04:00
}
2023-09-15 20:28:20 -04:00
void Engine : : DisplayInfo ( float elapsedTime , BlockType bloc ) {
2021-10-26 17:28:37 -04:00
m_textureFont . Bind ( ) ;
std : : ostringstream ss ;
2023-09-16 00:12:14 -04:00
2023-10-15 23:36:26 -04:00
auto [ scaleX , scaleY ] = GetScale ( ) ;
2023-09-16 00:12:14 -04:00
2023-10-15 23:36:26 -04:00
float fPosX = ( Width ( ) / 100.0f ) * scaleX ;
float fPosY = Height ( ) - ( Height ( ) * 0.05 ) * scaleY ;
float charSize = 20 + ( 24 - 20 ) * ( Width ( ) - 1600 ) / ( 1920 - 1600 ) ;
2023-09-16 00:12:14 -04:00
2021-10-26 17:28:37 -04:00
ss < < " Fps : " < < GetFps ( elapsedTime ) ;
2023-10-15 23:36:26 -04:00
PrintText ( fPosX , fPosY , ss . str ( ) ) ;
2021-10-26 17:28:37 -04:00
ss . str ( " " ) ;
2023-10-15 23:36:26 -04:00
fPosY - = charSize ;
2021-11-26 11:59:02 -05:00
ss < < " Rendered Chunks : " < < m_renderCount ;
2023-10-15 23:36:26 -04:00
PrintText ( fPosX , fPosY , ss . str ( ) ) ;
2021-11-26 11:59:02 -05:00
ss . str ( " " ) ;
2023-10-15 23:36:26 -04:00
fPosY - = charSize ;
2021-12-15 21:00:06 -05:00
ss < < " To-Be-Deleted Chunks : " < < m_world . GettbDeleted ( ) ;
2023-10-15 23:36:26 -04:00
PrintText ( fPosX , fPosY , ss . str ( ) ) ;
2021-12-15 21:00:06 -05:00
ss . str ( " " ) ;
2023-10-15 23:36:26 -04:00
fPosY - = charSize ;
2023-10-23 16:11:35 -04:00
float fPosYJump = ( ( Height ( ) - ( Height ( ) * 0.9f ) ) * scaleY ) ;
2023-10-15 23:36:26 -04:00
fPosY = fPosYJump ;
fPosY - = charSize ;
ss < < " Velocity : " < < m_player . GetVelocity ( ) ;
PrintText ( fPosX , fPosY , ss . str ( ) ) ;
2021-10-26 17:28:37 -04:00
ss . str ( " " ) ;
2023-10-15 23:36:26 -04:00
fPosY - = charSize ;
2021-10-26 17:28:37 -04:00
ss < < " Direction : " < < m_player . GetDirection ( ) ;
2023-10-15 23:36:26 -04:00
PrintText ( fPosX , fPosY , ss . str ( ) ) ;
2021-10-26 17:28:37 -04:00
ss . str ( " " ) ;
2023-10-15 23:36:26 -04:00
fPosY - = charSize ;
2021-10-26 17:28:37 -04:00
ss < < " Position : " < < m_player . GetPosition ( ) ;
2023-10-15 23:36:26 -04:00
PrintText ( fPosX , fPosY , ss . str ( ) ) ;
2021-12-07 18:59:50 -05:00
ss . str ( " " ) ;
2023-10-15 23:36:26 -04:00
fPosY - = charSize ;
2023-09-16 00:12:14 -04:00
2023-10-15 23:36:26 -04:00
ss < < " Block : " ;
2021-12-07 18:59:50 -05:00
if ( bloc = = BTYPE_LAST )
2023-10-15 23:36:26 -04:00
ss < < " Weapon " ;
else
ss < < ( int ) bloc ;
PrintText ( fPosX , fPosYJump , ss . str ( ) ) ;
2023-09-15 20:28:20 -04:00
}
2023-10-23 16:11:35 -04:00
void Engine : : DisplaySingleOrMultiplayerMenu ( ) {
2023-10-25 01:01:25 -04:00
glEnable ( GL_BLEND ) ;
glBlendFunc ( GL_SRC_ALPHA , GL_ONE_MINUS_SRC_ALPHA ) ;
glBlendEquation ( GL_FUNC_ADD ) ;
2023-10-23 16:11:35 -04:00
glDisable ( GL_STENCIL_TEST ) ;
glDisable ( GL_DEPTH_TEST ) ;
glMatrixMode ( GL_PROJECTION ) ;
glPushMatrix ( ) ;
glLoadIdentity ( ) ;
glOrtho ( 0 , Width ( ) , 0 , Height ( ) , - 1 , 1 ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPushMatrix ( ) ;
2023-10-25 01:01:25 -04:00
auto [ scaleX , scaleY ] = GetScale ( ) ;
2023-10-23 16:11:35 -04:00
float fBackPosX = 0.0f ;
2023-10-25 01:01:25 -04:00
float fBackPosY = 0.0f ;
float fBackWidth = Width ( ) ;
float fBackHeight = Height ( ) ;
2023-10-23 16:11:35 -04:00
2023-10-25 01:01:25 -04:00
m_textureSoloMultiMenu . Bind ( ) ;
2023-10-23 16:11:35 -04:00
glBegin ( GL_QUADS ) ;
2023-10-25 01:01:25 -04:00
glTexCoord2f ( 0.0f , 0.0f ) ; glVertex2f ( fBackPosX , fBackPosY ) ;
glTexCoord2f ( 1.0f , 0.0f ) ; glVertex2f ( fBackWidth , fBackPosY ) ;
glTexCoord2f ( 1.0f , 1.0f ) ; glVertex2f ( fBackWidth , fBackHeight ) ;
glTexCoord2f ( 0.0f , 1.0f ) ; glVertex2f ( fBackPosX , fBackHeight ) ;
2023-10-23 16:11:35 -04:00
glEnd ( ) ;
2023-10-25 01:01:25 -04:00
float centerX = ( Width ( ) / 2.0f ) ;
float centerY = ( Height ( ) / 2.0f ) ;
float titleWidth = ( centerX * 1.85f ) * scaleX ;
float titleHeight = ( centerY * 1.85f ) * scaleY ;
2023-10-23 16:11:35 -04:00
2023-10-25 01:01:25 -04:00
// Solo game indicator
m_textureTitle . Bind ( ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0.0f , 0.0f ) ; glVertex2f ( centerX , centerY ) ;
glTexCoord2f ( 1.0f , 0.0f ) ; glVertex2f ( titleWidth , centerY ) ;
glTexCoord2f ( 1.0f , 1.0f ) ; glVertex2f ( titleWidth , titleHeight ) ;
glTexCoord2f ( 0.0f , 1.0f ) ; glVertex2f ( centerX , titleHeight ) ;
glEnd ( ) ;
glBindTexture ( GL_TEXTURE_2D , 0 ) ;
// Solo game indicator
float fPosX = ( centerX * 1.1f ) * scaleX ;
float fPosXWidth = ( centerX * 1.75f ) * scaleX ;
float soloPosY = ( centerY * 0.75f ) * scaleY ;
float soloHeight = ( centerY * 0.9f ) * scaleY ;
glColor4f ( 1.0f , 1.0f , 1.0f , 0.5f ) ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0.0f , 0.0f ) ; glVertex2f ( fPosX , soloPosY ) ;
glTexCoord2f ( 1.0f , 0.0f ) ; glVertex2f ( fPosXWidth , soloPosY ) ;
glTexCoord2f ( 1.0f , 1.0f ) ; glVertex2f ( fPosXWidth , soloHeight ) ;
glTexCoord2f ( 0.0f , 1.0f ) ; glVertex2f ( fPosX , soloHeight ) ;
glEnd ( ) ;
// Multiplayer game indicator
float multiPosY = ( centerY * 0.5f ) * scaleY ;
float multiHeight = ( centerY * 0.65f ) * scaleY ;
glBegin ( GL_QUADS ) ;
glTexCoord2f ( 0.0f , 0.0f ) ; glVertex2f ( fPosX , multiPosY ) ;
glTexCoord2f ( 1.0f , 0.0f ) ; glVertex2f ( fPosXWidth , multiPosY ) ;
glTexCoord2f ( 1.0f , 1.0f ) ; glVertex2f ( fPosXWidth , multiHeight ) ;
glTexCoord2f ( 0.0f , 1.0f ) ; glVertex2f ( fPosX , multiHeight ) ;
glEnd ( ) ;
2023-09-16 00:12:14 -04:00
2023-10-25 01:01:25 -04:00
// TODO: Add SOLO / MULTIPLAYER text with font
2023-10-25 02:06:29 -04:00
glColor4f ( 1.0f , 1.0f , 1.0f , 1.0f ) ;
2023-10-23 16:11:35 -04:00
glEnable ( GL_STENCIL_TEST ) ;
glEnable ( GL_DEPTH_TEST ) ;
2023-09-16 00:12:14 -04:00
2023-10-23 16:11:35 -04:00
glMatrixMode ( GL_PROJECTION ) ;
glPopMatrix ( ) ;
glMatrixMode ( GL_MODELVIEW ) ;
glPopMatrix ( ) ;
2023-09-15 20:28:20 -04:00
}
void Engine : : DrawHud ( float elapsedTime , BlockType bloc ) {
2023-09-16 00:12:14 -04:00
// Setter le blend function, tout ce qui sera noir sera transparent
2023-09-15 20:28:20 -04:00
glDisable ( GL_STENCIL_TEST ) ;
2023-09-16 00:12:14 -04:00
glDisable ( GL_DEPTH_TEST ) ;
2023-09-15 20:28:20 -04:00
glBlendFunc ( GL_SRC_ALPHA , GL_ONE ) ;
glBlendEquation ( GL_FUNC_ADD ) ;
2023-10-16 17:36:04 -04:00
glEnable ( GL_BLEND ) ;
2023-09-16 00:12:14 -04:00
2023-09-15 20:28:20 -04:00
glMatrixMode ( GL_PROJECTION ) ;
glPushMatrix ( ) ;
2023-09-16 00:12:14 -04:00
2023-09-15 20:28:20 -04:00
glLoadIdentity ( ) ;
glOrtho ( 0 , Width ( ) , 0 , Height ( ) , - 1 , 1 ) ;
2023-09-16 00:12:14 -04:00
2023-09-15 20:28:20 -04:00
glMatrixMode ( GL_MODELVIEW ) ;
glPushMatrix ( ) ;
2023-09-23 17:15:35 -04:00
int timer = GetCountdown ( elapsedTime ) ;
2023-09-15 20:28:20 -04:00
2023-10-02 15:55:45 -04:00
if ( m_keyK ) {
SystemNotification ( m_messageNotification ) ;
m_keyK = false ;
}
if ( m_keyL ) {
2023-10-23 16:11:35 -04:00
2023-10-02 15:55:45 -04:00
KillNotification ( m_player , m_player ) ;
m_keyL = false ;
}
2023-09-15 20:28:20 -04:00
if ( m_displayInfo ) {
DisplayInfo ( elapsedTime , bloc ) ;
}
2023-09-16 00:12:14 -04:00
if ( m_displayHud ) {
2023-09-23 17:15:35 -04:00
DisplayHud ( timer ) ;
2023-09-16 00:12:14 -04:00
}
2023-09-15 20:28:20 -04:00
if ( m_displayCrosshair ) {
DisplayCrosshair ( ) ;
}
2023-09-15 11:24:43 -04:00
2021-12-06 11:08:34 -05:00
glBlendFunc ( GL_CONSTANT_COLOR , GL_ONE_MINUS_CONSTANT_COLOR ) ;
glBlendEquation ( GL_FUNC_SUBTRACT ) ;
2023-09-16 00:12:14 -04:00
2021-12-06 11:08:34 -05:00
glEnable ( GL_STENCIL_TEST ) ;
2023-09-16 00:12:14 -04:00
glEnable ( GL_DEPTH_TEST ) ;
2021-10-26 17:28:37 -04:00
glMatrixMode ( GL_PROJECTION ) ;
glPopMatrix ( ) ;
2023-09-16 00:12:14 -04:00
2021-10-26 17:28:37 -04:00
glMatrixMode ( GL_MODELVIEW ) ;
glPopMatrix ( ) ;
}
2023-10-15 23:36:26 -04:00
void Engine : : PrintText ( float x , float y , const std : : string & t , float charSizeMultiplier ) {
auto [ scaleX , scaleY ] = GetScale ( ) ;
2023-10-23 16:11:35 -04:00
float scale = std : : min ( scaleX , scaleY ) ;
2023-10-15 23:36:26 -04:00
float baseCharSize = 20 + ( 24 - 20 ) * ( Width ( ) - 1600 ) / ( 1920 - 1600 ) ;
float charSize = baseCharSize * charSizeMultiplier ;
2021-10-26 17:28:37 -04:00
glLoadIdentity ( ) ;
glTranslated ( x , y , 0 ) ;
2023-09-16 00:12:14 -04:00
2021-10-26 17:28:37 -04:00
for ( unsigned int i = 0 ; i < t . length ( ) ; + + i ) {
float left = ( float ) ( ( t [ i ] - 32 ) % 16 ) / 16.f ;
float top = ( float ) ( ( t [ i ] - 32 ) / 16 ) / 16.f ;
2023-10-15 23:36:26 -04:00
top + = 0.5f ;
2023-09-16 00:12:14 -04:00
2021-10-26 17:28:37 -04:00
glBegin ( GL_QUADS ) ;
2023-10-15 23:36:26 -04:00
glTexCoord2f ( left , 1.f - top - .0625f ) ; glVertex2f ( 0 , 0 ) ;
glTexCoord2f ( left + .0625f , 1.f - top - .0625f ) ; glVertex2f ( charSize * scale , 0 ) ;
glTexCoord2f ( left + .0625f , 1.f - top ) ; glVertex2f ( charSize * scale , charSize * scale ) ;
glTexCoord2f ( left , 1.f - top ) ; glVertex2f ( 0 , charSize * scale ) ;
2021-10-26 17:28:37 -04:00
glEnd ( ) ;
2023-09-15 11:24:43 -04:00
2023-10-23 16:11:35 -04:00
glTranslated ( 0.5555f * charSize * scale , 0 , 0 ) ;
2021-10-26 17:28:37 -04:00
}
}
2023-10-15 23:36:26 -04:00
std : : pair < float , float > Engine : : GetScale ( ) const {
float widthRatio = static_cast < float > ( Width ( ) ) / BASE_WIDTH ;
float heightRatio = static_cast < float > ( Height ( ) ) / BASE_HEIGHT ;
return { widthRatio , heightRatio } ;
2023-09-16 21:38:58 -04:00
}
2021-10-26 17:28:37 -04:00
int Engine : : GetFps ( float elapsedTime ) const { return 1 / elapsedTime ; }
2023-09-23 17:15:35 -04:00
int Engine : : GetCountdown ( float elapsedTime ) {
if ( m_resetcountdown )
{
m_countdown = m_time + COUNTDOWN ;
m_resetcountdown = false ;
}
2023-09-25 15:38:37 -04:00
if ( m_countdown < m_time )
Stop ( ) ;
2023-10-23 16:11:35 -04:00
if ( ! m_stopcountdown )
2023-09-23 17:15:35 -04:00
m_time + = elapsedTime ;
return m_countdown - ( int ) m_time ;
}
2021-10-26 17:28:37 -04:00
void Engine : : Render ( float elapsedTime ) {
2021-12-06 09:45:51 -05:00
glClear ( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT ) ;
2021-12-07 18:59:50 -05:00
2023-10-23 16:57:19 -04:00
m_time_SplashScreen + = elapsedTime ;
if ( m_time_SplashScreen < 2 )
DrawSplachScreen ( ) ;
else if ( m_gamestate = = GameState : : PLAY )
2023-10-02 17:09:03 -04:00
{
2023-10-16 17:36:04 -04:00
HideCursor ( ) ;
2023-10-16 16:35:26 -04:00
CenterMouse ( ) ; //D<> placement de centermouse dans l'action de jouer
2021-09-27 10:20:58 -04:00
2023-10-02 17:09:03 -04:00
//static float gameTime = elapsedTime;
2023-10-16 16:35:26 -04:00
static irrklang : : ISound * step ; // Pour les sons de pas.
2023-10-16 17:36:04 -04:00
static float pollTime = 0 ;
2023-10-02 17:09:03 -04:00
static float bulletTime = 0 ;
static BlockType bloc = 1 ;
2021-09-27 10:20:58 -04:00
2023-10-02 17:09:03 -04:00
if ( elapsedTime > 0.1f ) return ;
2021-09-27 10:20:58 -04:00
2023-10-02 17:09:03 -04:00
//gameTime += elapsedTime;
pollTime + = elapsedTime ;
2021-09-27 10:20:58 -04:00
2023-10-02 17:09:03 -04:00
Transformation all ;
Transformation skybox ;
2023-10-16 17:36:04 -04:00
Vector3f vstep ;
2022-04-02 15:26:55 -04:00
2023-10-02 17:09:03 -04:00
// Transformations initiales
glMatrixMode ( GL_MODELVIEW ) ;
glLoadIdentity ( ) ;
2023-09-15 11:24:43 -04:00
2023-10-02 17:09:03 -04:00
if ( bulletTime > 0.f ) bulletTime - = elapsedTime ;
if ( bulletTime < 0.f ) bulletTime = 0.f ;
2022-04-02 15:26:55 -04:00
2023-10-16 17:36:04 -04:00
static bool leftright = false ;
if ( pollTime > = .005f ) {
Player : : Sound snd = m_player . ApplyPhysics ( m_player . GetInput ( m_keyW , m_keyS , m_keyA , m_keyD , m_keySpace , ( bloc = = BTYPE_LAST & & bulletTime < = 0.f & & m_mouseL ) , elapsedTime ) , & m_world , elapsedTime ) ;
switch ( snd ) {
case Player : : Sound : : STEP :
if ( leftright )
vstep = Vector3f ( m_player . GetPosition ( ) . x + m_player . GetDirection ( ) . z , m_player . GetPosition ( ) . y - 1.7f , m_player . GetPosition ( ) . z + m_player . GetDirection ( ) . x ) ;
else vstep = Vector3f ( m_player . GetPosition ( ) . x - m_player . GetDirection ( ) . z , m_player . GetPosition ( ) . y - 1.7f , m_player . GetPosition ( ) . z - m_player . GetDirection ( ) . x ) ;
2023-10-23 16:10:21 -04:00
m_audio . Create3DAudioObj ( step , AUDIO_PATH " step.wav " , vstep , m_player . GetVelocity ( ) , false , .8f ) ;
2023-10-16 17:36:04 -04:00
leftright = ! leftright ;
break ;
case Player : : Sound : : FALL :
2023-10-23 16:10:21 -04:00
m_audio . Create3DAudioObj ( step , AUDIO_PATH " hit.wav " , m_player . GetPosition ( ) , m_player . GetVelocity ( ) , false , 1.f ) ;
2023-10-16 17:36:04 -04:00
break ;
default : break ;
2021-12-07 18:59:50 -05:00
}
2023-10-16 17:36:04 -04:00
m_audio . Update3DAudio ( m_player . GetPOV ( ) , m_player . GetDirection ( ) , m_player . GetVelocity ( ) ) ; // Ajustement du positionnement 3D avec les coordonn<6E> es du joueur et
// son vecteur de v<> locit<69> (pour l'effet Doppler)
pollTime = 0 ;
2023-10-02 17:09:03 -04:00
}
2021-12-06 21:46:46 -05:00
2023-10-02 17:09:03 -04:00
m_player . ApplyTransformation ( all ) ;
m_player . ApplyTransformation ( skybox , false ) ; // Version d'ApplyTransformation qui ne tient compte que de la rotation
// (donc l'objet ne bouge pas relativement au joueur, ce qui est pratique pour une skybox!).
if ( m_mouseWU ) bloc + + ;
else if ( m_mouseWD ) bloc - - ;
if ( bloc = = BTYPE_LAST + 1 ) bloc = BTYPE_AIR + 1 ;
2023-10-16 16:35:26 -04:00
else if ( bloc = = BTYPE_AIR ) bloc = BTYPE_LAST ; // La selection de BTYPE_LAST <20> quipe l'arme.
2023-10-02 17:09:03 -04:00
m_mouseWU = m_mouseWD = false ;
2023-10-16 17:36:04 -04:00
if ( m_mouseL ) {
if ( bloc ! = BTYPE_LAST )
m_world . ChangeBlockAtCursor ( bloc , m_player . GetPosition ( ) , m_player . GetDirection ( ) , m_block ) ;
else if ( bulletTime < = 0.f ) {
for ( int x = 0 ; x < MAX_BULLETS ; + + x ) // Ajouter une balle dans l'array (aussi connu sous le nom de "faire pow pow").
if ( ! m_bullets [ x ] ) {
m_bullets [ x ] = new Bullet ( m_player . GetPOV ( ) + m_player . GetDirection ( ) , m_player . GetDirection ( ) ) ;
break ;
}
else if ( x = = MAX_BULLETS - 1 ) { // S'il y a pas d'espace dans l'array, prendre la place de la premi<6D> re balle de l'array.
m_bullets [ 0 ] - > ~ Bullet ( ) ;
m_bullets [ 0 ] = new Bullet ( m_player . GetPOV ( ) + m_player . GetDirection ( ) , m_player . GetDirection ( ) ) ;
}
2021-12-07 18:59:50 -05:00
}
}
2021-11-30 19:55:11 -05:00
else if ( m_mouseR )
2023-09-30 14:46:54 -04:00
m_world . ChangeBlockAtCursor ( BTYPE_AIR , m_player . GetPosition ( ) , m_player . GetDirection ( ) , m_block ) ;
2023-10-16 12:02:37 -04:00
for ( int x = 0 ; x < MAX_BULLETS ; + + x ) { // Array de bullets en jeu.
if ( m_bullets [ x ] ) {
for ( int b = 0 ; b < BULLET_UPDATES_PER_FRAME ; + + b )
if ( m_bullets [ x ] - > Update ( & m_world , elapsedTime , BULLET_UPDATES_PER_FRAME ) ) {
m_bullets [ x ] - > ~ Bullet ( ) ;
if ( m_whoosh [ x ] )
m_whoosh [ x ] - > drop ( ) ;
m_bullets [ x ] = nullptr ;
m_whoosh [ x ] = nullptr ;
2021-12-07 18:59:50 -05:00
break ;
}
2023-10-16 12:02:37 -04:00
else if ( ! m_whoosh [ x ] ) {
m_whoosh [ x ] = m_audio . Create3DAudioObj ( m_whoosh [ x ] , AUDIO_PATH " noise.wav " , m_bullets [ x ] - > getPos ( ) , m_bullets [ x ] - > getVel ( ) , true , ( m_bullets [ x ] - > getPos ( ) - m_player . GetPosition ( ) ) . Length ( ) ) ;
2021-12-07 18:59:50 -05:00
}
2023-10-16 12:02:37 -04:00
else m_audio . Render3DAudioObj ( m_whoosh [ x ] , m_bullets [ x ] - > getPos ( ) , m_bullets [ x ] - > getVel ( ) , 5 - ( m_bullets [ x ] - > getPos ( ) - m_player . GetPosition ( ) ) . Length ( ) ) ;
2021-12-07 18:59:50 -05:00
}
}
2021-11-19 13:25:52 -05:00
2023-10-16 17:36:04 -04:00
m_wrenderer . RenderWorld ( & m_world , m_renderCount , m_player . GetPosition ( ) , m_player . GetDirection ( ) , all , m_shader01 , m_textureAtlas ) ;
m_world . Update ( m_bullets , m_player . GetPosition ( ) , m_blockinfo ) ;
m_wrenderer . UpdateWorld ( & m_world , m_player . GetPosition ( ) , m_blockinfo ) ;
2021-12-07 18:59:50 -05:00
2023-10-16 17:36:04 -04:00
if ( m_isSkybox ) m_skybox . Render ( skybox ) ;
2023-10-02 17:09:03 -04:00
2023-10-16 17:36:04 -04:00
DrawHud ( elapsedTime , bloc ) ;
2023-10-27 14:53:45 -04:00
DisplayPovGun ( ) ;
ProcessNotificationQueue ( ) ;
2023-10-30 14:36:44 -04:00
if ( m_damage )
{
InstantDamage ( ) ;
}
2023-10-16 17:36:04 -04:00
static bool fell = false ;
if ( m_player . GetPosition ( ) . y < 1.7f & & ! fell ) {
2023-10-23 16:10:21 -04:00
m_audio . Create3DAudioObj ( m_scream , AUDIO_PATH " scream.wav " , m_player . GetPOV ( ) , m_player . GetVelocity ( ) , false , 1.f ) ;
2023-10-16 17:36:04 -04:00
fell = true ;
}
else if ( m_player . GetPosition ( ) . y < - 20.f ) {
m_player = Player ( Vector3f ( .5f , CHUNK_SIZE_Y + 1.8f , .5f ) ) ; // Respawn si le bonho- joueur tombe en bas du monde.
fell = false ;
}
2021-11-26 11:59:02 -05:00
2021-12-07 18:59:50 -05:00
}
2023-10-16 17:36:04 -04:00
else if ( m_gamestate = = GameState : : MAIN_MENU | | m_gamestate = = GameState : : OPTIONS )
{
DrawMenu ( ) ;
2021-12-07 18:59:50 -05:00
}
2023-10-16 17:36:04 -04:00
else if ( m_gamestate = = GameState : : QUIT )
Stop ( ) ;
2021-09-24 10:15:43 -04:00
}
2021-12-02 18:12:35 -05:00
void Engine : : KeyPressEvent ( unsigned char key ) {
2021-10-11 11:37:58 -04:00
switch ( key ) {
2023-09-15 11:24:43 -04:00
case 0 : // A - Gauche
2021-09-27 10:20:58 -04:00
if ( ! m_keyA ) {
m_keyA = true ;
}
break ;
2023-09-15 11:24:43 -04:00
case 3 : // D - Droite
if ( ! m_keyD ) {
m_keyD = true ;
}
break ;
case 18 : // S - Reculer
2021-09-27 10:20:58 -04:00
if ( ! m_keyS ) {
m_keyS = true ;
}
break ;
2023-09-15 11:24:43 -04:00
case 22 : // W - Avancer
if ( ! m_keyW ) {
m_keyW = true ;
2021-09-27 10:20:58 -04:00
}
break ;
2023-09-15 11:24:43 -04:00
case 36 : // ESC - Quitter
2023-10-16 17:36:04 -04:00
m_gamestate = GameState : : MAIN_MENU ;
//Stop();
2021-10-04 12:29:10 -04:00
break ;
2023-09-15 11:24:43 -04:00
case 57 : // Space - Sauter
2021-10-01 10:52:33 -04:00
if ( ! m_keySpace ) {
m_keySpace = true ;
}
break ;
2023-10-16 16:35:26 -04:00
case 94 : // F10 - Plein <20> cran
2023-09-16 21:38:58 -04:00
IsFullscreen ( ) ? SetFullscreen ( false ) : SetFullscreen ( true ) ;
//SetFullscreen(!IsFullscreen());
2023-09-15 11:24:43 -04:00
break ;
2023-09-15 20:28:20 -04:00
case 2 : // C - Ignorer
break ;
2021-12-07 18:59:50 -05:00
case 5 : // F - Ignorer
2023-09-15 11:24:43 -04:00
break ;
2023-10-02 15:55:45 -04:00
case 10 : // K - Debugging DisplayNotification()
m_keyK = true ;
2023-10-16 16:35:26 -04:00
m_messageNotification = " notifications systeme peuvent <20> tre affich<63> " ;
2023-10-02 15:55:45 -04:00
break ;
case 11 : // L - Debugging DisplayNotification()
m_keyL = true ;
break ;
2023-09-23 17:15:35 -04:00
case 6 : // G - Ignorer
break ;
2021-10-19 10:27:59 -04:00
case 12 : // M - Ignorer
2023-09-15 11:24:43 -04:00
break ;
case 7 : // H - Ignorer
break ;
case 8 : // I - Ignorer
break ;
2023-10-23 15:43:55 -04:00
case 9 : // J - InstantDamage
m_damage = true ;
2023-10-16 12:02:37 -04:00
case 15 : // P - Ignorer
2023-10-23 15:43:55 -04:00
break ;
2021-11-26 11:59:02 -05:00
case 17 : // R - Ignorer
2021-09-27 10:20:58 -04:00
break ;
2023-09-23 17:15:35 -04:00
case 19 : // T - Ignorer
2023-10-23 16:11:35 -04:00
break ;
2023-09-15 11:24:43 -04:00
case 24 : // Y - Ignorer
break ;
case 255 : // Fn - Ignorer
break ;
2021-09-27 10:20:58 -04:00
default :
std : : cout < < " Unhandled key: " < < ( int ) key < < std : : endl ;
}
2021-09-24 10:15:43 -04:00
}
2021-12-02 18:12:35 -05:00
void Engine : : KeyReleaseEvent ( unsigned char key ) {
2021-10-11 11:37:58 -04:00
switch ( key ) {
2023-09-15 11:24:43 -04:00
case 0 : // A - Stop gauche
m_keyA = false ;
break ;
2023-09-15 20:28:20 -04:00
case 2 : // C - Toggle crosshair
m_displayCrosshair = ! m_displayCrosshair ;
std : : cout < < " DISPLAY CROSSHAIR " < < ( m_displayCrosshair ? " enabled " : " disabled " ) < < std : : endl ;
break ;
2023-09-15 11:24:43 -04:00
case 3 : // D - Stop droite
m_keyD = false ;
break ;
case 5 : // F - Toggle flash
2021-12-07 18:59:50 -05:00
m_flash = ! m_flash ;
break ;
2023-09-23 17:15:35 -04:00
case 6 : // G - Toggle Stop Countdown
m_stopcountdown = ! m_stopcountdown ;
std : : cout < < " STOP COUNTDOWN " < < ( m_stopcountdown ? " enabled " : " disabled " ) < < std : : endl ;
break ;
2023-09-15 11:24:43 -04:00
case 7 : // H - Toggle HUD
m_displayHud = ! m_displayHud ;
std : : cout < < " DISPLAY HUD " < < ( m_displayHud ? " enabled " : " disabled " ) < < std : : endl ;
break ;
case 8 : // I - Toggle render data
2023-09-15 20:28:20 -04:00
m_displayInfo = ! m_displayInfo ;
std : : cout < < " DISPLAY INFO " < < ( m_displayInfo ? " enabled " : " disabled " ) < < std : : endl ;
2023-09-15 11:24:43 -04:00
break ;
2023-10-02 15:55:45 -04:00
case 10 : // K
m_keyK = false ;
break ;
case 11 : // L - Debugging DisplayNotification()
m_keyL = false ;
break ;
2023-09-15 11:24:43 -04:00
case 12 : // M - Toggle music
2021-10-25 10:50:08 -04:00
m_audio . ToggleMusicState ( ) ;
2021-10-19 10:27:59 -04:00
break ;
2023-10-16 12:02:37 -04:00
case 15 :
for ( int x = 0 ; x < MAX_BULLETS ; + + x ) // Ajouter une balle dans l'array (aussi connu sous le nom de "faire pow pow").
if ( ! m_bullets [ x ] ) {
m_bullets [ x ] = new Bullet ( m_player . GetPOV ( ) - Vector3f ( 1.f , 0.f , 1.f ) , Vector3f ( 1.f , 0.f , 1.f ) ) ;
break ;
}
2023-10-16 17:43:32 -04:00
else if ( x = = MAX_BULLETS - 1 ) { // S'il y a pas d'espace dans l'array, prendre la place de la premi<6D> re balle de l'array.
2023-10-16 12:02:37 -04:00
m_bullets [ 0 ] - > ~ Bullet ( ) ;
m_bullets [ 0 ] = new Bullet ( m_player . GetPOV ( ) - Vector3f ( 1.f , 0.f , 1.f ) , Vector3f ( 1.f , 0.f , 1.f ) ) ;
}
break ;
2023-09-15 11:24:43 -04:00
case 17 : // R - Toggle skybox
2021-12-01 21:21:45 -05:00
m_isSkybox = ! m_isSkybox ;
2021-11-26 11:59:02 -05:00
break ;
2023-09-15 11:24:43 -04:00
case 18 : // S - Stop reculer
m_keyS = false ;
break ;
2023-09-23 17:15:35 -04:00
case 19 : // T -Reset countdown
m_resetcountdown = true ;
std : : cout < < " RESET COUNTDOWN " < < std : : endl ;
break ;
2023-09-15 11:24:43 -04:00
case 22 : // W - Stop avancer
m_keyW = false ;
break ;
case 24 : // Y - Wireframe
2021-09-27 10:20:58 -04:00
m_wireframe = ! m_wireframe ;
if ( m_wireframe )
glPolygonMode ( GL_FRONT_AND_BACK , GL_LINE ) ;
else
glPolygonMode ( GL_FRONT_AND_BACK , GL_FILL ) ;
break ;
2023-09-15 11:24:43 -04:00
case 57 : // Espace - Stop sauter
2021-10-01 10:52:33 -04:00
m_keySpace = false ;
break ;
2021-09-27 10:20:58 -04:00
}
2021-09-24 10:15:43 -04:00
}
2021-12-02 18:12:35 -05:00
void Engine : : MouseMoveEvent ( int x , int y ) {
2021-10-04 12:29:10 -04:00
m_player . TurnLeftRight ( x - ( Width ( ) / 2 ) ) ;
m_player . TurnTopBottom ( y - ( Height ( ) / 2 ) ) ;
2021-09-27 13:15:57 -04:00
2023-10-16 16:35:26 -04:00
// Centrer la souris seulement si elle n'est pas d<> j<EFBFBD> centr<74> e
// Il est n<> cessaire de faire la v<> rification pour <20> viter de tomber
// dans une boucle infinie o<> l'appel <20> CenterMouse g<> n<EFBFBD> re un
2021-09-27 10:20:58 -04:00
// MouseMoveEvent, qui rapelle CenterMouse qui rapelle un autre
// MouseMoveEvent, etc
if ( x = = ( Width ( ) / 2 ) & & y = = ( Height ( ) / 2 ) )
return ;
2021-09-24 10:15:43 -04:00
}
2021-11-26 11:59:02 -05:00
void Engine : : MousePressEvent ( const MOUSE_BUTTON & button , int x , int y ) {
2023-10-02 17:09:03 -04:00
m_mousemx = x ;
m_mousemy = y ;
if ( m_gamestate = = GameState : : PLAY )
{
switch ( button ) {
case MOUSE_BUTTON_LEFT :
m_mouseL = true ;
break ;
case MOUSE_BUTTON_RIGHT :
m_mouseR = true ;
break ;
case MOUSE_BUTTON_MIDDLE :
m_mouseC = true ;
break ;
case MOUSE_BUTTON_WHEEL_UP :
m_mouseWU = true ;
break ;
case MOUSE_BUTTON_WHEEL_DOWN :
m_mouseWD = true ;
break ;
case MOUSE_BUTTON_NONE : break ;
}
}
else if ( m_gamestate = = GameState : : MAIN_MENU )
{
if ( ( m_mousemx > = 285 & & m_mousemx < = 490 ) & & ( m_mousemy > = 150 & & m_mousemy < = 250 ) )
m_gamestate = GameState : : PLAY ;
if ( ( m_mousemx > = 305 & & m_mousemx < = 450 ) & & ( m_mousemy > = 300 & & m_mousemy < = 400 ) )
m_gamestate = GameState : : QUIT ;
2021-11-26 11:59:02 -05:00
}
2021-09-24 10:15:43 -04:00
}
2021-11-26 11:59:02 -05:00
void Engine : : MouseReleaseEvent ( const MOUSE_BUTTON & button , int x , int y ) {
switch ( button ) {
case MOUSE_BUTTON_LEFT :
m_mouseL = false ;
2021-11-27 13:35:39 -05:00
m_block = false ;
2021-11-26 11:59:02 -05:00
break ;
case MOUSE_BUTTON_RIGHT :
m_mouseR = false ;
2021-11-27 13:35:39 -05:00
m_block = false ;
2021-11-26 11:59:02 -05:00
break ;
case MOUSE_BUTTON_MIDDLE :
m_mouseC = false ;
break ;
case MOUSE_BUTTON_WHEEL_UP :
m_mouseWU = false ;
break ;
case MOUSE_BUTTON_WHEEL_DOWN :
m_mouseWD = false ;
break ;
case MOUSE_BUTTON_NONE : break ;
}
2021-09-24 10:15:43 -04:00
}
2023-09-16 00:12:14 -04:00
bool Engine : : LoadTexture ( Texture & texture , const std : : string & filename , bool useMipmaps , bool stopOnError ) {
texture . Load ( filename , useMipmaps ) ;
2023-09-15 11:24:43 -04:00
if ( ! texture . IsValid ( ) ) {
2021-09-27 10:20:58 -04:00
std : : cerr < < " Unable to load texture ( " < < filename < < " ) " < < std : : endl ;
if ( stopOnError )
Stop ( ) ;
2021-09-24 10:15:43 -04:00
2021-09-27 10:20:58 -04:00
return false ;
}
2021-09-24 10:15:43 -04:00
2021-09-27 10:20:58 -04:00
return true ;
2021-09-24 10:15:43 -04:00
}