This commit is contained in:
Saggi Mizrahi 2016-12-22 01:28:53 +00:00 committed by GitHub
commit ac05e039b1
28 changed files with 226 additions and 552 deletions

14
.gitignore vendored
View File

@ -51,6 +51,17 @@ ipch/
*.exe
!tools/rREM/rrem.exe
# Ignore all examples files
examples/*
# Unignore all examples dirs
!examples/*/
# Unignore all examples files with extension
!examples/*.c
!examples/*.lua
!examples/*.png
# Unignore examples Makefile
!examples/Makefile
# Ignore files build by xcode
*.mode*v*
*.pbxuser
@ -68,9 +79,6 @@ DerivedData/
src/libraylib.a
src/libraylib.bc
# oculus example
!examples/oculus_glfw_sample/
# external libraries DLLs
!src/external/glfw3/lib/win32/glfw3.dll
!src/external/openal_soft/lib/win32/OpenAL32.dll

View File

@ -11,7 +11,7 @@ NOTE:
It includes some interesting new features and is a stepping stone towards raylib future.
HUGE changes:
[rlua] LUA BINDING: Complete raylib LUA binding, ALL raylib functions ported to LUA plus the +60 code examples.
[rlua] Lua BINDING: Complete raylib Lua binding, ALL raylib functions ported to Lua plus the +60 code examples.
[audio] COMPLETE REDESIGN: Improved music support and also raw audio data processing and playing, +20 new functions added.
[physac] COMPLETE REWRITE: Improved performance, functionality and simplified usage, moved to own repository and added multiple examples!

View File

@ -158,7 +158,7 @@ notes on raylib 1.6
On November 2016, only 4 months after raylib 1.5, arrives raylib 1.6. This new version represents another big review of the library and includes some interesting additions. This version conmmemorates raylib 3rd anniversary (raylib 1.0 was published on November 2013) and it is a stepping stone for raylib future. raylib roadmap has been reviewed and redefined to focus on its primary objective: create a simple and easy-to-use library to learn videogames programming. Some of the new features:
Complete raylib LUA binding. All raylib functions plus the +60 code examples have been ported to LUA, now LUA users can enjoy coding videogames in LUA while using all the internal power of raylib. This addition also open the doors to LUA scripting support for a future raylib-based engine, being able to move game logic (Init, Update, Draw, De-Init) to LUA scripts while keep using raylib functionality.
Complete raylib Lua binding. All raylib functions plus the +60 code examples have been ported to Lua, now Lua users can enjoy coding videogames in Lua while using all the internal power of raylib. This addition also open the doors to Lua scripting support for a future raylib-based engine, being able to move game logic (Init, Update, Draw, De-Init) to Lua scripts while keep using raylib functionality.
Completely redesigned audio module. Based on the new direction taken in raylib 1.5, it has been further improved and more functionality added (+20 new functions) to allow raw audio processing and streaming. FLAC file format support has also been added. In the same line, OpenAL Soft backend is now provided as a static library in Windows to allow static linking and get ride of OpenAL32.dll. Now raylib Windows games are completey self-contained, no external libraries required any more!
@ -273,6 +273,9 @@ contributing (in some way or another) to make raylib project better. Huge thanks
- [Emanuele Petriglia](https://github.com/LelixSuper) for working on multiple GNU/Linux improvements and developing [TicTacToe](https://github.com/LelixSuper/TicTacToe) raylib game.
- [Joshua Reisenauer](https://github.com/kd7tck) for adding audio modules support (XM, MOD) and reviewing audio system.
- Marcelo Paez (paezao) for his help on OSX to solve High DPI display issue. Thanks Marcelo!
- [Ghassan Al-Mashareqa](https://github.com/ghassanpl) for his amazing contribution with raylib Lua module, I just work over his code to implement [rlua](https://github.com/raysan5/raylib/blob/master/src/rlua.h)
- [Teodor Stoenescu](https://github.com/teodor-stoenescu) for his improvements on OBJ object loading.
Please, if I forget someone in this list, excuse me and write me an email to remind me to add you!
[raysan5]: mailto:raysan5@gmail.com "Ramon Santamaria - Ray San"

View File

@ -17,7 +17,7 @@ raylib 1.x
raylib 1.6
[DONE] LUA scripting support (raylib lua wrapper)
[DONE] Lua scripting support (raylib Lua wrapper)
[DONE] Redesigned audio module
raylib 1.5

View File

@ -112,7 +112,7 @@ int main()
//----------------------------------------------------------------------------------
BeginDrawing();
ClearBackground(WHITE);
ClearBackground(RAYWHITE);
for (int i = MAX_CIRCLES - 1; i >= 0; i--)
{

View File

@ -24,10 +24,52 @@
********************************************************************************************/
#include <stdio.h>
#if defined(_WIN32)
#include <conio.h> // Windows only, no stardard library
#endif
#include "audio.h"
#if defined(__linux)
#include <stdio.h>
#include <termios.h>
#include <unistd.h>
#include <fcntl.h>
static int kbhit(void)
{
struct termios oldt, newt;
int ch;
int oldf;
tcgetattr(STDIN_FILENO, &oldt);
newt = oldt;
newt.c_lflag &= ~(ICANON | ECHO);
tcsetattr(STDIN_FILENO, TCSANOW, &newt);
oldf = fcntl(STDIN_FILENO, F_GETFL, 0);
fcntl(STDIN_FILENO, F_SETFL, oldf | O_NONBLOCK);
ch = getchar();
tcsetattr(STDIN_FILENO, TCSANOW, &oldt);
fcntl(STDIN_FILENO, F_SETFL, oldf);
if(ch != EOF)
{
ungetc(ch, stdin);
return 1;
}
return 0;
}
static char getch()
{
return getchar();
}
#endif
#define KEY_ESCAPE 27
int main()

View File

@ -12,7 +12,7 @@
#include "raylib.h"
#define PHYSAC_IMPLEMENTATION
#include "..\src\physac.h"
#include "../src/physac.h"
int main()
{

View File

@ -12,7 +12,7 @@
#include "raylib.h"
#define PHYSAC_IMPLEMENTATION
#include "..\src\physac.h"
#include "../src/physac.h"
int main()
{

View File

@ -12,7 +12,7 @@
#include "raylib.h"
#define PHYSAC_IMPLEMENTATION
#include "..\src\physac.h"
#include "../src/physac.h"
#define VELOCITY 0.5f

View File

@ -12,7 +12,7 @@
#include "raylib.h"
#define PHYSAC_IMPLEMENTATION
#include "..\src\physac.h"
#include "../src/physac.h"
int main()
{

View File

@ -12,7 +12,7 @@
#include "raylib.h"
#define PHYSAC_IMPLEMENTATION
#include "..\src\physac.h"
#include "../src/physac.h"
int main()
{

View File

@ -144,7 +144,7 @@ int main(void)
{
// Update
//----------------------------------------------------------------------------------
UpdateOculusTracking();
UpdateOculusTracking(&camera);
//----------------------------------------------------------------------------------
// Draw

View File

@ -1,29 +0,0 @@
========================================================================
STATIC LIBRARY : raylib Project Overview
========================================================================
AppWizard has created this raylib library project for you.
No source files were created as part of your project.
raylib.vcxproj
This is the main project file for VC++ projects generated using an Application Wizard.
It contains information about the version of Visual C++ that generated the file, and
information about the platforms, configurations, and project features selected with the
Application Wizard.
raylib.vcxproj.filters
This is the filters file for VC++ projects generated using an Application Wizard.
It contains information about the association between the files in your project
and the filters. This association is used in the IDE to show grouping of files with
similar extensions under a specific node (for e.g. ".cpp" files are associated with the
"Source Files" filter).
/////////////////////////////////////////////////////////////////////////////
Other notes:
AppWizard uses "TODO:" comments to indicate parts of the source code you
should add to or customize.
/////////////////////////////////////////////////////////////////////////////

View File

@ -52,8 +52,7 @@
#include <stdarg.h> // Required for: va_list, va_start(), vfprintf(), va_end()
#else
#include "raylib.h"
#include "utils.h" // Required for: DecompressData()
// NOTE: Includes Android fopen() function map
#include "utils.h" // Required for: fopen() Android mapping, TraceLog()
#endif
#include "AL/al.h" // OpenAL basic header
@ -324,117 +323,6 @@ Sound LoadSoundFromWave(Wave wave)
return sound;
}
// Load sound to memory from rRES file (raylib Resource)
// TODO: Maybe rresName could be directly a char array with all the data?
Sound LoadSoundFromRES(const char *rresName, int resId)
{
Sound sound = { 0 };
#if defined(AUDIO_STANDALONE)
TraceLog(WARNING, "Sound loading from rRES resource file not supported on standalone mode");
#else
bool found = false;
char id[4]; // rRES file identifier
unsigned char version; // rRES file version and subversion
char useless; // rRES header reserved data
short numRes;
ResInfoHeader infoHeader;
FILE *rresFile = fopen(rresName, "rb");
if (rresFile == NULL) TraceLog(WARNING, "[%s] rRES raylib resource file could not be opened", rresName);
else
{
// Read rres file (basic file check - id)
fread(&id[0], sizeof(char), 1, rresFile);
fread(&id[1], sizeof(char), 1, rresFile);
fread(&id[2], sizeof(char), 1, rresFile);
fread(&id[3], sizeof(char), 1, rresFile);
fread(&version, sizeof(char), 1, rresFile);
fread(&useless, sizeof(char), 1, rresFile);
if ((id[0] != 'r') && (id[1] != 'R') && (id[2] != 'E') &&(id[3] != 'S'))
{
TraceLog(WARNING, "[%s] This is not a valid raylib resource file", rresName);
}
else
{
// Read number of resources embedded
fread(&numRes, sizeof(short), 1, rresFile);
for (int i = 0; i < numRes; i++)
{
fread(&infoHeader, sizeof(ResInfoHeader), 1, rresFile);
if (infoHeader.id == resId)
{
found = true;
// Check data is of valid SOUND type
if (infoHeader.type == 1) // SOUND data type
{
// TODO: Check data compression type
// NOTE: We suppose compression type 2 (DEFLATE - default)
// Reading SOUND parameters
Wave wave;
short sampleRate, bps;
char channels, reserved;
fread(&sampleRate, sizeof(short), 1, rresFile); // Sample rate (frequency)
fread(&bps, sizeof(short), 1, rresFile); // Bits per sample
fread(&channels, 1, 1, rresFile); // Channels (1 - mono, 2 - stereo)
fread(&reserved, 1, 1, rresFile); // <reserved>
wave.sampleRate = sampleRate;
wave.sampleSize = bps;
wave.channels = (short)channels;
unsigned char *data = malloc(infoHeader.size);
fread(data, infoHeader.size, 1, rresFile);
wave.data = DecompressData(data, infoHeader.size, infoHeader.srcSize);
free(data);
sound = LoadSoundFromWave(wave);
// Sound is loaded, we can unload wave data
UnloadWave(wave);
}
else TraceLog(WARNING, "[%s] Required resource do not seem to be a valid SOUND resource", rresName);
}
else
{
// Depending on type, skip the right amount of parameters
switch (infoHeader.type)
{
case 0: fseek(rresFile, 6, SEEK_CUR); break; // IMAGE: Jump 6 bytes of parameters
case 1: fseek(rresFile, 6, SEEK_CUR); break; // SOUND: Jump 6 bytes of parameters
case 2: fseek(rresFile, 5, SEEK_CUR); break; // MODEL: Jump 5 bytes of parameters (TODO: Review)
case 3: break; // TEXT: No parameters
case 4: break; // RAW: No parameters
default: break;
}
// Jump DATA to read next infoHeader
fseek(rresFile, infoHeader.size, SEEK_CUR);
}
}
}
fclose(rresFile);
}
if (!found) TraceLog(WARNING, "[%s] Required resource id [%i] could not be found in the raylib resource file", rresName, resId);
#endif
return sound;
}
// Unload Wave data
void UnloadWave(Wave wave)
{
@ -454,7 +342,7 @@ void UnloadSound(Sound sound)
// Update sound buffer with new data
// NOTE: data must match sound.format
void UpdateSound(Sound sound, void *data, int numSamples)
void UpdateSound(Sound sound, const void *data, int numSamples)
{
ALint sampleRate, sampleSize, channels;
alGetBufferi(sound.buffer, AL_FREQUENCY, &sampleRate);
@ -604,7 +492,7 @@ void WaveFormat(Wave *wave, int sampleRate, int sampleSize, int channels)
// Copy a wave to a new wave
Wave WaveCopy(Wave wave)
{
Wave newWave;
Wave newWave = { 0 };
if (wave.sampleSize == 8) newWave.data = (unsigned char *)malloc(wave.sampleCount*wave.channels*sizeof(unsigned char));
else if (wave.sampleSize == 16) newWave.data = (short *)malloc(wave.sampleCount*wave.channels*sizeof(short));
@ -822,8 +710,8 @@ void UpdateMusicStream(Music music)
if (processed > 0)
{
bool active = true;
short pcm[AUDIO_BUFFER_SIZE];
float pcmf[AUDIO_BUFFER_SIZE];
short pcm[AUDIO_BUFFER_SIZE]; // TODO: Dynamic allocation (uses more than 16KB of stack)
float pcmf[AUDIO_BUFFER_SIZE]; // TODO: Dynamic allocation (uses more than 16KB of stack)
int numBuffersToProcess = processed;
int numSamples = 0; // Total size of data steamed in L+R samples for xm floats,
@ -952,7 +840,7 @@ float GetMusicTimePlayed(Music music)
float secondsPlayed = 0.0f;
unsigned int samplesPlayed = music->totalSamples - music->samplesLeft;
secondsPlayed = (float)samplesPlayed/(music->stream.sampleRate*music->stream.channels);
secondsPlayed = (float)(samplesPlayed/(music->stream.sampleRate*music->stream.channels));
return secondsPlayed;
}
@ -1004,17 +892,17 @@ AudioStream InitAudioStream(unsigned int sampleRate, unsigned int sampleSize, un
{
if (stream.sampleSize == 8)
{
unsigned char pcm[AUDIO_BUFFER_SIZE] = { 0 };
unsigned char pcm[AUDIO_BUFFER_SIZE] = { 0 }; // TODO: Dynamic allocation (uses more than 16KB of stack)
alBufferData(stream.buffers[i], stream.format, pcm, AUDIO_BUFFER_SIZE*sizeof(unsigned char), stream.sampleRate);
}
else if (stream.sampleSize == 16)
{
short pcm[AUDIO_BUFFER_SIZE] = { 0 };
short pcm[AUDIO_BUFFER_SIZE] = { 0 }; // TODO: Dynamic allocation (uses more than 16KB of stack)
alBufferData(stream.buffers[i], stream.format, pcm, AUDIO_BUFFER_SIZE*sizeof(short), stream.sampleRate);
}
else if (stream.sampleSize == 32)
{
float pcm[AUDIO_BUFFER_SIZE] = { 0.0f };
float pcm[AUDIO_BUFFER_SIZE] = { 0.0f }; // TODO: Dynamic allocation (uses more than 16KB of stack)
alBufferData(stream.buffers[i], stream.format, pcm, AUDIO_BUFFER_SIZE*sizeof(float), stream.sampleRate);
}
}
@ -1195,12 +1083,14 @@ static Wave LoadWAV(const char *fileName)
// Read in the sound data into the soundData variable
fread(wave.data, waveData.subChunkSize, 1, wavFile);
// Now we set the variables that we need later
wave.sampleCount = waveData.subChunkSize;
// Store wave parameters
wave.sampleRate = waveFormat.sampleRate;
wave.sampleSize = waveFormat.bitsPerSample;
wave.channels = waveFormat.numChannels;
// NOTE: subChunkSize comes in bytes, we need to translate it to number of samples
wave.sampleCount = waveData.subChunkSize/(waveFormat.bitsPerSample/8);
TraceLog(INFO, "[%s] WAV file loaded successfully (SampleRate: %i, SampleSize: %i, Channels: %i)", fileName, wave.sampleRate, wave.sampleSize, wave.channels);
}
}

View File

@ -115,7 +115,7 @@ Wave LoadWaveEx(float *data, int sampleCount, int sampleRate, int sampleSize, in
Sound LoadSound(const char *fileName); // Load sound to memory
Sound LoadSoundFromWave(Wave wave); // Load sound to memory from wave data
Sound LoadSoundFromRES(const char *rresName, int resId); // Load sound to memory from rRES file (raylib Resource)
void UpdateSound(Sound sound, void *data, int numSamples); // Update sound buffer with new data
void UpdateSound(Sound sound, const void *data, int numSamples); // Update sound buffer with new data
void UnloadWave(Wave wave); // Unload wave data
void UnloadSound(Sound sound); // Unload sound
void PlaySound(Sound sound); // Play a sound

View File

@ -223,15 +223,15 @@ void SetCameraMode(Camera camera, int mode)
float dy = v2.y - v1.y;
float dz = v2.z - v1.z;
cameraTargetDistance = sqrt(dx*dx + dy*dy + dz*dz);
cameraTargetDistance = sqrtf(dx*dx + dy*dy + dz*dz);
Vector2 distance = { 0.0f, 0.0f };
distance.x = sqrt(dx*dx + dz*dz);
distance.y = sqrt(dx*dx + dy*dy);
distance.x = sqrtf(dx*dx + dz*dz);
distance.y = sqrtf(dx*dx + dy*dy);
// Camera angle calculation
cameraAngle.x = asin(fabs(dx)/distance.x); // Camera angle in plane XZ (0 aligned with Z, move positive CCW)
cameraAngle.y = -asin(fabs(dy)/distance.y); // Camera angle in plane XY (0 aligned with X, move positive CW)
cameraAngle.x = asinf(fabsf(dx)/distance.x); // Camera angle in plane XZ (0 aligned with Z, move positive CCW)
cameraAngle.y = -asinf(fabsf(dy)/distance.y); // Camera angle in plane XY (0 aligned with X, move positive CW)
// NOTE: Just testing what cameraAngle means
//cameraAngle.x = 0.0f*DEG2RAD; // Camera angle in plane XZ (0 aligned with Z, move positive CCW)
@ -285,10 +285,10 @@ void UpdateCamera(Camera *camera)
{
HideCursor();
if (mousePosition.x < screenHeight/3) SetMousePosition((Vector2){ screenWidth - screenHeight/3, mousePosition.y });
else if (mousePosition.y < screenHeight/3) SetMousePosition((Vector2){ mousePosition.x, screenHeight - screenHeight/3 });
else if (mousePosition.x > (screenWidth - screenHeight/3)) SetMousePosition((Vector2){ screenHeight/3, mousePosition.y });
else if (mousePosition.y > (screenHeight - screenHeight/3)) SetMousePosition((Vector2){ mousePosition.x, screenHeight/3 });
if (mousePosition.x < (float)screenHeight/3.0f) SetMousePosition((Vector2){ screenWidth - screenHeight/3, mousePosition.y });
else if (mousePosition.y < (float)screenHeight/3.0f) SetMousePosition((Vector2){ mousePosition.x, screenHeight - screenHeight/3 });
else if (mousePosition.x > (screenWidth - (float)screenHeight/3.0f)) SetMousePosition((Vector2){ screenHeight/3, mousePosition.y });
else if (mousePosition.y > (screenHeight - (float)screenHeight/3.0f)) SetMousePosition((Vector2){ mousePosition.x, screenHeight/3 });
else
{
mousePositionDelta.x = mousePosition.x - previousMousePosition.x;
@ -321,6 +321,7 @@ void UpdateCamera(Camera *camera)
if (cameraTargetDistance > CAMERA_FREE_DISTANCE_MAX_CLAMP) cameraTargetDistance = CAMERA_FREE_DISTANCE_MAX_CLAMP;
}
// Camera looking down
// TODO: Review, weird comparisson of cameraTargetDistance == 120.0f?
else if ((camera->position.y > camera->target.y) && (cameraTargetDistance == CAMERA_FREE_DISTANCE_MAX_CLAMP) && (mouseWheelMove < 0))
{
camera->target.x += mouseWheelMove*(camera->target.x - camera->position.x)*CAMERA_MOUSE_SCROLL_SENSITIVITY/cameraTargetDistance;
@ -341,6 +342,7 @@ void UpdateCamera(Camera *camera)
if (cameraTargetDistance < CAMERA_FREE_DISTANCE_MIN_CLAMP) cameraTargetDistance = CAMERA_FREE_DISTANCE_MIN_CLAMP;
}
// Camera looking up
// TODO: Review, weird comparisson of cameraTargetDistance == 120.0f?
else if ((camera->position.y < camera->target.y) && (cameraTargetDistance == CAMERA_FREE_DISTANCE_MAX_CLAMP) && (mouseWheelMove < 0))
{
camera->target.x += mouseWheelMove*(camera->target.x - camera->position.x)*CAMERA_MOUSE_SCROLL_SENSITIVITY/cameraTargetDistance;
@ -385,9 +387,9 @@ void UpdateCamera(Camera *camera)
else
{
// Camera panning
camera->target.x += ((mousePositionDelta.x*-CAMERA_FREE_MOUSE_SENSITIVITY)*cos(cameraAngle.x) + (mousePositionDelta.y*CAMERA_FREE_MOUSE_SENSITIVITY)*sin(cameraAngle.x)*sin(cameraAngle.y))*(cameraTargetDistance/CAMERA_FREE_PANNING_DIVIDER);
camera->target.y += ((mousePositionDelta.y*CAMERA_FREE_MOUSE_SENSITIVITY)*cos(cameraAngle.y))*(cameraTargetDistance/CAMERA_FREE_PANNING_DIVIDER);
camera->target.z += ((mousePositionDelta.x*CAMERA_FREE_MOUSE_SENSITIVITY)*sin(cameraAngle.x) + (mousePositionDelta.y*CAMERA_FREE_MOUSE_SENSITIVITY)*cos(cameraAngle.x)*sin(cameraAngle.y))*(cameraTargetDistance/CAMERA_FREE_PANNING_DIVIDER);
camera->target.x += ((mousePositionDelta.x*-CAMERA_FREE_MOUSE_SENSITIVITY)*cosf(cameraAngle.x) + (mousePositionDelta.y*CAMERA_FREE_MOUSE_SENSITIVITY)*sinf(cameraAngle.x)*sinf(cameraAngle.y))*(cameraTargetDistance/CAMERA_FREE_PANNING_DIVIDER);
camera->target.y += ((mousePositionDelta.y*CAMERA_FREE_MOUSE_SENSITIVITY)*cosf(cameraAngle.y))*(cameraTargetDistance/CAMERA_FREE_PANNING_DIVIDER);
camera->target.z += ((mousePositionDelta.x*CAMERA_FREE_MOUSE_SENSITIVITY)*sinf(cameraAngle.x) + (mousePositionDelta.y*CAMERA_FREE_MOUSE_SENSITIVITY)*cosf(cameraAngle.x)*sinf(cameraAngle.y))*(cameraTargetDistance/CAMERA_FREE_PANNING_DIVIDER);
}
}
@ -404,19 +406,19 @@ void UpdateCamera(Camera *camera)
case CAMERA_FIRST_PERSON:
case CAMERA_THIRD_PERSON:
{
camera->position.x += (sin(cameraAngle.x)*direction[MOVE_BACK] -
sin(cameraAngle.x)*direction[MOVE_FRONT] -
cos(cameraAngle.x)*direction[MOVE_LEFT] +
cos(cameraAngle.x)*direction[MOVE_RIGHT])/PLAYER_MOVEMENT_SENSITIVITY;
camera->position.x += (sinf(cameraAngle.x)*direction[MOVE_BACK] -
sinf(cameraAngle.x)*direction[MOVE_FRONT] -
cosf(cameraAngle.x)*direction[MOVE_LEFT] +
cosf(cameraAngle.x)*direction[MOVE_RIGHT])/PLAYER_MOVEMENT_SENSITIVITY;
camera->position.y += (sin(cameraAngle.y)*direction[MOVE_FRONT] -
sin(cameraAngle.y)*direction[MOVE_BACK] +
camera->position.y += (sinf(cameraAngle.y)*direction[MOVE_FRONT] -
sinf(cameraAngle.y)*direction[MOVE_BACK] +
1.0f*direction[MOVE_UP] - 1.0f*direction[MOVE_DOWN])/PLAYER_MOVEMENT_SENSITIVITY;
camera->position.z += (cos(cameraAngle.x)*direction[MOVE_BACK] -
cos(cameraAngle.x)*direction[MOVE_FRONT] +
sin(cameraAngle.x)*direction[MOVE_LEFT] -
sin(cameraAngle.x)*direction[MOVE_RIGHT])/PLAYER_MOVEMENT_SENSITIVITY;
camera->position.z += (cosf(cameraAngle.x)*direction[MOVE_BACK] -
cosf(cameraAngle.x)*direction[MOVE_FRONT] +
sinf(cameraAngle.x)*direction[MOVE_LEFT] -
sinf(cameraAngle.x)*direction[MOVE_RIGHT])/PLAYER_MOVEMENT_SENSITIVITY;
bool isMoving = false; // Required for swinging
@ -439,9 +441,9 @@ void UpdateCamera(Camera *camera)
if (cameraTargetDistance < CAMERA_THIRD_PERSON_DISTANCE_CLAMP) cameraTargetDistance = CAMERA_THIRD_PERSON_DISTANCE_CLAMP;
// Camera is always looking at player
camera->target.x = camera->position.x + CAMERA_THIRD_PERSON_OFFSET.x*cos(cameraAngle.x) + CAMERA_THIRD_PERSON_OFFSET.z*sin(cameraAngle.x);
camera->target.x = camera->position.x + CAMERA_THIRD_PERSON_OFFSET.x*cosf(cameraAngle.x) + CAMERA_THIRD_PERSON_OFFSET.z*sinf(cameraAngle.x);
camera->target.y = camera->position.y + CAMERA_THIRD_PERSON_OFFSET.y;
camera->target.z = camera->position.z + CAMERA_THIRD_PERSON_OFFSET.z*sin(cameraAngle.x) - CAMERA_THIRD_PERSON_OFFSET.x*sin(cameraAngle.x);
camera->target.z = camera->position.z + CAMERA_THIRD_PERSON_OFFSET.z*sinf(cameraAngle.x) - CAMERA_THIRD_PERSON_OFFSET.x*sinf(cameraAngle.x);
}
else // CAMERA_FIRST_PERSON
{
@ -450,18 +452,18 @@ void UpdateCamera(Camera *camera)
else if (cameraAngle.y < CAMERA_FIRST_PERSON_MAX_CLAMP*DEG2RAD) cameraAngle.y = CAMERA_FIRST_PERSON_MAX_CLAMP*DEG2RAD;
// Camera is always looking at player
camera->target.x = camera->position.x - sin(cameraAngle.x)*CAMERA_FIRST_PERSON_FOCUS_DISTANCE;
camera->target.y = camera->position.y + sin(cameraAngle.y)*CAMERA_FIRST_PERSON_FOCUS_DISTANCE;
camera->target.z = camera->position.z - cos(cameraAngle.x)*CAMERA_FIRST_PERSON_FOCUS_DISTANCE;
camera->target.x = camera->position.x - sinf(cameraAngle.x)*CAMERA_FIRST_PERSON_FOCUS_DISTANCE;
camera->target.y = camera->position.y + sinf(cameraAngle.y)*CAMERA_FIRST_PERSON_FOCUS_DISTANCE;
camera->target.z = camera->position.z - cosf(cameraAngle.x)*CAMERA_FIRST_PERSON_FOCUS_DISTANCE;
if (isMoving) swingCounter++;
// Camera position update
// NOTE: On CAMERA_FIRST_PERSON player Y-movement is limited to player 'eyes position'
camera->position.y = playerEyesPosition - sin(swingCounter/CAMERA_FIRST_PERSON_STEP_TRIGONOMETRIC_DIVIDER)/CAMERA_FIRST_PERSON_STEP_DIVIDER;
camera->position.y = playerEyesPosition - sinf(swingCounter/CAMERA_FIRST_PERSON_STEP_TRIGONOMETRIC_DIVIDER)/CAMERA_FIRST_PERSON_STEP_DIVIDER;
camera->up.x = sin(swingCounter/(CAMERA_FIRST_PERSON_STEP_TRIGONOMETRIC_DIVIDER*2))/CAMERA_FIRST_PERSON_WAVING_DIVIDER;
camera->up.z = -sin(swingCounter/(CAMERA_FIRST_PERSON_STEP_TRIGONOMETRIC_DIVIDER*2))/CAMERA_FIRST_PERSON_WAVING_DIVIDER;
camera->up.x = sinf(swingCounter/(CAMERA_FIRST_PERSON_STEP_TRIGONOMETRIC_DIVIDER*2))/CAMERA_FIRST_PERSON_WAVING_DIVIDER;
camera->up.z = -sinf(swingCounter/(CAMERA_FIRST_PERSON_STEP_TRIGONOMETRIC_DIVIDER*2))/CAMERA_FIRST_PERSON_WAVING_DIVIDER;
}
} break;
default: break;
@ -473,10 +475,10 @@ void UpdateCamera(Camera *camera)
(cameraMode == CAMERA_THIRD_PERSON))
{
// TODO: It seems camera->position is not correctly updated or some rounding issue makes the camera move straight to camera->target...
camera->position.x = sin(cameraAngle.x)*cameraTargetDistance*cos(cameraAngle.y) + camera->target.x;
if (cameraAngle.y <= 0.0f) camera->position.y = sin(cameraAngle.y)*cameraTargetDistance*sin(cameraAngle.y) + camera->target.y;
else camera->position.y = -sin(cameraAngle.y)*cameraTargetDistance*sin(cameraAngle.y) + camera->target.y;
camera->position.z = cos(cameraAngle.x)*cameraTargetDistance*cos(cameraAngle.y) + camera->target.z;
camera->position.x = sinf(cameraAngle.x)*cameraTargetDistance*cosf(cameraAngle.y) + camera->target.x;
if (cameraAngle.y <= 0.0f) camera->position.y = sinf(cameraAngle.y)*cameraTargetDistance*sinf(cameraAngle.y) + camera->target.y;
else camera->position.y = -sinf(cameraAngle.y)*cameraTargetDistance*sinf(cameraAngle.y) + camera->target.y;
camera->position.z = cosf(cameraAngle.x)*cameraTargetDistance*cosf(cameraAngle.y) + camera->target.z;
}
}

View File

@ -42,13 +42,14 @@
*
**********************************************************************************************/
#include "raylib.h" // raylib main header
#include "raylib.h"
#include "rlgl.h" // raylib OpenGL abstraction layer to OpenGL 1.1, 3.3+ or ES2
#include "utils.h" // Includes Android fopen map, InitAssetManager(), TraceLog()
#include "utils.h" // Required for: fopen() Android mapping, TraceLog()
#define RAYMATH_IMPLEMENTATION // Use raymath as a header-only library (includes implementation)
#define RAYMATH_EXTERN_INLINE // Compile raymath functions as static inline (remember, it's a compiler hint)
#include "raymath.h" // Required for Vector3 and Matrix functions
#include "raymath.h" // Required for: Vector3 and Matrix functions
#define GESTURES_IMPLEMENTATION
#include "gestures.h" // Gestures detection functionality
@ -264,6 +265,7 @@ static void SwapBuffers(void); // Copy back buffer to f
static void LogoAnimation(void); // Plays raylib logo appearing animation
#if defined(PLATFORM_DESKTOP) || defined(PLATFORM_RPI)
static void TakeScreenshot(void); // Takes a screenshot and saves it in the same folder as executable
static void SetupViewport(void);
#endif
#if defined(PLATFORM_DESKTOP) || defined(PLATFORM_WEB)
@ -744,8 +746,7 @@ void EndTextureMode(void)
rlDisableRenderTexture(); // Disable render target
// Set viewport to default framebuffer size (screen size)
// TODO: consider possible viewport offsets
rlViewport(0, 0, GetScreenWidth(), GetScreenHeight());
SetupViewport();
rlMatrixMode(RL_PROJECTION); // Switch to PROJECTION matrix
rlLoadIdentity(); // Reset current matrix (PROJECTION)
@ -779,7 +780,7 @@ float GetFrameTime(void)
// As we are operate quite a lot with frameTime,
// it could be no stable, so we round it before passing it around
// NOTE: There are still problems with high framerates (>500fps)
double roundedFrameTime = round(frameTime*10000)/10000.0;
double roundedFrameTime = round(frameTime*10000)/10000.0;
return (float)roundedFrameTime; // Time in seconds to run a frame
}
@ -1089,7 +1090,7 @@ Vector2 GetWorldToScreen(Vector3 position, Camera camera)
QuaternionTransform(&worldPos, matProj);
// Calculate normalized device coordinates (inverted y)
Vector3 ndcPos = { worldPos.x/worldPos.w, -worldPos.y/worldPos.w, worldPos.z/worldPos.z };
Vector3 ndcPos = { worldPos.x/worldPos.w, -worldPos.y/worldPos.w, worldPos.z/worldPos.w };
// Calculate 2d screen position vector
Vector2 screenPosition = { (ndcPos.x + 1.0f)/2.0f*(float)GetScreenWidth(), (ndcPos.y + 1.0f)/2.0f*(float)GetScreenHeight() };
@ -1776,19 +1777,8 @@ static void InitGraphicsDevice(int width, int height)
// NOTE: screenWidth and screenHeight not used, just stored as globals
rlglInit(screenWidth, screenHeight);
#ifdef __APPLE__
// Get framebuffer size of current window
// NOTE: Required to handle HighDPI display correctly on OSX because framebuffer
// is automatically reasized to adapt to new DPI.
// When OS does that, it can be detected using GLFW3 callback: glfwSetFramebufferSizeCallback()
int fbWidth, fbHeight;
glfwGetFramebufferSize(window, &fbWidth, &fbHeight);
rlViewport(renderOffsetX/2, renderOffsetY/2, fbWidth - renderOffsetX, fbHeight - renderOffsetY);
#else
// Initialize screen viewport (area of the screen that you will actually draw to)
// NOTE: Viewport must be recalculated if screen is resized
rlViewport(renderOffsetX/2, renderOffsetY/2, renderWidth - renderOffsetX, renderHeight - renderOffsetY);
#endif
// Setup default viewport
SetupViewport();
// Initialize internal projection and modelview matrices
// NOTE: Default to orthographic projection mode with top-left corner at (0,0)
@ -1805,6 +1795,23 @@ static void InitGraphicsDevice(int width, int height)
#endif
}
static void SetupViewport(void)
{
#ifdef __APPLE__
// Get framebuffer size of current window
// NOTE: Required to handle HighDPI display correctly on OSX because framebuffer
// is automatically reasized to adapt to new DPI.
// When OS does that, it can be detected using GLFW3 callback: glfwSetFramebufferSizeCallback()
int fbWidth, fbHeight;
glfwGetFramebufferSize(window, &fbWidth, &fbHeight);
rlViewport(renderOffsetX/2, renderOffsetY/2, fbWidth - renderOffsetX, fbHeight - renderOffsetY);
#else
// Initialize screen viewport (area of the screen that you will actually draw to)
// NOTE: Viewport must be recalculated if screen is resized
rlViewport(renderOffsetX/2, renderOffsetY/2, renderWidth - renderOffsetX, renderHeight - renderOffsetY);
#endif
}
// Compute framebuffer size relative to screen size and display size
// NOTE: Global variables renderWidth/renderHeight and renderOffsetX/renderOffsetY can be modified
static void SetupFramebufferSize(int displayWidth, int displayHeight)

View File

@ -179,7 +179,7 @@ static int tapCounter = 0; // TAP counter (one tap implies
// Hold gesture variables
static bool resetHold = false; // HOLD reset to get first touch point again
static float timeHold = 0.0f; // HOLD duration in milliseconds
static double timeHold = 0.0f; // HOLD duration in milliseconds
// Drag gesture variables
static Vector2 dragVector = { 0.0f , 0.0f }; // DRAG vector (between initial and current position)
@ -423,11 +423,11 @@ float GetGestureHoldDuration(void)
{
// NOTE: time is calculated on current gesture HOLD
float time = 0.0f;
double time = 0.0;
if (currentGesture == GESTURE_HOLD) time = (float)GetCurrentTime() - timeHold;
if (currentGesture == GESTURE_HOLD) time = GetCurrentTime() - timeHold;
return time;
return (float)time;
}
// Get drag vector (between initial touch point to current)
@ -474,7 +474,7 @@ static float Vector2Angle(Vector2 initialPosition, Vector2 finalPosition)
{
float angle;
angle = atan2(finalPosition.y - initialPosition.y, finalPosition.x - initialPosition.x)*(180.0f/PI);
angle = atan2f(finalPosition.y - initialPosition.y, finalPosition.x - initialPosition.x)*(180.0f/PI);
if (angle < 0) angle += 360.0f;
@ -489,7 +489,7 @@ static float Vector2Distance(Vector2 v1, Vector2 v2)
float dx = v2.x - v1.x;
float dy = v2.y - v1.y;
result = sqrt(dx*dx + dy*dy);
result = (float)sqrt(dx*dx + dy*dy);
return result;
}

View File

@ -648,89 +648,6 @@ Model LoadModelEx(Mesh data, bool dynamic)
return model;
}
// Load a 3d model from rRES file (raylib Resource)
Model LoadModelFromRES(const char *rresName, int resId)
{
Model model = { 0 };
bool found = false;
char id[4]; // rRES file identifier
unsigned char version; // rRES file version and subversion
char useless; // rRES header reserved data
short numRes;
ResInfoHeader infoHeader;
FILE *rresFile = fopen(rresName, "rb");
if (rresFile == NULL)
{
TraceLog(WARNING, "[%s] rRES raylib resource file could not be opened", rresName);
}
else
{
// Read rres file (basic file check - id)
fread(&id[0], sizeof(char), 1, rresFile);
fread(&id[1], sizeof(char), 1, rresFile);
fread(&id[2], sizeof(char), 1, rresFile);
fread(&id[3], sizeof(char), 1, rresFile);
fread(&version, sizeof(char), 1, rresFile);
fread(&useless, sizeof(char), 1, rresFile);
if ((id[0] != 'r') && (id[1] != 'R') && (id[2] != 'E') &&(id[3] != 'S'))
{
TraceLog(WARNING, "[%s] This is not a valid raylib resource file", rresName);
}
else
{
// Read number of resources embedded
fread(&numRes, sizeof(short), 1, rresFile);
for (int i = 0; i < numRes; i++)
{
fread(&infoHeader, sizeof(ResInfoHeader), 1, rresFile);
if (infoHeader.id == resId)
{
found = true;
// Check data is of valid MODEL type
if (infoHeader.type == 8)
{
// TODO: Load model data
}
else
{
TraceLog(WARNING, "[%s] Required resource do not seem to be a valid MODEL resource", rresName);
}
}
else
{
// Depending on type, skip the right amount of parameters
switch (infoHeader.type)
{
case 0: fseek(rresFile, 6, SEEK_CUR); break; // IMAGE: Jump 6 bytes of parameters
case 1: fseek(rresFile, 6, SEEK_CUR); break; // SOUND: Jump 6 bytes of parameters
case 2: fseek(rresFile, 5, SEEK_CUR); break; // MODEL: Jump 5 bytes of parameters (TODO: Review)
case 3: break; // TEXT: No parameters
case 4: break; // RAW: No parameters
default: break;
}
// Jump DATA to read next infoHeader
fseek(rresFile, infoHeader.size, SEEK_CUR);
}
}
}
fclose(rresFile);
}
if (!found) TraceLog(WARNING, "[%s] Required resource id [%i] could not be found in the raylib resource file", rresName, resId);
return model;
}
// Load a heightmap image as a 3d model
// NOTE: model map size is defined in generic units
Model LoadHeightmap(Image heightmap, Vector3 size)
@ -1517,8 +1434,8 @@ bool CheckCollisionRayBox(Ray ray, BoundingBox box)
t[3] = (box.max.y - ray.position.y)/ray.direction.y;
t[4] = (box.min.z - ray.position.z)/ray.direction.z;
t[5] = (box.max.z - ray.position.z)/ray.direction.z;
t[6] = fmax(fmax(fmin(t[0], t[1]), fmin(t[2], t[3])), fmin(t[4], t[5]));
t[7] = fmin(fmin(fmax(t[0], t[1]), fmax(t[2], t[3])), fmax(t[4], t[5]));
t[6] = (float)fmax(fmax(fmin(t[0], t[1]), fmin(t[2], t[3])), fmin(t[4], t[5]));
t[7] = (float)fmin(fmin(fmax(t[0], t[1]), fmax(t[2], t[3])), fmax(t[4], t[5]));
collision = !(t[7] < 0 || t[6] > t[7]);

View File

@ -239,9 +239,10 @@ PHYSACDEF void ClosePhysics(void);
// Functions required to query time on Windows
int __stdcall QueryPerformanceCounter(unsigned long long int *lpPerformanceCount);
int __stdcall QueryPerformanceFrequency(unsigned long long int *lpFrequency);
#elif defined(__linux)
#elif defined(__linux) || defined(PLATFORM_WEB)
#include <sys/time.h> // Required for: timespec
#include <time.h> // Required for: clock_gettime()
#include <stdint.h>
#endif
//----------------------------------------------------------------------------------
@ -266,7 +267,7 @@ PHYSACDEF void ClosePhysics(void);
static unsigned int usedMemory = 0; // Total allocated dynamic memory
static bool physicsThreadEnabled = false; // Physics thread enabled state
static double currentTime = 0; // Current time in milliseconds
#if defined(PLATFORM_ANDROID) || defined(PLATFORM_RPI)
#if defined(PLATFORM_ANDROID) || defined(PLATFORM_RPI) || defined(__linux) || defined(PLATFORM_WEB)
static double baseTime = 0; // Android and RPI platforms base time
#endif
static double startTime = 0; // Start time in milliseconds
@ -1942,7 +1943,7 @@ static double GetCurrentTime(void)
{
double time = 0;
#if defined(PLATFORM_DESKTOP) || defined(PLATFORM_WEB)
#if defined(_WIN32)
unsigned long long int clockFrequency, currentTime;
QueryPerformanceFrequency(&clockFrequency);
@ -1951,7 +1952,7 @@ static double GetCurrentTime(void)
time = (double)((double)currentTime/clockFrequency)*1000;
#endif
#if defined(PLATFORM_ANDROID) || defined(PLATFORM_RPI)
#if defined(PLATFORM_ANDROID) || defined(PLATFORM_RPI) || defined(__linux) || defined(PLATFORM_WEB)
struct timespec ts;
clock_gettime(CLOCK_MONOTONIC, &ts);
uint64_t temp = (uint64_t)ts.tv_sec*1000000000LLU + (uint64_t)ts.tv_nsec;

View File

@ -19,7 +19,7 @@
* Multiple platforms support: Windows, Linux, Mac, Android, Raspberry Pi, HTML5 and Oculus Rift CV1
* Custom color palette for fancy visuals on raywhite background
* Minimal external dependencies (GLFW3, OpenGL, OpenAL)
* Complete binding for LUA [rlua]
* Complete binding for Lua [rlua]
*
* External libs:
* GLFW3 (www.glfw.org) for window/context management and input [core]
@ -770,10 +770,8 @@ RLAPI bool CheckCollisionPointTriangle(Vector2 point, Vector2 p1, Vector2 p2, Ve
RLAPI Image LoadImage(const char *fileName); // Load an image into CPU memory (RAM)
RLAPI Image LoadImageEx(Color *pixels, int width, int height); // Load image data from Color array data (RGBA - 32bit)
RLAPI Image LoadImageRaw(const char *fileName, int width, int height, int format, int headerSize); // Load image data from RAW file
RLAPI Image LoadImageFromRES(const char *rresName, int resId); // Load an image from rRES file (raylib Resource)
RLAPI Texture2D LoadTexture(const char *fileName); // Load an image as texture into GPU memory
RLAPI Texture2D LoadTextureEx(void *data, int width, int height, int textureFormat); // Load a texture from raw data into GPU memory
RLAPI Texture2D LoadTextureFromRES(const char *rresName, int resId); // Load an image as texture from rRES file (raylib Resource)
RLAPI Texture2D LoadTextureFromImage(Image image); // Load a texture from image data
RLAPI RenderTexture2D LoadRenderTexture(int width, int height); // Load a texture to be used for rendering
RLAPI void UnloadImage(Image image); // Unload image from CPU memory (RAM)
@ -857,7 +855,6 @@ RLAPI void DrawLight(Light light);
//------------------------------------------------------------------------------------
RLAPI Model LoadModel(const char *fileName); // Load a 3d model (.OBJ)
RLAPI Model LoadModelEx(Mesh data, bool dynamic); // Load a 3d model (from mesh data)
RLAPI Model LoadModelFromRES(const char *rresName, int resId); // Load a 3d model from rRES file (raylib Resource)
RLAPI Model LoadHeightmap(Image heightmap, Vector3 size); // Load a heightmap image as a 3d model
RLAPI Model LoadCubicmap(Image cubicmap); // Load a map image as a 3d model (cubes based)
RLAPI void UnloadModel(Model model); // Unload 3d model from memory
@ -933,8 +930,8 @@ RLAPI Wave LoadWave(const char *fileName); // Load wa
RLAPI Wave LoadWaveEx(float *data, int sampleCount, int sampleRate, int sampleSize, int channels); // Load wave data from float array data (32bit)
RLAPI Sound LoadSound(const char *fileName); // Load sound to memory
RLAPI Sound LoadSoundFromWave(Wave wave); // Load sound to memory from wave data
RLAPI void UpdateSound(Sound sound, const void *data, int numSamples);// Update sound buffer with new data
RLAPI Sound LoadSoundFromRES(const char *rresName, int resId); // Load sound to memory from rRES file (raylib Resource)
RLAPI void UpdateSound(Sound sound, void *data, int numSamples); // Update sound buffer with new data
RLAPI void UnloadWave(Wave wave); // Unload wave data
RLAPI void UnloadSound(Sound sound); // Unload sound
RLAPI void PlaySound(Sound sound); // Play a sound

View File

@ -222,16 +222,16 @@ RMDEF Vector3 VectorPerpendicular(Vector3 v)
{
Vector3 result;
float min = fabs(v.x);
float min = fabsf(v.x);
Vector3 cardinalAxis = {1.0f, 0.0f, 0.0f};
if (fabs(v.y) < min)
if (fabsf(v.y) < min)
{
min = fabs(v.y);
min = fabsf(v.y);
cardinalAxis = (Vector3){0.0f, 1.0f, 0.0f};
}
if(fabs(v.z) < min)
if(fabsf(v.z) < min)
{
cardinalAxis = (Vector3){0.0f, 0.0f, 1.0f};
}
@ -256,7 +256,7 @@ RMDEF float VectorLength(const Vector3 v)
{
float length;
length = sqrt(v.x*v.x + v.y*v.y + v.z*v.z);
length = sqrtf(v.x*v.x + v.y*v.y + v.z*v.z);
return length;
}
@ -284,7 +284,7 @@ RMDEF void VectorNormalize(Vector3 *v)
length = VectorLength(*v);
if (length == 0) length = 1.0f;
if (length == 0.0f) length = 1.0f;
ilength = 1.0f/length;
@ -302,7 +302,7 @@ RMDEF float VectorDistance(Vector3 v1, Vector3 v2)
float dy = v2.y - v1.y;
float dz = v2.z - v1.z;
result = sqrt(dx*dx + dy*dy + dz*dz);
result = sqrtf(dx*dx + dy*dy + dz*dz);
return result;
}
@ -590,7 +590,7 @@ RMDEF Matrix MatrixRotate(Vector3 axis, float angle)
float x = axis.x, y = axis.y, z = axis.z;
float length = sqrt(x*x + y*y + z*z);
float length = sqrtf(x*x + y*y + z*z);
if ((length != 1.0f) && (length != 0.0f))
{

View File

@ -318,6 +318,7 @@ static bool texCompETC1Supported = false; // ETC1 texture compression support
static bool texCompETC2Supported = false; // ETC2/EAC texture compression support
static bool texCompPVRTSupported = false; // PVR texture compression support
static bool texCompASTCSupported = false; // ASTC texture compression support
#endif
// Extension supported flag: Anisotropic filtering
static bool texAnisotropicFilterSupported = false; // Anisotropic texture filtering support
@ -325,7 +326,6 @@ static float maxAnisotropicLevel = 0.0f; // Maximum anisotropy level supp
// Extension supported flag: Clamp mirror wrap mode
static bool texClampMirrorSupported = false; // Clamp mirror wrap mode supported
#endif
#if defined(RLGL_OCULUS_SUPPORT)
// OVR device variables
@ -902,6 +902,10 @@ void rlDisableTexture(void)
#if defined(GRAPHICS_API_OPENGL_11)
glDisable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, 0);
#else
// NOTE: If quads batch limit is reached,
// we force a draw call and next batch starts
if (quads.vCounter/4 >= MAX_QUADS_BATCH) rlglDraw();
#endif
}
@ -922,11 +926,11 @@ void rlTextureParameters(unsigned int id, int param, int value)
case RL_TEXTURE_MIN_FILTER: glTexParameteri(GL_TEXTURE_2D, param, value); break;
case RL_TEXTURE_ANISOTROPIC_FILTER:
{
if (value <= maxAnisotropicLevel) glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, value);
if (value <= maxAnisotropicLevel) glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, (float)value);
else if (maxAnisotropicLevel > 0.0f)
{
TraceLog(WARNING, "[TEX ID %i] Maximum anisotropic filter level supported is %iX", id, maxAnisotropicLevel);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, value);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, (float)value);
}
else TraceLog(WARNING, "Anisotropic filtering not supported");
} break;
@ -1733,7 +1737,7 @@ void rlglGenerateMipmaps(Texture2D *texture)
{
#if defined(GRAPHICS_API_OPENGL_11)
// Compute required mipmaps
void *data = rlglReadTexturePixels(texture);
void *data = rlglReadTexturePixels(*texture);
// NOTE: data size is reallocated to fit mipmaps data
// NOTE: CPU mipmap generation only supports RGBA 32bit data
@ -1776,7 +1780,7 @@ void rlglGenerateMipmaps(Texture2D *texture)
#define MIN(a,b) (((a)<(b))?(a):(b))
#define MAX(a,b) (((a)>(b))?(a):(b))
texture->mipmaps = 1 + floor(log2(MAX(texture->width, texture->height)));
texture->mipmaps = 1 + (int)floor(log(MAX(texture->width, texture->height))/log(2));
#endif
}
else TraceLog(WARNING, "[TEX ID %i] Mipmaps can not be generated", texture->id);

View File

@ -133,6 +133,7 @@ RLUADEF void CloseLuaDevice(void); // De-initialize Lua system
#define LuaPush_AudioStream(L, aud) LuaPushOpaqueType(L, aud)
#define LuaGetArgument_string luaL_checkstring
#define LuaGetArgument_ptr (void *)luaL_checkinteger
#define LuaGetArgument_int (int)luaL_checkinteger
#define LuaGetArgument_unsigned (unsigned)luaL_checkinteger
#define LuaGetArgument_char (char)luaL_checkinteger
@ -1198,7 +1199,7 @@ int lua_GetGamepadName(lua_State* L)
// TODO: Return gamepad name id
int arg1 = LuaGetArgument_int(L, 1);
char * result = GetGamepadName(arg1);
const char * result = GetGamepadName(arg1);
//lua_pushboolean(L, result);
return 1;
}
@ -2863,7 +2864,7 @@ int lua_LoadWaveEx(lua_State* L)
{
// TODO: Wave LoadWaveEx(float *data, int sampleCount, int sampleRate, int sampleSize, int channels);
int arg1 = 0;
float * arg1 = 0;
int arg2 = LuaGetArgument_int(L, 2);
int arg3 = LuaGetArgument_int(L, 3);
int arg4 = LuaGetArgument_int(L, 4);
@ -2904,7 +2905,7 @@ int lua_UpdateSound(lua_State* L)
Sound arg1 = LuaGetArgument_Sound(L, 1);
const char * arg2 = LuaGetArgument_string(L, 2);
int * arg3 = LuaGetArgument_int(L, 3);
int arg3 = LuaGetArgument_int(L, 3);
UpdateSound(arg1, arg2, arg3);
return 0;
}

View File

@ -453,16 +453,17 @@ bool CheckCollisionCircleRec(Vector2 center, float radius, Rectangle rec)
int recCenterX = rec.x + rec.width/2;
int recCenterY = rec.y + rec.height/2;
float dx = fabs(center.x - recCenterX);
float dy = fabs(center.y - recCenterY);
float dx = fabsf(center.x - recCenterX);
float dy = fabsf(center.y - recCenterY);
if (dx > (rec.width/2 + radius)) { return false; }
if (dy > (rec.height/2 + radius)) { return false; }
if (dx > ((float)rec.width/2.0f + radius)) { return false; }
if (dy > ((float)rec.height/2.0f + radius)) { return false; }
if (dx <= (rec.width/2)) { return true; }
if (dy <= (rec.height/2)) { return true; }
if (dx <= ((float)rec.width/2.0f)) { return true; }
if (dy <= ((float)rec.height/2.0f)) { return true; }
float cornerDistanceSq = (dx - rec.width/2)*(dx - rec.width/2) + (dy - rec.height/2)*(dy - rec.height/2);
float cornerDistanceSq = (dx - (float)rec.width/2.0f)*(dx - (float)rec.width/2.0f) +
(dy - (float)rec.height/2.0f)*(dy - (float)rec.height/2.0f);
return (cornerDistanceSq <= (radius*radius));
}

View File

@ -367,7 +367,7 @@ void DrawTextEx(SpriteFont spriteFont, const char *text, Vector2 position, float
if ((unsigned char)text[i] == '\n')
{
// NOTE: Fixed line spacing of 1.5 lines
textOffsetY += ((spriteFont.size + spriteFont.size/2)*scaleFactor);
textOffsetY += (int)((spriteFont.size + spriteFont.size/2)*scaleFactor);
textOffsetX = 0;
}
else
@ -394,8 +394,8 @@ void DrawTextEx(SpriteFont spriteFont, const char *text, Vector2 position, float
spriteFont.charRecs[index].width*scaleFactor,
spriteFont.charRecs[index].height*scaleFactor }, (Vector2){ 0, 0 }, 0.0f, tint);
if (spriteFont.charAdvanceX[index] == 0) textOffsetX += (spriteFont.charRecs[index].width*scaleFactor + spacing);
else textOffsetX += (spriteFont.charAdvanceX[index]*scaleFactor + spacing);
if (spriteFont.charAdvanceX[index] == 0) textOffsetX += (int)(spriteFont.charRecs[index].width*scaleFactor + spacing);
else textOffsetX += (int)(spriteFont.charAdvanceX[index]*scaleFactor + spacing);
}
}
}
@ -460,14 +460,14 @@ int MeasureText(const char *text, int fontSize)
Vector2 MeasureTextEx(SpriteFont spriteFont, const char *text, float fontSize, int spacing)
{
int len = strlen(text);
int tempLen = 0; // Used to count longer text line num chars
int tempLen = 0; // Used to count longer text line num chars
int lenCounter = 0;
int textWidth = 0;
int tempTextWidth = 0; // Used to count longer text line width
float textWidth = 0;
float tempTextWidth = 0; // Used to count longer text line width
int textHeight = spriteFont.size;
float scaleFactor = fontSize/spriteFont.size;
float textHeight = (float)spriteFont.size;
float scaleFactor = fontSize/(float)spriteFont.size;
for (int i = 0; i < len; i++)
{
@ -485,7 +485,7 @@ Vector2 MeasureTextEx(SpriteFont spriteFont, const char *text, float fontSize, i
if (tempTextWidth < textWidth) tempTextWidth = textWidth;
lenCounter = 0;
textWidth = 0;
textHeight += (spriteFont.size + spriteFont.size/2); // NOTE: Fixed line spacing of 1.5 lines
textHeight += ((float)spriteFont.size*1.5f); // NOTE: Fixed line spacing of 1.5 lines
}
if (tempLen < lenCounter) tempLen = lenCounter;
@ -494,8 +494,8 @@ Vector2 MeasureTextEx(SpriteFont spriteFont, const char *text, float fontSize, i
if (tempTextWidth < textWidth) tempTextWidth = textWidth;
Vector2 vec;
vec.x = (float)tempTextWidth*scaleFactor + (tempLen - 1)*spacing; // Adds chars spacing to measure
vec.y = (float)textHeight*scaleFactor;
vec.x = tempTextWidth*scaleFactor + (float)((tempLen - 1)*spacing); // Adds chars spacing to measure
vec.y = textHeight*scaleFactor;
return vec;
}
@ -504,10 +504,8 @@ Vector2 MeasureTextEx(SpriteFont spriteFont, const char *text, float fontSize, i
// NOTE: Uses default font
void DrawFPS(int posX, int posY)
{
char buffer[20];
// NOTE: We are rendering fps every second for better viewing on high framerates
// TODO: Not working properly on ANDROID and RPI
// TODO: Not working properly on ANDROID and RPI (for high framerates)
static float fps = 0.0f;
static int counter = 0;
@ -520,12 +518,11 @@ void DrawFPS(int posX, int posY)
else
{
fps = GetFPS();
refreshRate = fps;
refreshRate = (int)fps;
counter = 0;
}
sprintf(buffer, "%2.0f FPS", fps);
DrawText(buffer, posX, posY, 20, LIME);
DrawText(FormatText("%2.0f FPS", fps), posX, posY, 20, LIME);
}
//----------------------------------------------------------------------------------

View File

@ -37,11 +37,10 @@
#include <string.h> // Required for: strcmp(), strrchr(), strncmp()
#include "rlgl.h" // raylib OpenGL abstraction layer to OpenGL 1.1, 3.3 or ES2
// Required: rlglLoadTexture() rlDeleteTextures(),
// rlglGenerateMipmaps(), some funcs for DrawTexturePro()
// Required for: rlglLoadTexture() rlDeleteTextures(),
// rlglGenerateMipmaps(), some funcs for DrawTexturePro()
#include "utils.h" // rRES data decompression utility function
// NOTE: Includes Android fopen function map
#include "utils.h" // Required for: fopen() Android mapping, TraceLog()
// Support only desired texture formats, by default: JPEG, PNG, BMP, TGA
//#define STBI_NO_JPEG // Image format .jpg and .jpeg
@ -216,7 +215,7 @@ Image LoadImageRaw(const char *fileName, int width, int height, int format, int
fread(image.data, size, 1, rawFile);
// TODO: Check if data have been read
// TODO: Check if data has been read
image.width = width;
image.height = height;
@ -229,118 +228,6 @@ Image LoadImageRaw(const char *fileName, int width, int height, int format, int
return image;
}
// Load an image from rRES file (raylib Resource)
// TODO: Review function to support multiple color modes
Image LoadImageFromRES(const char *rresName, int resId)
{
Image image = { 0 };
bool found = false;
char id[4]; // rRES file identifier
unsigned char version; // rRES file version and subversion
char useless; // rRES header reserved data
short numRes;
ResInfoHeader infoHeader;
FILE *rresFile = fopen(rresName, "rb");
if (rresFile == NULL)
{
TraceLog(WARNING, "[%s] rRES raylib resource file could not be opened", rresName);
}
else
{
// Read rres file (basic file check - id)
fread(&id[0], sizeof(char), 1, rresFile);
fread(&id[1], sizeof(char), 1, rresFile);
fread(&id[2], sizeof(char), 1, rresFile);
fread(&id[3], sizeof(char), 1, rresFile);
fread(&version, sizeof(char), 1, rresFile);
fread(&useless, sizeof(char), 1, rresFile);
if ((id[0] != 'r') && (id[1] != 'R') && (id[2] != 'E') &&(id[3] != 'S'))
{
TraceLog(WARNING, "[%s] This is not a valid raylib resource file", rresName);
}
else
{
// Read number of resources embedded
fread(&numRes, sizeof(short), 1, rresFile);
for (int i = 0; i < numRes; i++)
{
fread(&infoHeader, sizeof(ResInfoHeader), 1, rresFile);
if (infoHeader.id == resId)
{
found = true;
// Check data is of valid IMAGE type
if (infoHeader.type == 0) // IMAGE data type
{
// TODO: Check data compression type
// NOTE: We suppose compression type 2 (DEFLATE - default)
short imgWidth, imgHeight;
char colorFormat, mipmaps;
fread(&imgWidth, sizeof(short), 1, rresFile); // Image width
fread(&imgHeight, sizeof(short), 1, rresFile); // Image height
fread(&colorFormat, 1, 1, rresFile); // Image data color format (default: RGBA 32 bit)
fread(&mipmaps, 1, 1, rresFile); // Mipmap images included (default: 0)
image.width = (int)imgWidth;
image.height = (int)imgHeight;
unsigned char *compData = malloc(infoHeader.size);
fread(compData, infoHeader.size, 1, rresFile);
unsigned char *imgData = DecompressData(compData, infoHeader.size, infoHeader.srcSize);
// TODO: Review color mode
//image.data = (unsigned char *)malloc(sizeof(unsigned char)*imgWidth*imgHeight*4);
image.data = imgData;
//free(imgData);
free(compData);
TraceLog(INFO, "[%s] Image loaded successfully from resource, size: %ix%i", rresName, image.width, image.height);
}
else
{
TraceLog(WARNING, "[%s] Required resource do not seem to be a valid IMAGE resource", rresName);
}
}
else
{
// Depending on type, skip the right amount of parameters
switch (infoHeader.type)
{
case 0: fseek(rresFile, 6, SEEK_CUR); break; // IMAGE: Jump 6 bytes of parameters
case 1: fseek(rresFile, 6, SEEK_CUR); break; // SOUND: Jump 6 bytes of parameters
case 2: fseek(rresFile, 5, SEEK_CUR); break; // MODEL: Jump 5 bytes of parameters (TODO: Review)
case 3: break; // TEXT: No parameters
case 4: break; // RAW: No parameters
default: break;
}
// Jump DATA to read next infoHeader
fseek(rresFile, infoHeader.size, SEEK_CUR);
}
}
}
fclose(rresFile);
}
if (!found) TraceLog(WARNING, "[%s] Required resource id [%i] could not be found in the raylib resource file", rresName, resId);
return image;
}
// Load an image as texture into GPU memory
Texture2D LoadTexture(const char *fileName)
{
@ -377,18 +264,6 @@ Texture2D LoadTextureEx(void *data, int width, int height, int textureFormat)
return texture;
}
// Load an image as texture from rRES file (raylib Resource)
Texture2D LoadTextureFromRES(const char *rresName, int resId)
{
Texture2D texture;
Image image = LoadImageFromRES(rresName, resId);
texture = LoadTextureFromImage(image);
UnloadImage(image);
return texture;
}
// Load a texture from image data
// NOTE: image is not unloaded, it must be done manually
Texture2D LoadTextureFromImage(Image image)
@ -1100,18 +975,18 @@ void ImageResizeNN(Image *image,int newWidth,int newHeight)
Color *output = (Color *)malloc(newWidth*newHeight*sizeof(Color));
// EDIT: added +1 to account for an early rounding problem
int x_ratio = (int)((image->width<<16)/newWidth) + 1;
int y_ratio = (int)((image->height<<16)/newHeight) + 1;
int xRatio = (int)((image->width << 16)/newWidth) + 1;
int yRatio = (int)((image->height << 16)/newHeight) + 1;
int x2, y2;
for (int i = 0; i < newHeight; i++)
for (int y = 0; y < newHeight; y++)
{
for (int j = 0; j < newWidth; j++)
for (int x = 0; x < newWidth; x++)
{
x2 = ((j*x_ratio) >> 16);
y2 = ((i*y_ratio) >> 16);
x2 = ((x*xRatio) >> 16);
y2 = ((y*yRatio) >> 16);
output[(i*newWidth) + j] = pixels[(y2*image->width) + x2] ;
output[(y*newWidth) + x] = pixels[(y2*image->width) + x2] ;
}
}
@ -1584,7 +1459,7 @@ void DrawTexturePro(Texture2D texture, Rectangle sourceRec, Rectangle destRec, V
rlEnableTexture(texture.id);
rlPushMatrix();
rlTranslatef(destRec.x, destRec.y, 0);
rlTranslatef((float)destRec.x, (float)destRec.y, 0);
rlRotatef(rotation, 0, 0, 1);
rlTranslatef(-origin.x, -origin.y, 0);
@ -1598,15 +1473,15 @@ void DrawTexturePro(Texture2D texture, Rectangle sourceRec, Rectangle destRec, V
// Bottom-right corner for texture and quad
rlTexCoord2f((float)sourceRec.x/texture.width, (float)(sourceRec.y + sourceRec.height)/texture.height);
rlVertex2f(0.0f, destRec.height);
rlVertex2f(0.0f, (float)destRec.height);
// Top-right corner for texture and quad
rlTexCoord2f((float)(sourceRec.x + sourceRec.width)/texture.width, (float)(sourceRec.y + sourceRec.height)/texture.height);
rlVertex2f(destRec.width, destRec.height);
rlVertex2f((float)destRec.width, (float)destRec.height);
// Top-left corner for texture and quad
rlTexCoord2f((float)(sourceRec.x + sourceRec.width)/texture.width, (float)sourceRec.y/texture.height);
rlVertex2f(destRec.width, 0.0f);
rlVertex2f((float)destRec.width, 0.0f);
rlEnd();
rlPopMatrix();

View File

@ -49,9 +49,6 @@
#include "external/stb_image_write.h" // Required for: stbi_write_png()
#endif
#include "external/tinfl.c" // Required for: tinfl_decompress_mem_to_mem()
// NOTE: DEFLATE algorythm data decompression
#define DO_NOT_TRACE_DEBUG_MSGS // Avoid DEBUG messages tracing
//----------------------------------------------------------------------------------
@ -75,45 +72,6 @@ static int android_close(void *cookie);
// Module Functions Definition - Utilities
//----------------------------------------------------------------------------------
// Data decompression function
// NOTE: Allocated data MUST be freed!
unsigned char *DecompressData(const unsigned char *data, unsigned long compSize, int uncompSize)
{
int tempUncompSize;
unsigned char *pUncomp;
// Allocate buffer to hold decompressed data
pUncomp = (mz_uint8 *)malloc((size_t)uncompSize);
// Check correct memory allocation
if (pUncomp == NULL)
{
TraceLog(WARNING, "Out of memory while decompressing data");
}
else
{
// Decompress data
tempUncompSize = tinfl_decompress_mem_to_mem(pUncomp, (size_t)uncompSize, data, compSize, 1);
if (tempUncompSize == -1)
{
TraceLog(WARNING, "Data decompression failed");
free(pUncomp);
}
if (uncompSize != (int)tempUncompSize)
{
TraceLog(WARNING, "Expected uncompressed size do not match, data may be corrupted");
TraceLog(WARNING, " -- Expected uncompressed size: %i", uncompSize);
TraceLog(WARNING, " -- Returned uncompressed size: %i", tempUncompSize);
}
TraceLog(INFO, "Data decompressed successfully from %u bytes to %u bytes", (mz_uint32)compSize, (mz_uint32)tempUncompSize);
}
return pUncomp;
}
#if defined(PLATFORM_DESKTOP) || defined(PLATFORM_RPI)
// Creates a bitmap (BMP) file from an array of pixel data
// NOTE: This function is not explicitly available to raylib users