Merge branch 'master' of https://github.com/Syphonx/raylib-public
This commit is contained in:
commit
0e1078c13d
28
BINDINGS.md
Normal file
28
BINDINGS.md
Normal file
|
|
@ -0,0 +1,28 @@
|
||||||
|
### raylib bindings
|
||||||
|
|
||||||
|
Some people ported raylib to other languages in form of bindings or wrappers to the library, here is a list with the ones I'm aware of:
|
||||||
|
|
||||||
|
- [raylib](https://github.com/raysan5/raylib) : raylib **C/C++** version (default)
|
||||||
|
- [raylib-lua](https://github.com/raysan5/raylib-lua) : raylib **Lua** binding
|
||||||
|
- [raylib-lua-ffi](https://github.com/raysan5/raylib/issues/693) : raylib **Lua** ffi binding
|
||||||
|
- [raylib-go](https://github.com/gen2brain/raylib-go) : raylib **Go** binding
|
||||||
|
- [raylib-Nim](https://gitlab.com/define-private-public/raylib-Nim) : raylib **Nim** binding
|
||||||
|
- [cray](https://gitlab.com/Zatherz/cray) - raylib **Crystal** binding
|
||||||
|
- [Graphics::Raylib](https://metacpan.org/pod/Graphics::Raylib) : raylib **Perl** wrapper
|
||||||
|
- [raylib-pascal](https://github.com/drezgames/raylib-pascal) - raylib **Pascal** binding
|
||||||
|
- [Raylib-cs](https://github.com/ChrisDill/Raylib-cs) : raylib **C#** binding
|
||||||
|
- [RaylibSharp](https://github.com/TheLumaio/RaylibSharp) : raylib **C#** binding
|
||||||
|
- [raylib-ruby-ffi](https://github.com/D3nX/raylib-ruby-ffi) : raylib **Ruby** binding
|
||||||
|
- [raylib-rs](https://github.com/deltaphc/raylib-rs) : raylib **Rust** binding
|
||||||
|
- [raylib-py](https://github.com/overdev/raylib-py) : raylib **Python** binding
|
||||||
|
- [raylib-haskell](https://github.com/DevJac/raylib-haskell) : raylib **Haskell** binding
|
||||||
|
- [raylib-java](https://github.com/XoanaIO/raylib-java) : raylib **Java** binding
|
||||||
|
- [raylib-chaiscript](https://github.com/RobLoach/raylib-chaiscript) : raylib **ChaiScript** binding
|
||||||
|
- [node-raylib](https://github.com/RobLoach/node-raylib) : **Node.js** raylib binding
|
||||||
|
- *[raylib flat-assembler Usage example]()*
|
||||||
|
- *[raylib COBOL Usage example](https://github.com/Martinfx/Cobol/tree/master/OpenCobol/Games/raylib)*
|
||||||
|
|
||||||
|
Usually, raylib bindings follow the convention: `raylib-{language}`
|
||||||
|
|
||||||
|
Let me know if you're writing a new binding for raylib, I will list it here and I usually
|
||||||
|
provide the icon/logo for that new language binding.
|
||||||
|
|
@ -55,35 +55,6 @@ To open new issue for raylib (bug, enhancement, discussion...), just try to foll
|
||||||
- Verify that changes don't break the build (at least on Windows platform). As many platforms where you can test it, the better, but don't worry
|
- Verify that changes don't break the build (at least on Windows platform). As many platforms where you can test it, the better, but don't worry
|
||||||
if you cannot test all the platforms.
|
if you cannot test all the platforms.
|
||||||
|
|
||||||
### raylib bindings
|
|
||||||
|
|
||||||
Some people ported raylib to other languages in form of bindings or wrappers to the library, here is a list with the ones I'm aware of:
|
|
||||||
|
|
||||||
- [raylib](https://github.com/raysan5/raylib) : raylib **C/C++** version (default)
|
|
||||||
- [raylib-lua](https://github.com/raysan5/raylib-lua) : raylib **Lua** binding
|
|
||||||
- [raylib-lua-ffi](https://github.com/raysan5/raylib/issues/693) : raylib **Lua** ffi binding
|
|
||||||
- [raylib-go](https://github.com/gen2brain/raylib-go) : raylib **Go** binding
|
|
||||||
- [raylib-Nim](https://gitlab.com/define-private-public/raylib-Nim) : raylib **Nim** binding
|
|
||||||
- [cray](https://gitlab.com/Zatherz/cray) - raylib **Crystal** binding
|
|
||||||
- [Graphics::Raylib](https://metacpan.org/pod/Graphics::Raylib) : raylib **Perl** wrapper
|
|
||||||
- [raylib-pascal](https://github.com/drezgames/raylib-pascal) - raylib **Pascal** binding
|
|
||||||
- [Raylib-cs](https://github.com/ChrisDill/Raylib-cs) : raylib **C#** binding
|
|
||||||
- [RaylibSharp](https://github.com/TheLumaio/RaylibSharp) : raylib **C#** binding
|
|
||||||
- [raylib-ruby-ffi](https://github.com/D3nX/raylib-ruby-ffi) : raylib **Ruby** binding
|
|
||||||
- [raylib-rs](https://github.com/deltaphc/raylib-rs) : raylib **Rust** binding
|
|
||||||
- [raylib-py](https://github.com/overdev/raylib-py) : raylib **Python** binding
|
|
||||||
- [raylib-haskell](https://github.com/DevJac/raylib-haskell) : raylib **Haskell** binding
|
|
||||||
- [raylib-java](https://github.com/XoanaIO/raylib-java) : raylib **Java** binding
|
|
||||||
- [raylib-chaiscript](https://github.com/RobLoach/raylib-chaiscript) : raylib **ChaiScript** binding
|
|
||||||
- [node-raylib](https://github.com/RobLoach/node-raylib) : **Node.js** raylib binding
|
|
||||||
- *[raylib flat-assembler Usage example]()*
|
|
||||||
- *[raylib COBOL Usage example](https://github.com/Martinfx/Cobol/tree/master/OpenCobol/Games/raylib)*
|
|
||||||
|
|
||||||
Usually, raylib bindings follow the convention: `raylib-{language}`
|
|
||||||
|
|
||||||
Let me know if you're writing a new binding for raylib, I will list it here and I usually
|
|
||||||
provide the icon/logo for that new language binding.
|
|
||||||
|
|
||||||
### Contact information
|
### Contact information
|
||||||
|
|
||||||
If you have any doubt, don't hesitate to [contact me](mailto:ray@raylib.com)!.
|
If you have any doubt, don't hesitate to [contact me](mailto:ray@raylib.com)!.
|
||||||
|
|
|
||||||
380
projects/Geany/raylib.c.tags
Normal file
380
projects/Geany/raylib.c.tags
Normal file
|
|
@ -0,0 +1,380 @@
|
||||||
|
# format=pipe
|
||||||
|
RaylibIsAwesome|SuperStefkaGeanyTags|OpenSourceHaveFun|
|
||||||
|
InitWindow|void|(int width, int height, const char *title);|
|
||||||
|
CloseWindow|void|(void);|
|
||||||
|
IsWindowReady|bool|(void);|
|
||||||
|
WindowShouldClose|bool|(void);|
|
||||||
|
IsWindowMinimized|bool(void);|
|
||||||
|
ToggleFullscreen|void|(void);|
|
||||||
|
SetWindowIcon|void|(Image image);|
|
||||||
|
SetWindowTitle|void|(const char *title);|
|
||||||
|
SetWindowPosition|void|(int x, int y);|
|
||||||
|
SetWindowMonitor|void|(int monitor);|
|
||||||
|
SetWindowMinSize|void|(int width, int height);|
|
||||||
|
SetWindowSize|void|(int width, int height);|
|
||||||
|
GetScreenWidth|int|(void);|
|
||||||
|
GetScreenHeight|int|(void);|
|
||||||
|
ShowCursor|void|(void);|
|
||||||
|
HideCursor|void|(void);|
|
||||||
|
IsCursorHidden|bool|(void);|
|
||||||
|
EnableCursor|void|(void);
|
||||||
|
DisableCursor|void|(void);|
|
||||||
|
ClearBackground|void|(Color color);|
|
||||||
|
BeginDrawing|void|(void);|
|
||||||
|
EndDrawing|void|(void);|
|
||||||
|
BeginMode2D|void|(Camera2D camera);|
|
||||||
|
EndMode2D|void|(void);
|
||||||
|
BeginMode3D|void|(Camera3D camera);|
|
||||||
|
EndMode3D|void|(void);|
|
||||||
|
BeginTextureMode|void|(RenderTexture2D target);|
|
||||||
|
EndTextureMode|void|(void);|
|
||||||
|
GetMouseRay|Ray|(Vector2 mousePosition, Camera camera);|
|
||||||
|
GetWorldToScreen|Vector2|(Vector3 position, Camera camera);|
|
||||||
|
GetCameraMatrix|Matrix|(Camera camera);|
|
||||||
|
SetTargetFPS|void|(int fps);|
|
||||||
|
GetFPS|int|(void);|
|
||||||
|
GetFrameTime|float|(void);|
|
||||||
|
GetTime|double|(void);|
|
||||||
|
ColorToInt|int|(Color color);|
|
||||||
|
ColorNormalize|Vector4|(Color color);|
|
||||||
|
ColorToHSV|Vector3|(Color color);|
|
||||||
|
GetColor|Color|(int hexValue);|
|
||||||
|
Fade|Color|(Color color, float alpha);|
|
||||||
|
ShowLogo|void|(void);|
|
||||||
|
SetConfigFlags|void|(unsigned char flags);|
|
||||||
|
SetTraceLog|void|(unsigned char types);|
|
||||||
|
TraceLog|void|(int logType, const char *text, ...);|
|
||||||
|
TakeScreenshot|void|(const char *fileName);|
|
||||||
|
GetRandomValue|int|(int min, int max);|
|
||||||
|
IsFileExtension|bool|(const char *fileName, const char *ext);|
|
||||||
|
GetExtension|const char *|(const char *fileName);|
|
||||||
|
GetFileName|const char *|(const char *filePath);|
|
||||||
|
GetDirectoryPath|const char *|(const char *fileName);|
|
||||||
|
GetWorkingDirectory|const char *|(void);|
|
||||||
|
ChangeDirectory|bool|(const char *dir);|
|
||||||
|
IsFileDropped|bool|(void);|
|
||||||
|
GetDroppedFiles|char **|(int *count);|
|
||||||
|
ClearDroppedFiles|void|(void);|
|
||||||
|
StorageSaveValue|void|(int position, int value);|
|
||||||
|
StorageLoadValue|int|(int position);|
|
||||||
|
IsKeyPressed|bool|(int key);|
|
||||||
|
IsKeyDown|bool|(int key);|
|
||||||
|
IsKeyReleased|bool|(int key);|
|
||||||
|
IsKeyUp|bool|(int key);|
|
||||||
|
GetKeyPressed|int|(void);|
|
||||||
|
SetExitKey|void|(int key);|
|
||||||
|
IsGamepadAvailable|bool|(int gamepad);|
|
||||||
|
IsGamepadName|bool|(int gamepad, const char *name);|
|
||||||
|
GetGamepadName|const char *|(int gamepad);|
|
||||||
|
IsGamepadButtonPressed|bool|(int gamepad, int button);|
|
||||||
|
IsGamepadButtonDown|bool|(int gamepad, int button);|
|
||||||
|
IsGamepadButtonReleased|bool|(int gamepad, int button);|
|
||||||
|
IsGamepadButtonUp|bool|(int gamepad, int button);|
|
||||||
|
GetGamepadButtonPressed|int|(void);|
|
||||||
|
GetGamepadAxisCount|int|(int gamepad);|
|
||||||
|
GetGamepadAxisMovement|float|(int gamepad, int axis);|
|
||||||
|
IsMouseButtonPressed|bool|(int button);|
|
||||||
|
IsMouseButtonDown|bool|(int button);|
|
||||||
|
IsMouseButtonReleased|bool|(int button);|
|
||||||
|
IsMouseButtonUp|bool|(int button);|
|
||||||
|
GetMouseX|int|(void);|
|
||||||
|
GetMouseY|int|(void);|
|
||||||
|
GetMousePosition|Vector2|(void);|
|
||||||
|
SetMousePosition|void|(Vector2 position);|
|
||||||
|
GetMouseWheelMove|int|(void);|
|
||||||
|
GetTouchX|int|(void);|
|
||||||
|
GetTouchY|int|(void);|
|
||||||
|
GetTouchPosition|Vector2|(int index);|
|
||||||
|
SetGesturesEnabled|void|(unsigned int gestureFlags);|
|
||||||
|
IsGestureDetected|bool|(int gesture);|
|
||||||
|
GetGestureDetected|int|(void);|
|
||||||
|
GetTouchPointsCount|int|(void);|
|
||||||
|
GetGestureHoldDuration|float|(void);|
|
||||||
|
GetGestureDragVector|Vector2|(void);|
|
||||||
|
GetGestureDragAngle|float|(void);|
|
||||||
|
GetGesturePinchVector|Vector2|(void);|
|
||||||
|
GetGesturePinchAngle|float|(void);|
|
||||||
|
SetCameraMode|void|(Camera camera, int mode);|
|
||||||
|
UpdateCamera|void|(Camera *camera);|
|
||||||
|
SetCameraPanControl|void|(int panKey);|
|
||||||
|
SetCameraAltControl|void|(int altKey);|
|
||||||
|
SetCameraSmoothZoomControl|void|(int szKey);|
|
||||||
|
SetCameraMoveControls|void|(int frontKey, int backKey, int rightKey, int leftKey, int upKey, int downKey);|
|
||||||
|
DrawPixel|void|(int posX, int posY, Color color);|
|
||||||
|
DrawPixelV|void|(Vector2 position, Color color);
|
||||||
|
DrawLine|void|(int startPosX, int startPosY, int endPosX, int endPosY, Color color);
|
||||||
|
DrawLineV|void|(Vector2 startPos, Vector2 endPos, Color color);|
|
||||||
|
DrawLineEx|void|(Vector2 startPos, Vector2 endPos, float thick, Color color);|
|
||||||
|
DrawLineBezier|void|(Vector2 startPos, Vector2 endPos, float thick, Color color);|
|
||||||
|
DrawCircle|void|(int centerX, int centerY, float radius, Color color);|
|
||||||
|
DrawCircleGradient|void|(int centerX, int centerY, float radius, Color color1, Color color2);|
|
||||||
|
DrawCircleV|void|(Vector2 center, float radius, Color color);|
|
||||||
|
DrawCircleLines|void|(int centerX, int centerY, float radius, Color color);|
|
||||||
|
DrawRectangle|void|(int posX, int posY, int width, int height, Color color);|
|
||||||
|
DrawRectangleV|void|(Vector2 position, Vector2 size, Color color);|
|
||||||
|
DrawRectangleRec|void|(Rectangle rec, Color color);|
|
||||||
|
DrawRectanglePro|void|(Rectangle rec, Vector2 origin, float rotation, Color color);|
|
||||||
|
DrawRectangleGradientV|void|(int posX, int posY, int width, int height, Color color1, Color color2);|
|
||||||
|
DrawRectangleGradientH|void|(int posX, int posY, int width, int height, Color color1, Color color2);|
|
||||||
|
DrawRectangleGradientEx|void|(Rectangle rec, Color col1, Color col2, Color col3, Color col4);|
|
||||||
|
DrawRectangleLines|void|(int posX, int posY, int width, int height, Color color);|
|
||||||
|
DrawRectangleLinesEx|void|(Rectangle rec, int lineThick, Color color);|
|
||||||
|
DrawTriangle|void|(Vector2 v1, Vector2 v2, Vector2 v3, Color color);|
|
||||||
|
DrawTriangleLines|void|(Vector2 v1, Vector2 v2, Vector2 v3, Color color);|
|
||||||
|
DrawPoly|void|(Vector2 center, int sides, float radius, float rotation, Color color);|
|
||||||
|
DrawPolyEx|void|(Vector2 *points, int numPoints, Color color);|
|
||||||
|
DrawPolyExLines|void|(Vector2 *points, int numPoints, Color color);|
|
||||||
|
CheckCollisionRecs|bool|(Rectangle rec1, Rectangle rec2);|
|
||||||
|
CheckCollisionCircles|bool|(Vector2 center1, float radius1, Vector2 center2, float radius2);|
|
||||||
|
CheckCollisionCircleRec|bool|(Vector2 center, float radius, Rectangle rec);|
|
||||||
|
GetCollisionRec|Rectangle|(Rectangle rec1, Rectangle rec2);|
|
||||||
|
CheckCollisionPointRec|bool|(Vector2 point, Rectangle rec);|
|
||||||
|
CheckCollisionPointCircle|bool|(Vector2 point, Vector2 center, float radius);|
|
||||||
|
CheckCollisionPointTriangle|bool|(Vector2 point, Vector2 p1, Vector2 p2, Vector2 p3);|
|
||||||
|
LoadImage|Image|(const char *fileName);|
|
||||||
|
LoadImageEx|Image|(Color *pixels, int width, int height);|
|
||||||
|
LoadImagePro|Image|(void *data, int width, int height, int format);|
|
||||||
|
LoadImageRaw|Image|(const char *fileName, int width, int height, int format, int headerSize);|
|
||||||
|
ExportImage|void|(const char *fileName, Image image);|
|
||||||
|
LoadTexture|Texture2D|(const char *fileName);|
|
||||||
|
LoadTextureFromImage|Texture2D|(Image image);|
|
||||||
|
RenderTexture2D LoadRenderTexture(int width, int height);|
|
||||||
|
UnloadImage|void|(Image image);|
|
||||||
|
UnloadTexture|void|(Texture2D texture);|
|
||||||
|
UnloadRenderTexture|void|(RenderTexture2D target);|
|
||||||
|
GetImageData|Color *|(Image image);|
|
||||||
|
GetImageDataNormalized|Vector4 *|(Image image);|
|
||||||
|
GetPixelDataSize|int|(int width, int height, int format);|
|
||||||
|
GetTextureData|Image|(Texture2D texture);|
|
||||||
|
UpdateTexture|void|(Texture2D texture, const void *pixels);|
|
||||||
|
ImageCopy|Image|(Image image);|
|
||||||
|
ImageToPOT|void|(Image *image, Color fillColor);|
|
||||||
|
ImageFormat|void|(Image *image, int newFormat);|
|
||||||
|
ImageAlphaMask|void|(Image *image, Image alphaMask);|
|
||||||
|
ImageAlphaClear|void|(Image *image, Color color, float threshold);|
|
||||||
|
ImageAlphaCrop|void|(Image *image, float threshold);|
|
||||||
|
ImageAlphaPremultiply|void|(Image *image);|
|
||||||
|
ImageCrop|void|(Image *image, Rectangle crop);|
|
||||||
|
ImageResize|void|(Image *image, int newWidth, int newHeight);|
|
||||||
|
ImageResizeNN|void|(Image *image, int newWidth,int newHeight);|
|
||||||
|
ImageResizeCanvas|void|(Image *image, int newWidth, int newHeight, int offsetX, int offsetY, Color color);|
|
||||||
|
ImageMipmaps|void|(Image *image);|
|
||||||
|
ImageDither|void|(Image *image, int rBpp, int gBpp, int bBpp, int aBpp);|
|
||||||
|
ImageText|Image|(const char *text, int fontSize, Color color);|
|
||||||
|
ImageTextEx|Image|(Font font, const char *text, float fontSize, float spacing, Color tint);|
|
||||||
|
ImageDraw|void|(Image *dst, Image src, Rectangle srcRec, Rectangle dstRec);|
|
||||||
|
ImageDrawRectangle|void|(Image *dst, Vector2 position, Rectangle rec, Color color);|
|
||||||
|
ImageDrawText|void|(Image *dst, Vector2 position, const char *text, int fontSize, Color color);|
|
||||||
|
ImageDrawTextEx|void|(Image *dst, Vector2 position, Font font, const char *text, float fontSize, float spacing, Color color);|
|
||||||
|
ImageFlipVertical|void|(Image *image);|
|
||||||
|
ImageFlipHorizontal|void|(Image *image);|
|
||||||
|
ImageRotateCW|void|(Image *image);|
|
||||||
|
ImageRotateCCW|void|(Image *image);|
|
||||||
|
ImageColorTint|void|(Image *image, Color color);|
|
||||||
|
ImageColorInvert|void|(Image *image);|
|
||||||
|
ImageColorGrayscale|void|(Image *image);|
|
||||||
|
ImageColorContrast|void|(Image *image, float contrast);|
|
||||||
|
ImageColorBrightness|void|(Image *image, int brightness);|
|
||||||
|
ImageColorReplace|void|(Image *image, Color color, Color replace);|
|
||||||
|
GenImageColor|void|(int width, int height, Color color);|
|
||||||
|
GenImageGradientV|void|(int width, int height, Color top, Color bottom);|
|
||||||
|
GenImageGradientH|void|(int width, int height, Color left, Color right);|
|
||||||
|
GenImageGradientRadial|void|(int width, int height, float density, Color inner, Color outer);|
|
||||||
|
GenImageChecked|void|(int width, int height, int checksX, int checksY, Color col1, Color col2);|
|
||||||
|
GenImageWhiteNoise|void|(int width, int height, float factor);|
|
||||||
|
GenImagePerlinNoise|void|(int width, int height, int offsetX, int offsetY, float scale);|
|
||||||
|
GenImageCellular|void|(int width, int height, int tileSize);|
|
||||||
|
GenTextureMipmaps|void|(Texture2D *texture);|
|
||||||
|
SetTextureFilter|void|(Texture2D texture, int filterMode);|
|
||||||
|
SetTextureWrap|void|(Texture2D texture, int wrapMode);|
|
||||||
|
DrawTexture|void|(Texture2D texture, int posX, int posY, Color tint);|
|
||||||
|
DrawTextureV|void|(Texture2D texture, Vector2 position, Color tint);|
|
||||||
|
DrawTextureEx|void|(Texture2D texture, Vector2 position, float rotation, float scale, Color tint);|
|
||||||
|
DrawTextureRec|void|(Texture2D texture, Rectangle sourceRec, Vector2 position, Color tint);|
|
||||||
|
DrawTexturePro|void|(Texture2D texture, Rectangle sourceRec, Rectangle destRec, Vector2 origin, float rotation, Color tint);|
|
||||||
|
GetFontDefault|Font|(void);|
|
||||||
|
LoadFont|Font|(const char *fileName);|
|
||||||
|
LoadFontEx|Font|(const char *fileName, int fontSize, int charsCount, int *fontChars);|
|
||||||
|
LoadFontData|CharInfo *|(const char *fileName, int fontSize, int *fontChars, int charsCount, bool sdf);|
|
||||||
|
GenImageFontAtlas|Image|(CharInfo *chars, int fontSize, int charsCount, int padding, int packMethod);|
|
||||||
|
UnloadFont|void|(Font font);|
|
||||||
|
DrawFPS|void|(int posX, int posY);|
|
||||||
|
DrawText|void|(const char *text, int posX, int posY, int fontSize, Color color);|
|
||||||
|
DrawTextEx|void|(Font font, const char* text, Vector2 position, float fontSize, float spacing, Color tint);|
|
||||||
|
MeasureText|int|(const char *text, int fontSize);|
|
||||||
|
MeasureTextEx|Vector2|(Font font, const char *text, float fontSize, float spacing);|
|
||||||
|
FormatText|const char *|(const char *text, ...);|
|
||||||
|
SubText|const char *|(const char *text, int position, int length);|
|
||||||
|
GetGlyphIndex|int|(Font font, int character);|
|
||||||
|
DrawLine3D|void|(Vector3 startPos, Vector3 endPos, Color color);|
|
||||||
|
DrawCircle3D|void|(Vector3 center, float radius, Vector3 rotationAxis, float rotationAngle, Color color);|
|
||||||
|
DrawCube|void|(Vector3 position, float width, float height, float length, Color color);|
|
||||||
|
DrawCubeV|void|(Vector3 position, Vector3 size, Color color);|
|
||||||
|
DrawCubeWires|void|(Vector3 position, float width, float height, float length, Color color);|
|
||||||
|
DrawCubeTexture|void|(Texture2D texture, Vector3 position, float width, float height, float length, Color color);|
|
||||||
|
DrawSphere|void|(Vector3 centerPos, float radius, Color color);|
|
||||||
|
DrawSphereEx|void|(Vector3 centerPos, float radius, int rings, int slices, Color color);|
|
||||||
|
DrawSphereWires|void|(Vector3 centerPos, float radius, int rings, int slices, Color color);|
|
||||||
|
DrawCylinder|void|(Vector3 position, float radiusTop, float radiusBottom, float height, int slices, Color color);|
|
||||||
|
DrawCylinderWires|void|(Vector3 position, float radiusTop, float radiusBottom, float height, int slices, Color color);|
|
||||||
|
DrawPlane|void|(Vector3 centerPos, Vector2 size, Color color);|
|
||||||
|
DrawRay|void|(Ray ray, Color color);|
|
||||||
|
DrawGrid|void|(int slices, float spacing);|
|
||||||
|
DrawGizmo|void|(Vector3 position);|
|
||||||
|
LoadModel|Model|(const char *fileName);|
|
||||||
|
LoadModelFromMesh|Model|(Mesh mesh);|
|
||||||
|
UnloadModel|void|(Model model);|
|
||||||
|
LoadMesh|Mesh|(const char *fileName);|
|
||||||
|
UnloadMesh|void|(Mesh *mesh);|
|
||||||
|
ExportMesh|void|(const char *fileName, Mesh mesh);|
|
||||||
|
MeshBoundingBox|BoundingBox|(Mesh mesh);|
|
||||||
|
MeshTangents|void|(Mesh *mesh);|
|
||||||
|
MeshBinormals|void|(Mesh *mesh);|
|
||||||
|
GenMeshPlane|Mesh|(float width, float length, int resX, int resZ);|
|
||||||
|
GenMeshCube|Mesh|(float width, float height, float length);|
|
||||||
|
GenMeshSphere|Mesh|(float radius, int rings, int slices);|
|
||||||
|
GenMeshHemiSphere|Mesh|(float radius, int rings, int slices);|
|
||||||
|
GenMeshCylinder|Mesh|(float radius, float height, int slices);|
|
||||||
|
GenMeshTorus|Mesh|(float radius, float size, int radSeg, int sides);|
|
||||||
|
GenMeshKnot|Mesh|(float radius, float size, int radSeg, int sides);|
|
||||||
|
GenMeshHeightmap|Mesh|(Image heightmap, Vector3 size);|
|
||||||
|
GenMeshCubicmap|Mesh|(Image cubicmap, Vector3 cubeSize);|
|
||||||
|
LoadMaterial|Material|(const char *fileName);|
|
||||||
|
LoadMaterialDefault|Material|(void);|
|
||||||
|
UnloadMaterial|void|(Material material);|
|
||||||
|
DrawModel|void|(Model model, Vector3 position, float scale, Color tint);|
|
||||||
|
DrawModelEx|void|(Model model, Vector3 position, Vector3 rotationAxis, float rotationAngle, Vector3 scale, Color tint);|
|
||||||
|
DrawModelWires|void|(Model model, Vector3 position, float scale, Color tint);|
|
||||||
|
DrawModelWiresEx|void|(Model model, Vector3 position, Vector3 rotationAxis, float rotationAngle, Vector3 scale, Color tint);|
|
||||||
|
DrawBoundingBox|void|(BoundingBox box, Color color);|
|
||||||
|
DrawBillboard|void|(Camera camera, Texture2D texture, Vector3 center, float size, Color tint);|
|
||||||
|
DrawBillboardRec|void|(Camera camera, Texture2D texture, Rectangle sourceRec, Vector3 center, float size, Color tint);|
|
||||||
|
CheckCollisionSpheres|bool|(Vector3 centerA, float radiusA, Vector3 centerB, float radiusB);|
|
||||||
|
CheckCollisionBoxes|bool|(Vector3 minBBox1, Vector3 maxBBox1, Vector3 minBBox2, Vector3 maxBBox2);|
|
||||||
|
CheckCollisionBoxSphere|bool|(Vector3 minBBox, Vector3 maxBBox, Vector3 centerSphere, float radiusSphere);|
|
||||||
|
CheckCollisionRaySphere|bool|(Ray ray, Vector3 spherePosition, float sphereRadius);|
|
||||||
|
CheckCollisionRaySphereEx|bool|(Ray ray, Vector3 spherePosition, float sphereRadius, Vector3 *collisionPoint);|
|
||||||
|
CheckCollisionRayBox|bool|(Ray ray, Vector3 minBBox, Vector3 maxBBox);|
|
||||||
|
GetCollisionRayModel|RayHitInfo|(Ray ray, Model *model);|
|
||||||
|
GetCollisionRayTriangle|RayHitInfo|(Ray ray, Vector3 p1, Vector3 p2, Vector3 p3);|
|
||||||
|
GetCollisionRayGround|RayHitInfo|(Ray ray, float groundHeight);|
|
||||||
|
LoadText|char *|(const char *fileName);|
|
||||||
|
LoadShader|Shader|(char *vsFileName, char *fsFileName);|
|
||||||
|
LoadShaderCode|Shader|(char *vsCode, char *fsCode);|
|
||||||
|
UnloadShader|void|(Shader shader);|
|
||||||
|
GetShaderDefault|Shader|(void);|
|
||||||
|
GetTextureDefault|Texture2D|(void);|
|
||||||
|
GetShaderLocation|int|(Shader shader, const char *uniformName);|
|
||||||
|
SetShaderValue|void|(Shader shader, int uniformLoc, float *value, int size);|
|
||||||
|
SetShaderValuei|void|(Shader shader, int uniformLoc, int *value, int size);|
|
||||||
|
SetShaderValueMatrix|void|(Shader shader, int uniformLoc, Matrix mat);|
|
||||||
|
SetMatrixProjection|void|(Matrix proj);|
|
||||||
|
SetMatrixModelview|void|(Matrix view);|
|
||||||
|
GetMatrixModelview|Matrix|();|
|
||||||
|
BeginShaderMode|void|(Shader shader);|
|
||||||
|
EndShaderMode|void|(void);|
|
||||||
|
BeginBlendMode|void|(int mode);|
|
||||||
|
EndBlendMode|void|(void);|
|
||||||
|
GetVrDeviceInfo|VrDeviceInfo|(int vrDeviceType);|
|
||||||
|
InitVrSimulator|void|(VrDeviceInfo info);|
|
||||||
|
CloseVrSimulator|void|(void);|
|
||||||
|
IsVrSimulatorReady|bool|(void);|
|
||||||
|
UpdateVrTracking|void|(Camera *camera);|
|
||||||
|
ToggleVrMode|void|(void);|
|
||||||
|
BeginVrDrawing|void|(void);|
|
||||||
|
EndVrDrawing|void|(void);|
|
||||||
|
InitAudioDevice|void|(void);|
|
||||||
|
CloseAudioDevice|void|(void);|
|
||||||
|
IsAudioDeviceReady|bool|(void);|
|
||||||
|
SetMasterVolume|void|(float volume);|
|
||||||
|
LoadWave|Wave|(const char *fileName);|
|
||||||
|
LoadWaveEx|Wave|(float *data, int sampleCount, int sampleRate, int sampleSize, int channels);|
|
||||||
|
LoadSound|Sound|(const char *fileName);|
|
||||||
|
LoadSoundFromWave|Sound|(Wave wave);|
|
||||||
|
UpdateSound|void|(Sound sound, void *data, int numSamples);|
|
||||||
|
UnloadWave|void|(Wave wave);|
|
||||||
|
UnloadSound|void|(Sound sound);|
|
||||||
|
PlaySound|void|(Sound sound);|
|
||||||
|
PauseSound|void|(Sound sound);|
|
||||||
|
ResumeSound|void|(Sound sound);|
|
||||||
|
StopSound|void|(Sound sound);|
|
||||||
|
IsSoundPlaying|bool|(Sound sound);|
|
||||||
|
SetSoundVolume|void|(Sound sound, float volume);|
|
||||||
|
SetSoundPitch|void|(Sound sound, float pitch);|
|
||||||
|
WaveFormat|void|(Wave *wave, int sampleRate, int sampleSize, int channels);|
|
||||||
|
WaveCopy|Wave|(Wave wave);|
|
||||||
|
WaveCrop|void|(Wave *wave, int initSample, int finalSample);|
|
||||||
|
GetWaveData|float *|(Wave wave);|
|
||||||
|
LoadMusicStream|Music|(const char *fileName);|
|
||||||
|
UnloadMusicStream|void|(Music music);|
|
||||||
|
PlayMusicStream|void|(Music music);|
|
||||||
|
UpdateMusicStream|void|(Music music);|
|
||||||
|
StopMusicStream|void|(Music music);|
|
||||||
|
PauseMusicStream|void|(Music music);|
|
||||||
|
ResumeMusicStream|void|(Music music);|
|
||||||
|
IsMusicPlaying|bool|(Music music);|
|
||||||
|
SetMusicVolume|void|(Music music, float volume);|
|
||||||
|
SetMusicPitch|void|(Music music, float pitch);|
|
||||||
|
SetMusicLoopCount|void|(Music music, float count);|
|
||||||
|
GetMusicTimeLength|float|(Music music);|
|
||||||
|
GetMusicTimePlayed|float|(Music music);|
|
||||||
|
InitAudioStream|AudioStream|(unsigned int sampleRate, unsigned int sampleSize, unsigned int channels);|
|
||||||
|
UpdateAudioStream|void|(AudioStream stream, void *data, int numSamples);|
|
||||||
|
CloseAudioStream|void|(AudioStream stream);|
|
||||||
|
IsAudioBufferProcessed|bool|(AudioStream stream);|
|
||||||
|
PlayAudioStream|void|(AudioStream stream);|
|
||||||
|
PauseAudioStream|void|(AudioStream stream);|
|
||||||
|
ResumeAudioStream|void|(AudioStream stream);|
|
||||||
|
StopAudioStream|void|(AudioStream stream);|
|
||||||
|
Color|struct||
|
||||||
|
Rectangle|struct||
|
||||||
|
Vector2|struct||
|
||||||
|
Vector3|struct||
|
||||||
|
Vector4|struct||
|
||||||
|
Quaternion|struct||
|
||||||
|
Matrix|struct||
|
||||||
|
Image|struct||
|
||||||
|
Texture|struct||
|
||||||
|
RenderTexture|struct||
|
||||||
|
CharInfo|struct||
|
||||||
|
Font|struct||
|
||||||
|
Camera|struct||
|
||||||
|
Camera2D|struct||
|
||||||
|
Mesh|struct||
|
||||||
|
Shader|struct||
|
||||||
|
MaterialMap|struct||
|
||||||
|
Material|struct||
|
||||||
|
Model|struct||
|
||||||
|
Ray|struct||
|
||||||
|
RayHitInfo|struct||
|
||||||
|
Wave|struct||
|
||||||
|
Sound|struct||
|
||||||
|
Music|struct||
|
||||||
|
AudioStream|struct||
|
||||||
|
LIGHTGRAY|#define||
|
||||||
|
GRAY|#define||
|
||||||
|
DARKGRAY|#define||
|
||||||
|
YELLOW|#define||
|
||||||
|
GOLD|#define||
|
||||||
|
ORANGE|#define||
|
||||||
|
PINK|#define||
|
||||||
|
RED|#define||
|
||||||
|
MAROON|#define||
|
||||||
|
GREEN|#define||
|
||||||
|
LIME|#define||
|
||||||
|
DARKGREEN|#define||
|
||||||
|
SKYBLUE|#define||
|
||||||
|
BLUE|#define||
|
||||||
|
DARKBLUE|#define||
|
||||||
|
PURPLE|#define||
|
||||||
|
VIOLET|#define||
|
||||||
|
DARKPURPLE|#define||
|
||||||
|
BEIGE|#define||
|
||||||
|
BROWN|#define||
|
||||||
|
DARKBROWN|#define||
|
||||||
|
WHITE|#define||
|
||||||
|
BLACK|#define||
|
||||||
|
BLANK|#define||
|
||||||
|
MAGENTA|#define||
|
||||||
|
RAYWHITE|#define||
|
||||||
|
|
||||||
|
|
@ -246,7 +246,7 @@
|
||||||
<ClInclude Include="..\..\..\src\external\glad.h" />
|
<ClInclude Include="..\..\..\src\external\glad.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\jar_mod.h" />
|
<ClInclude Include="..\..\..\src\external\jar_mod.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\jar_xm.h" />
|
<ClInclude Include="..\..\..\src\external\jar_xm.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\mini_al.h" />
|
<ClInclude Include="..\..\..\src\external\miniaudio.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\stb_image.h" />
|
<ClInclude Include="..\..\..\src\external\stb_image.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\stb_image_resize.h" />
|
<ClInclude Include="..\..\..\src\external\stb_image_resize.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\stb_image_write.h" />
|
<ClInclude Include="..\..\..\src\external\stb_image_write.h" />
|
||||||
|
|
|
||||||
|
|
@ -174,7 +174,7 @@
|
||||||
<ClInclude Include="..\..\..\src\external\glad.h" />
|
<ClInclude Include="..\..\..\src\external\glad.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\jar_mod.h" />
|
<ClInclude Include="..\..\..\src\external\jar_mod.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\jar_xm.h" />
|
<ClInclude Include="..\..\..\src\external\jar_xm.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\mini_al.h" />
|
<ClInclude Include="..\..\..\src\external\miniaudio.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\stb_image.h" />
|
<ClInclude Include="..\..\..\src\external\stb_image.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\stb_image_resize.h" />
|
<ClInclude Include="..\..\..\src\external\stb_image_resize.h" />
|
||||||
<ClInclude Include="..\..\..\src\external\stb_image_write.h" />
|
<ClInclude Include="..\..\..\src\external\stb_image_write.h" />
|
||||||
|
|
|
||||||
|
|
@ -49,7 +49,7 @@ if(USE_AUDIO)
|
||||||
set(sources ${raylib_sources})
|
set(sources ${raylib_sources})
|
||||||
else()
|
else()
|
||||||
MESSAGE(STATUS "Audio Backend: None (-DUSE_AUDIO=OFF)")
|
MESSAGE(STATUS "Audio Backend: None (-DUSE_AUDIO=OFF)")
|
||||||
set(INCLUDE_AUDIO_MODULE 0)
|
set(RAYLIB_MODULE_AUDIO 0)
|
||||||
list(REMOVE_ITEM raylib_sources ${CMAKE_CURRENT_SOURCE_DIR}/raudio.c)
|
list(REMOVE_ITEM raylib_sources ${CMAKE_CURRENT_SOURCE_DIR}/raudio.c)
|
||||||
set(sources ${raylib_sources})
|
set(sources ${raylib_sources})
|
||||||
endif()
|
endif()
|
||||||
|
|
|
||||||
85
src/Makefile
85
src/Makefile
|
|
@ -42,7 +42,7 @@
|
||||||
.PHONY: all clean install uninstall
|
.PHONY: all clean install uninstall
|
||||||
|
|
||||||
# Define required raylib variables
|
# Define required raylib variables
|
||||||
RAYLIB_VERSION = 2.0.0
|
RAYLIB_VERSION = 2.4.0
|
||||||
RAYLIB_API_VERSION = 2
|
RAYLIB_API_VERSION = 2
|
||||||
|
|
||||||
# See below for alternatives.
|
# See below for alternatives.
|
||||||
|
|
@ -59,9 +59,15 @@ RAYLIB_LIBTYPE ?= STATIC
|
||||||
# Build mode for library: DEBUG or RELEASE
|
# Build mode for library: DEBUG or RELEASE
|
||||||
RAYLIB_BUILD_MODE ?= RELEASE
|
RAYLIB_BUILD_MODE ?= RELEASE
|
||||||
|
|
||||||
# Included raylib audio module on compilation
|
# Include raylib modules on compilation
|
||||||
# NOTE: Some programs like tools could not require audio support
|
# NOTE: Some programs like tools could not require those modules
|
||||||
INCLUDE_AUDIO_MODULE ?= TRUE
|
RAYLIB_MODULE_AUDIO ?= TRUE
|
||||||
|
RAYLIB_MODULE_MODELS ?= TRUE
|
||||||
|
RAYLIB_MODULE_RAYGUI ?= FALSE
|
||||||
|
RAYLIB_MODULE_PHYSAC ?= FALSE
|
||||||
|
|
||||||
|
RAYLIB_MODULE_RAYGUI_PATH ?= .
|
||||||
|
RAYLIB_MODULE_PHYSAC_PATH ?= .
|
||||||
|
|
||||||
# Use external GLFW library instead of rglfw module
|
# Use external GLFW library instead of rglfw module
|
||||||
# TODO: Review usage of examples on Linux.
|
# TODO: Review usage of examples on Linux.
|
||||||
|
|
@ -179,33 +185,12 @@ ifeq ($(PLATFORM),PLATFORM_ANDROID)
|
||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
|
|
||||||
# RAYLIB_RELEASE_PATH points to library build path, right now
|
# Define raylib source code path
|
||||||
RAYLIB_RELEASE_PATH ?= $(RAYLIB_PATH)/src
|
RAYLIB_SRC_PATH ?= $(RAYLIB_PATH)/src
|
||||||
|
|
||||||
# Define output directory for compiled library
|
# Define output directory for compiled library, defaults to src directory
|
||||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
# NOTE: If externally provided, make sure directory exists
|
||||||
ifeq ($(PLATFORM_OS),WINDOWS)
|
RAYLIB_RELEASE_PATH ?= $(RAYLIB_PATH)/src
|
||||||
RAYLIB_RELEASE_PATH = $(RAYLIB_PATH)\mingw\i686-w64-mingw32\lib
|
|
||||||
endif
|
|
||||||
ifeq ($(PLATFORM_OS),LINUX)
|
|
||||||
RAYLIB_RELEASE_PATH = $(RAYLIB_PATH)/src
|
|
||||||
endif
|
|
||||||
ifeq ($(PLATFORM_OS),OSX)
|
|
||||||
RAYLIB_RELEASE_PATH = $(RAYLIB_PATH)/src
|
|
||||||
endif
|
|
||||||
ifeq ($(PLATFORM_OS),BSD)
|
|
||||||
RAYLIB_RELEASE_PATH = $(RAYLIB_PATH)/src
|
|
||||||
endif
|
|
||||||
endif
|
|
||||||
ifeq ($(PLATFORM),PLATFORM_RPI)
|
|
||||||
RAYLIB_RELEASE_PATH = $(RAYLIB_PATH)/src
|
|
||||||
endif
|
|
||||||
ifeq ($(PLATFORM),PLATFORM_WEB)
|
|
||||||
RAYLIB_RELEASE_PATH = $(RAYLIB_PATH)/src
|
|
||||||
endif
|
|
||||||
ifeq ($(PLATFORM),PLATFORM_ANDROID)
|
|
||||||
RAYLIB_RELEASE_PATH = $(RAYLIB_PATH)/src/android/$(ANDROID_ARCH_NAME)
|
|
||||||
endif
|
|
||||||
|
|
||||||
# Define raylib graphics api depending on selected platform
|
# Define raylib graphics api depending on selected platform
|
||||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||||
|
|
@ -393,7 +378,6 @@ OBJS = core.o \
|
||||||
shapes.o \
|
shapes.o \
|
||||||
textures.o \
|
textures.o \
|
||||||
text.o \
|
text.o \
|
||||||
models.o \
|
|
||||||
utils.o
|
utils.o
|
||||||
|
|
||||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||||
|
|
@ -401,10 +385,18 @@ ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||||
OBJS += rglfw.o
|
OBJS += rglfw.o
|
||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
|
ifeq ($(RAYLIB_MODULE_MODELS),TRUE)
|
||||||
ifeq ($(INCLUDE_AUDIO_MODULE),TRUE)
|
OBJS += models.o
|
||||||
|
endif
|
||||||
|
ifeq ($(RAYLIB_MODULE_AUDIO),TRUE)
|
||||||
OBJS += raudio.o
|
OBJS += raudio.o
|
||||||
endif
|
endif
|
||||||
|
ifeq ($(RAYLIB_MODULE_RAYGUI),TRUE)
|
||||||
|
OBJS += raygui.o
|
||||||
|
endif
|
||||||
|
ifeq ($(RAYLIB_MODULE_PHYSAC),TRUE)
|
||||||
|
OBJS += physac.o
|
||||||
|
endif
|
||||||
|
|
||||||
ifeq ($(PLATFORM),PLATFORM_ANDROID)
|
ifeq ($(PLATFORM),PLATFORM_ANDROID)
|
||||||
OBJS += external/android/native_app_glue/android_native_app_glue.o
|
OBJS += external/android/native_app_glue/android_native_app_glue.o
|
||||||
|
|
@ -442,11 +434,6 @@ ifeq ($(PLATFORM),PLATFORM_WEB)
|
||||||
emcc -O1 $(OBJS) -o $(RAYLIB_RELEASE_PATH)/libraylib.bc
|
emcc -O1 $(OBJS) -o $(RAYLIB_RELEASE_PATH)/libraylib.bc
|
||||||
@echo "raylib library generated (libraylib.bc)!"
|
@echo "raylib library generated (libraylib.bc)!"
|
||||||
else
|
else
|
||||||
ifeq ($(PLATFORM_OS),WINDOWS)
|
|
||||||
if not exist $(RAYLIB_RELEASE_PATH) mkdir $(RAYLIB_RELEASE_PATH)
|
|
||||||
else
|
|
||||||
mkdir -p $(RAYLIB_RELEASE_PATH)
|
|
||||||
endif
|
|
||||||
ifeq ($(RAYLIB_LIBTYPE),SHARED)
|
ifeq ($(RAYLIB_LIBTYPE),SHARED)
|
||||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||||
ifeq ($(PLATFORM_OS),WINDOWS)
|
ifeq ($(PLATFORM_OS),WINDOWS)
|
||||||
|
|
@ -509,7 +496,7 @@ core.o : core.c raylib.h rlgl.h utils.h raymath.h camera.h gestures.h
|
||||||
|
|
||||||
# Compile rglfw module
|
# Compile rglfw module
|
||||||
rglfw.o : rglfw.c
|
rglfw.o : rglfw.c
|
||||||
$(CC) $(GLFW_CFLAGS) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM) -D$(GRAPHICS)
|
$(CC) -c $< $(CFLAGS) $(GLFW_CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM) -D$(GRAPHICS)
|
||||||
|
|
||||||
# Compile shapes module
|
# Compile shapes module
|
||||||
shapes.o : shapes.c raylib.h rlgl.h
|
shapes.o : shapes.c raylib.h rlgl.h
|
||||||
|
|
@ -523,6 +510,10 @@ textures.o : textures.c raylib.h rlgl.h utils.h
|
||||||
text.o : text.c raylib.h utils.h
|
text.o : text.c raylib.h utils.h
|
||||||
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM) -D$(GRAPHICS)
|
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM) -D$(GRAPHICS)
|
||||||
|
|
||||||
|
# Compile utils module
|
||||||
|
utils.o : utils.c utils.h
|
||||||
|
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM)
|
||||||
|
|
||||||
# Compile models module
|
# Compile models module
|
||||||
models.o : models.c raylib.h rlgl.h raymath.h
|
models.o : models.c raylib.h rlgl.h raymath.h
|
||||||
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM) -D$(GRAPHICS)
|
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM) -D$(GRAPHICS)
|
||||||
|
|
@ -531,9 +522,19 @@ models.o : models.c raylib.h rlgl.h raymath.h
|
||||||
raudio.o : raudio.c raylib.h
|
raudio.o : raudio.c raylib.h
|
||||||
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM)
|
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM)
|
||||||
|
|
||||||
# Compile utils module
|
# Compile raygui module
|
||||||
utils.o : utils.c utils.h
|
# NOTE: raygui header should be distributed with raylib.h
|
||||||
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM)
|
raygui.o : raygui.c raygui.h
|
||||||
|
@echo #define RAYGUI_IMPLEMENTATION > raygui.c
|
||||||
|
@echo #include "$(RAYLIB_MODULE_RAYGUI_PATH)/raygui.h" > raygui.c
|
||||||
|
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM) -DRAYGUI_IMPLEMENTATION
|
||||||
|
|
||||||
|
# Compile physac module
|
||||||
|
# NOTE: physac header should be distributed with raylib.h
|
||||||
|
physac.o : physac.c physac.h
|
||||||
|
@echo #define PHYSAC_IMPLEMENTATION > physac.c
|
||||||
|
@echo #include "$(RAYLIB_MODULE_PHYSAC_PATH)/physac.h" > physac.c
|
||||||
|
$(CC) -c $< $(CFLAGS) $(INCLUDE_PATHS) -D$(PLATFORM) -DRAYGUI_IMPLEMENTATION
|
||||||
|
|
||||||
|
|
||||||
# Install generated and needed files to desired directories.
|
# Install generated and needed files to desired directories.
|
||||||
|
|
|
||||||
69
src/core.c
69
src/core.c
|
|
@ -92,6 +92,8 @@
|
||||||
// Check if config flags have been externally provided on compilation line
|
// Check if config flags have been externally provided on compilation line
|
||||||
#if !defined(EXTERNAL_CONFIG_FLAGS)
|
#if !defined(EXTERNAL_CONFIG_FLAGS)
|
||||||
#include "config.h" // Defines module configuration flags
|
#include "config.h" // Defines module configuration flags
|
||||||
|
#else
|
||||||
|
#define RAYLIB_VERSION "2.5"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if (defined(__linux__) || defined(PLATFORM_WEB)) && _POSIX_C_SOURCE < 199309L
|
#if (defined(__linux__) || defined(PLATFORM_WEB)) && _POSIX_C_SOURCE < 199309L
|
||||||
|
|
@ -178,15 +180,14 @@
|
||||||
|
|
||||||
//#define GLFW_EXPOSE_NATIVE_COCOA // WARNING: Fails due to type redefinition
|
//#define GLFW_EXPOSE_NATIVE_COCOA // WARNING: Fails due to type redefinition
|
||||||
#include <GLFW/glfw3native.h> // Required for: glfwGetCocoaWindow()
|
#include <GLFW/glfw3native.h> // Required for: glfwGetCocoaWindow()
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if defined(__linux__)
|
#if defined(__linux__)
|
||||||
#include <linux/limits.h> // for NAME_MAX and PATH_MAX defines
|
#include <linux/limits.h> // for NAME_MAX and PATH_MAX defines
|
||||||
#define MAX_FILEPATH_LENGTH PATH_MAX // Use Linux define (4096)
|
#define MAX_FILEPATH_LENGTH PATH_MAX // Use Linux define (4096)
|
||||||
#else
|
#else
|
||||||
#define MAX_FILEPATH_LENGTH 256 // Use common value
|
#define MAX_FILEPATH_LENGTH 512 // Use common value
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if defined(PLATFORM_ANDROID)
|
#if defined(PLATFORM_ANDROID)
|
||||||
|
|
@ -779,24 +780,23 @@ void ToggleFullscreen(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Set icon for window (only PLATFORM_DESKTOP)
|
// Set icon for window (only PLATFORM_DESKTOP)
|
||||||
|
// NOTE: Image must be in RGBA format, 8bit per channel
|
||||||
void SetWindowIcon(Image image)
|
void SetWindowIcon(Image image)
|
||||||
{
|
{
|
||||||
#if defined(PLATFORM_DESKTOP)
|
#if defined(PLATFORM_DESKTOP)
|
||||||
Image imicon = ImageCopy(image);
|
if (image.format == UNCOMPRESSED_R8G8B8A8)
|
||||||
ImageFormat(&imicon, UNCOMPRESSED_R8G8B8A8);
|
{
|
||||||
|
GLFWimage icon[1] = { 0 };
|
||||||
|
|
||||||
GLFWimage icon[1] = { 0 };
|
icon[0].width = image.width;
|
||||||
|
icon[0].height = image.height;
|
||||||
|
icon[0].pixels = (unsigned char *)image.data;
|
||||||
|
|
||||||
icon[0].width = imicon.width;
|
// NOTE 1: We only support one image icon
|
||||||
icon[0].height = imicon.height;
|
// NOTE 2: The specified image data is copied before this function returns
|
||||||
icon[0].pixels = (unsigned char *)imicon.data;
|
glfwSetWindowIcon(window, 1, icon);
|
||||||
|
}
|
||||||
// NOTE 1: We only support one image icon
|
else TraceLog(LOG_WARNING, "Window icon image must be in R8G8B8A8 pixel format");
|
||||||
// NOTE 2: The specified image data is copied before this function returns
|
|
||||||
glfwSetWindowIcon(window, 1, icon);
|
|
||||||
|
|
||||||
// TODO: Support multi-image icons --> image.mipmaps
|
|
||||||
UnloadImage(imicon);
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1674,37 +1674,26 @@ const char *GetFileName(const char *filePath)
|
||||||
// Get filename string without extension (memory should be freed)
|
// Get filename string without extension (memory should be freed)
|
||||||
const char *GetFileNameWithoutExt(const char *filePath)
|
const char *GetFileNameWithoutExt(const char *filePath)
|
||||||
{
|
{
|
||||||
char *result, *lastDot, *lastSep;
|
#define MAX_FILENAMEWITHOUTEXT_LENGTH 64
|
||||||
|
|
||||||
char nameDot = '.'; // Default filename to extension separator character
|
static char fileName[MAX_FILENAMEWITHOUTEXT_LENGTH];
|
||||||
char pathSep = '/'; // Default filepath separator character
|
memset(fileName, 0, MAX_FILENAMEWITHOUTEXT_LENGTH);
|
||||||
|
|
||||||
// Error checks and allocate string
|
strcpy(fileName, GetFileName(filePath)); // Get filename with extension
|
||||||
if (filePath == NULL) return NULL;
|
|
||||||
|
|
||||||
// Try to allocate new string, same size as original
|
int len = strlen(fileName);
|
||||||
// NOTE: By default strlen() does not count the '\0' character
|
|
||||||
if ((result = (char *)malloc(strlen(filePath) + 1)) == NULL) return NULL;
|
|
||||||
|
|
||||||
strcpy(result, filePath); // Make a copy of the string
|
for (int i = 0; (i < len) && (i < MAX_FILENAMEWITHOUTEXT_LENGTH); i++)
|
||||||
|
|
||||||
// NOTE: strrchr() returns a pointer to the last occurrence of character
|
|
||||||
lastDot = strrchr(result, nameDot);
|
|
||||||
lastSep = (pathSep == 0)? NULL : strrchr(result, pathSep);
|
|
||||||
|
|
||||||
if (lastDot != NULL) // Check if it has an extension separator...
|
|
||||||
{
|
{
|
||||||
if (lastSep != NULL) // ...and it's before the extenstion separator...
|
if (fileName[i] == '.')
|
||||||
{
|
{
|
||||||
if (lastSep < lastDot)
|
// NOTE: We break on first '.' found
|
||||||
{
|
fileName[i] = '\0';
|
||||||
*lastDot = '\0'; // ...then remove it
|
break;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else *lastDot = '\0'; // Has extension separator with no path separator
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return result; // Return the modified string
|
return fileName;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get directory for a given fileName (with path)
|
// Get directory for a given fileName (with path)
|
||||||
|
|
@ -3449,7 +3438,7 @@ static void WindowDropCallback(GLFWwindow *window, int count, const char **paths
|
||||||
|
|
||||||
for (int i = 0; i < count; i++)
|
for (int i = 0; i < count; i++)
|
||||||
{
|
{
|
||||||
dropFilesPath[i] = (char *)malloc(sizeof(char)*MAX_FILEPATH_LENGTH); // Max path length using MAX_FILEPATH_LENGTH set to 256 char
|
dropFilesPath[i] = (char *)malloc(sizeof(char)*MAX_FILEPATH_LENGTH);
|
||||||
strcpy(dropFilesPath[i], paths[i]);
|
strcpy(dropFilesPath[i], paths[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
29952
src/external/mini_al.h
vendored
29952
src/external/mini_al.h
vendored
File diff suppressed because it is too large
Load Diff
31816
src/external/miniaudio.h
vendored
Normal file
31816
src/external/miniaudio.h
vendored
Normal file
File diff suppressed because it is too large
Load Diff
|
|
@ -285,6 +285,12 @@ void DrawCubeWires(Vector3 position, float width, float height, float length, Co
|
||||||
rlPopMatrix();
|
rlPopMatrix();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Draw cube wires (vector version)
|
||||||
|
void DrawCubeWiresV(Vector3 position, Vector3 size, Color color)
|
||||||
|
{
|
||||||
|
DrawCubeWires(position, size.x, size.y, size.z, color);
|
||||||
|
}
|
||||||
|
|
||||||
// Draw cube
|
// Draw cube
|
||||||
// NOTE: Cube position is the center position
|
// NOTE: Cube position is the center position
|
||||||
void DrawCubeTexture(Texture2D texture, Vector3 position, float width, float height, float length, Color color)
|
void DrawCubeTexture(Texture2D texture, Vector3 position, float width, float height, float length, Color color)
|
||||||
|
|
|
||||||
240
src/raudio.c
240
src/raudio.c
|
|
@ -1,6 +1,6 @@
|
||||||
/**********************************************************************************************
|
/**********************************************************************************************
|
||||||
*
|
*
|
||||||
* raudio - A simple and easy-to-use audio library based on mini_al
|
* raudio - A simple and easy-to-use audio library based on miniaudio
|
||||||
*
|
*
|
||||||
* FEATURES:
|
* FEATURES:
|
||||||
* - Manage audio device (init/close)
|
* - Manage audio device (init/close)
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
* supported by default, to remove support, just comment unrequired #define in this module
|
* supported by default, to remove support, just comment unrequired #define in this module
|
||||||
*
|
*
|
||||||
* DEPENDENCIES:
|
* DEPENDENCIES:
|
||||||
* mini_al.h - Audio device management lib (https://github.com/dr-soft/mini_al)
|
* miniaudio.h - Audio device management lib (https://github.com/dr-soft/miniaudio)
|
||||||
* stb_vorbis.h - Ogg audio files loading (http://www.nothings.org/stb_vorbis/)
|
* stb_vorbis.h - Ogg audio files loading (http://www.nothings.org/stb_vorbis/)
|
||||||
* dr_mp3.h - MP3 audio file loading (https://github.com/mackron/dr_libs)
|
* dr_mp3.h - MP3 audio file loading (https://github.com/mackron/dr_libs)
|
||||||
* dr_flac.h - FLAC audio file loading (https://github.com/mackron/dr_libs)
|
* dr_flac.h - FLAC audio file loading (https://github.com/mackron/dr_libs)
|
||||||
|
|
@ -35,7 +35,7 @@
|
||||||
*
|
*
|
||||||
* CONTRIBUTORS:
|
* CONTRIBUTORS:
|
||||||
* David Reid (github: @mackron) (Nov. 2017):
|
* David Reid (github: @mackron) (Nov. 2017):
|
||||||
* - Complete port to mini_al library
|
* - Complete port to miniaudio library
|
||||||
*
|
*
|
||||||
* Joshua Reisenauer (github: @kd7tck) (2015)
|
* Joshua Reisenauer (github: @kd7tck) (2015)
|
||||||
* - XM audio module support (jar_xm)
|
* - XM audio module support (jar_xm)
|
||||||
|
|
@ -77,11 +77,9 @@
|
||||||
#include "utils.h" // Required for: fopen() Android mapping
|
#include "utils.h" // Required for: fopen() Android mapping
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define MAL_NO_SDL
|
#define MA_NO_JACK
|
||||||
#define MAL_NO_JACK
|
#define MINIAUDIO_IMPLEMENTATION
|
||||||
#define MAL_NO_OPENAL
|
#include "external/miniaudio.h" // miniaudio library
|
||||||
#define MINI_AL_IMPLEMENTATION
|
|
||||||
#include "external/mini_al.h" // mini_al audio library
|
|
||||||
#undef PlaySound // Win32 API: windows.h > mmsystem.h defines PlaySound macro
|
#undef PlaySound // Win32 API: windows.h > mmsystem.h defines PlaySound macro
|
||||||
|
|
||||||
#include <stdlib.h> // Required for: malloc(), free()
|
#include <stdlib.h> // Required for: malloc(), free()
|
||||||
|
|
@ -208,9 +206,9 @@ void TraceLog(int msgType, const char *text, ...); // Show trace lo
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// mini_al AudioBuffer Functionality
|
// miniaudio AudioBuffer Functionality
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
#define DEVICE_FORMAT mal_format_f32
|
#define DEVICE_FORMAT ma_format_f32
|
||||||
#define DEVICE_CHANNELS 2
|
#define DEVICE_CHANNELS 2
|
||||||
#define DEVICE_SAMPLE_RATE 44100
|
#define DEVICE_SAMPLE_RATE 44100
|
||||||
|
|
||||||
|
|
@ -220,7 +218,7 @@ typedef enum { AUDIO_BUFFER_USAGE_STATIC = 0, AUDIO_BUFFER_USAGE_STREAM } AudioB
|
||||||
// NOTE: Slightly different logic is used when feeding data to the playback device depending on whether or not data is streamed
|
// NOTE: Slightly different logic is used when feeding data to the playback device depending on whether or not data is streamed
|
||||||
typedef struct rAudioBuffer rAudioBuffer;
|
typedef struct rAudioBuffer rAudioBuffer;
|
||||||
struct rAudioBuffer {
|
struct rAudioBuffer {
|
||||||
mal_dsp dsp; // Required for format conversion
|
ma_pcm_converter dsp; // Required for format conversion
|
||||||
float volume;
|
float volume;
|
||||||
float pitch;
|
float pitch;
|
||||||
bool playing;
|
bool playing;
|
||||||
|
|
@ -239,26 +237,26 @@ struct rAudioBuffer {
|
||||||
// NOTE: This system should probably be redesigned
|
// NOTE: This system should probably be redesigned
|
||||||
#define AudioBuffer rAudioBuffer
|
#define AudioBuffer rAudioBuffer
|
||||||
|
|
||||||
// mini_al global variables
|
// miniaudio global variables
|
||||||
static mal_context context;
|
static ma_context context;
|
||||||
static mal_device device;
|
static ma_device device;
|
||||||
static mal_mutex audioLock;
|
static ma_mutex audioLock;
|
||||||
static bool isAudioInitialized = MAL_FALSE;
|
static bool isAudioInitialized = MA_FALSE;
|
||||||
static float masterVolume = 1.0f;
|
static float masterVolume = 1.0f;
|
||||||
|
|
||||||
// Audio buffers are tracked in a linked list
|
// Audio buffers are tracked in a linked list
|
||||||
static AudioBuffer *firstAudioBuffer = NULL;
|
static AudioBuffer *firstAudioBuffer = NULL;
|
||||||
static AudioBuffer *lastAudioBuffer = NULL;
|
static AudioBuffer *lastAudioBuffer = NULL;
|
||||||
|
|
||||||
// mini_al functions declaration
|
// miniaudio functions declaration
|
||||||
static void OnLog(mal_context *pContext, mal_device *pDevice, const char *message);
|
static void OnLog(ma_context *pContext, ma_device *pDevice, ma_uint32 logLevel, const char *message);
|
||||||
static mal_uint32 OnSendAudioDataToDevice(mal_device *pDevice, mal_uint32 frameCount, void *pFramesOut);
|
static void OnSendAudioDataToDevice(ma_device *pDevice, void *pFramesOut, const void *pFramesInput, ma_uint32 frameCount);
|
||||||
static mal_uint32 OnAudioBufferDSPRead(mal_dsp *pDSP, mal_uint32 frameCount, void *pFramesOut, void *pUserData);
|
static ma_uint32 OnAudioBufferDSPRead(ma_pcm_converter *pDSP, void *pFramesOut, ma_uint32 frameCount, void *pUserData);
|
||||||
static void MixAudioFrames(float *framesOut, const float *framesIn, mal_uint32 frameCount, float localVolume);
|
static void MixAudioFrames(float *framesOut, const float *framesIn, ma_uint32 frameCount, float localVolume);
|
||||||
|
|
||||||
// AudioBuffer management functions declaration
|
// AudioBuffer management functions declaration
|
||||||
// NOTE: Those functions are not exposed by raylib... for the moment
|
// NOTE: Those functions are not exposed by raylib... for the moment
|
||||||
AudioBuffer *CreateAudioBuffer(mal_format format, mal_uint32 channels, mal_uint32 sampleRate, mal_uint32 bufferSizeInFrames, AudioBufferUsage usage);
|
AudioBuffer *CreateAudioBuffer(ma_format format, ma_uint32 channels, ma_uint32 sampleRate, ma_uint32 bufferSizeInFrames, AudioBufferUsage usage);
|
||||||
void DeleteAudioBuffer(AudioBuffer *audioBuffer);
|
void DeleteAudioBuffer(AudioBuffer *audioBuffer);
|
||||||
bool IsAudioBufferPlaying(AudioBuffer *audioBuffer);
|
bool IsAudioBufferPlaying(AudioBuffer *audioBuffer);
|
||||||
void PlayAudioBuffer(AudioBuffer *audioBuffer);
|
void PlayAudioBuffer(AudioBuffer *audioBuffer);
|
||||||
|
|
@ -270,35 +268,34 @@ void SetAudioBufferPitch(AudioBuffer *audioBuffer, float pitch);
|
||||||
void TrackAudioBuffer(AudioBuffer *audioBuffer);
|
void TrackAudioBuffer(AudioBuffer *audioBuffer);
|
||||||
void UntrackAudioBuffer(AudioBuffer *audioBuffer);
|
void UntrackAudioBuffer(AudioBuffer *audioBuffer);
|
||||||
|
|
||||||
|
|
||||||
// Log callback function
|
// Log callback function
|
||||||
static void OnLog(mal_context *pContext, mal_device *pDevice, const char *message)
|
static void OnLog(ma_context *pContext, ma_device *pDevice, ma_uint32 logLevel, const char *message)
|
||||||
{
|
{
|
||||||
(void)pContext;
|
(void)pContext;
|
||||||
(void)pDevice;
|
(void)pDevice;
|
||||||
|
|
||||||
TraceLog(LOG_ERROR, message); // All log messages from mini_al are errors
|
TraceLog(LOG_ERROR, message); // All log messages from miniaudio are errors
|
||||||
}
|
}
|
||||||
|
|
||||||
// Sending audio data to device callback function
|
// Sending audio data to device callback function
|
||||||
static mal_uint32 OnSendAudioDataToDevice(mal_device *pDevice, mal_uint32 frameCount, void *pFramesOut)
|
static void OnSendAudioDataToDevice(ma_device *pDevice, void *pFramesOut, const void *pFramesInput, ma_uint32 frameCount)
|
||||||
{
|
{
|
||||||
// This is where all of the mixing takes place.
|
// This is where all of the mixing takes place.
|
||||||
(void)pDevice;
|
(void)pDevice;
|
||||||
|
|
||||||
// Mixing is basically just an accumulation. We need to initialize the output buffer to 0.
|
// Mixing is basically just an accumulation. We need to initialize the output buffer to 0.
|
||||||
memset(pFramesOut, 0, frameCount*pDevice->channels*mal_get_bytes_per_sample(pDevice->format));
|
memset(pFramesOut, 0, frameCount*pDevice->playback.channels*ma_get_bytes_per_sample(pDevice->playback.format));
|
||||||
|
|
||||||
// Using a mutex here for thread-safety which makes things not real-time. This is unlikely to be necessary for this project, but may
|
// Using a mutex here for thread-safety which makes things not real-time. This is unlikely to be necessary for this project, but may
|
||||||
// want to consider how you might want to avoid this.
|
// want to consider how you might want to avoid this.
|
||||||
mal_mutex_lock(&audioLock);
|
ma_mutex_lock(&audioLock);
|
||||||
{
|
{
|
||||||
for (AudioBuffer *audioBuffer = firstAudioBuffer; audioBuffer != NULL; audioBuffer = audioBuffer->next)
|
for (AudioBuffer *audioBuffer = firstAudioBuffer; audioBuffer != NULL; audioBuffer = audioBuffer->next)
|
||||||
{
|
{
|
||||||
// Ignore stopped or paused sounds.
|
// Ignore stopped or paused sounds.
|
||||||
if (!audioBuffer->playing || audioBuffer->paused) continue;
|
if (!audioBuffer->playing || audioBuffer->paused) continue;
|
||||||
|
|
||||||
mal_uint32 framesRead = 0;
|
ma_uint32 framesRead = 0;
|
||||||
for (;;)
|
for (;;)
|
||||||
{
|
{
|
||||||
if (framesRead > frameCount)
|
if (framesRead > frameCount)
|
||||||
|
|
@ -310,21 +307,21 @@ static mal_uint32 OnSendAudioDataToDevice(mal_device *pDevice, mal_uint32 frameC
|
||||||
if (framesRead == frameCount) break;
|
if (framesRead == frameCount) break;
|
||||||
|
|
||||||
// Just read as much data as we can from the stream.
|
// Just read as much data as we can from the stream.
|
||||||
mal_uint32 framesToRead = (frameCount - framesRead);
|
ma_uint32 framesToRead = (frameCount - framesRead);
|
||||||
while (framesToRead > 0)
|
while (framesToRead > 0)
|
||||||
{
|
{
|
||||||
float tempBuffer[1024]; // 512 frames for stereo.
|
float tempBuffer[1024]; // 512 frames for stereo.
|
||||||
|
|
||||||
mal_uint32 framesToReadRightNow = framesToRead;
|
ma_uint32 framesToReadRightNow = framesToRead;
|
||||||
if (framesToReadRightNow > sizeof(tempBuffer)/sizeof(tempBuffer[0])/DEVICE_CHANNELS)
|
if (framesToReadRightNow > sizeof(tempBuffer)/sizeof(tempBuffer[0])/DEVICE_CHANNELS)
|
||||||
{
|
{
|
||||||
framesToReadRightNow = sizeof(tempBuffer)/sizeof(tempBuffer[0])/DEVICE_CHANNELS;
|
framesToReadRightNow = sizeof(tempBuffer)/sizeof(tempBuffer[0])/DEVICE_CHANNELS;
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_uint32 framesJustRead = (mal_uint32)mal_dsp_read(&audioBuffer->dsp, framesToReadRightNow, tempBuffer, audioBuffer->dsp.pUserData);
|
ma_uint32 framesJustRead = (ma_uint32)ma_pcm_converter_read(&audioBuffer->dsp, tempBuffer, framesToReadRightNow);
|
||||||
if (framesJustRead > 0)
|
if (framesJustRead > 0)
|
||||||
{
|
{
|
||||||
float *framesOut = (float *)pFramesOut + (framesRead*device.channels);
|
float *framesOut = (float *)pFramesOut + (framesRead*device.playback.channels);
|
||||||
float *framesIn = tempBuffer;
|
float *framesIn = tempBuffer;
|
||||||
MixAudioFrames(framesOut, framesIn, framesJustRead, audioBuffer->volume);
|
MixAudioFrames(framesOut, framesIn, framesJustRead, audioBuffer->volume);
|
||||||
|
|
||||||
|
|
@ -357,18 +354,16 @@ static mal_uint32 OnSendAudioDataToDevice(mal_device *pDevice, mal_uint32 frameC
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_mutex_unlock(&audioLock);
|
ma_mutex_unlock(&audioLock);
|
||||||
|
|
||||||
return frameCount; // We always output the same number of frames that were originally requested.
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// DSP read from audio buffer callback function
|
// DSP read from audio buffer callback function
|
||||||
static mal_uint32 OnAudioBufferDSPRead(mal_dsp *pDSP, mal_uint32 frameCount, void *pFramesOut, void *pUserData)
|
static ma_uint32 OnAudioBufferDSPRead(ma_pcm_converter *pDSP, void *pFramesOut, ma_uint32 frameCount, void *pUserData)
|
||||||
{
|
{
|
||||||
AudioBuffer *audioBuffer = (AudioBuffer *)pUserData;
|
AudioBuffer *audioBuffer = (AudioBuffer *)pUserData;
|
||||||
|
|
||||||
mal_uint32 subBufferSizeInFrames = (audioBuffer->bufferSizeInFrames > 1)? audioBuffer->bufferSizeInFrames/2 : audioBuffer->bufferSizeInFrames;
|
ma_uint32 subBufferSizeInFrames = (audioBuffer->bufferSizeInFrames > 1)? audioBuffer->bufferSizeInFrames/2 : audioBuffer->bufferSizeInFrames;
|
||||||
mal_uint32 currentSubBufferIndex = audioBuffer->frameCursorPos/subBufferSizeInFrames;
|
ma_uint32 currentSubBufferIndex = audioBuffer->frameCursorPos/subBufferSizeInFrames;
|
||||||
|
|
||||||
if (currentSubBufferIndex > 1)
|
if (currentSubBufferIndex > 1)
|
||||||
{
|
{
|
||||||
|
|
@ -381,10 +376,10 @@ static mal_uint32 OnAudioBufferDSPRead(mal_dsp *pDSP, mal_uint32 frameCount, voi
|
||||||
isSubBufferProcessed[0] = audioBuffer->isSubBufferProcessed[0];
|
isSubBufferProcessed[0] = audioBuffer->isSubBufferProcessed[0];
|
||||||
isSubBufferProcessed[1] = audioBuffer->isSubBufferProcessed[1];
|
isSubBufferProcessed[1] = audioBuffer->isSubBufferProcessed[1];
|
||||||
|
|
||||||
mal_uint32 frameSizeInBytes = mal_get_bytes_per_sample(audioBuffer->dsp.formatConverterIn.config.formatIn)*audioBuffer->dsp.formatConverterIn.config.channels;
|
ma_uint32 frameSizeInBytes = ma_get_bytes_per_sample(audioBuffer->dsp.formatConverterIn.config.formatIn)*audioBuffer->dsp.formatConverterIn.config.channels;
|
||||||
|
|
||||||
// Fill out every frame until we find a buffer that's marked as processed. Then fill the remainder with 0.
|
// Fill out every frame until we find a buffer that's marked as processed. Then fill the remainder with 0.
|
||||||
mal_uint32 framesRead = 0;
|
ma_uint32 framesRead = 0;
|
||||||
for (;;)
|
for (;;)
|
||||||
{
|
{
|
||||||
// We break from this loop differently depending on the buffer's usage. For static buffers, we simply fill as much data as we can. For
|
// We break from this loop differently depending on the buffer's usage. For static buffers, we simply fill as much data as we can. For
|
||||||
|
|
@ -398,21 +393,21 @@ static mal_uint32 OnAudioBufferDSPRead(mal_dsp *pDSP, mal_uint32 frameCount, voi
|
||||||
if (isSubBufferProcessed[currentSubBufferIndex]) break;
|
if (isSubBufferProcessed[currentSubBufferIndex]) break;
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_uint32 totalFramesRemaining = (frameCount - framesRead);
|
ma_uint32 totalFramesRemaining = (frameCount - framesRead);
|
||||||
if (totalFramesRemaining == 0) break;
|
if (totalFramesRemaining == 0) break;
|
||||||
|
|
||||||
mal_uint32 framesRemainingInOutputBuffer;
|
ma_uint32 framesRemainingInOutputBuffer;
|
||||||
if (audioBuffer->usage == AUDIO_BUFFER_USAGE_STATIC)
|
if (audioBuffer->usage == AUDIO_BUFFER_USAGE_STATIC)
|
||||||
{
|
{
|
||||||
framesRemainingInOutputBuffer = audioBuffer->bufferSizeInFrames - audioBuffer->frameCursorPos;
|
framesRemainingInOutputBuffer = audioBuffer->bufferSizeInFrames - audioBuffer->frameCursorPos;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
mal_uint32 firstFrameIndexOfThisSubBuffer = subBufferSizeInFrames * currentSubBufferIndex;
|
ma_uint32 firstFrameIndexOfThisSubBuffer = subBufferSizeInFrames * currentSubBufferIndex;
|
||||||
framesRemainingInOutputBuffer = subBufferSizeInFrames - (audioBuffer->frameCursorPos - firstFrameIndexOfThisSubBuffer);
|
framesRemainingInOutputBuffer = subBufferSizeInFrames - (audioBuffer->frameCursorPos - firstFrameIndexOfThisSubBuffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_uint32 framesToRead = totalFramesRemaining;
|
ma_uint32 framesToRead = totalFramesRemaining;
|
||||||
if (framesToRead > framesRemainingInOutputBuffer) framesToRead = framesRemainingInOutputBuffer;
|
if (framesToRead > framesRemainingInOutputBuffer) framesToRead = framesRemainingInOutputBuffer;
|
||||||
|
|
||||||
memcpy((unsigned char *)pFramesOut + (framesRead*frameSizeInBytes), audioBuffer->buffer + (audioBuffer->frameCursorPos*frameSizeInBytes), framesToRead*frameSizeInBytes);
|
memcpy((unsigned char *)pFramesOut + (framesRead*frameSizeInBytes), audioBuffer->buffer + (audioBuffer->frameCursorPos*frameSizeInBytes), framesToRead*frameSizeInBytes);
|
||||||
|
|
@ -437,7 +432,7 @@ static mal_uint32 OnAudioBufferDSPRead(mal_dsp *pDSP, mal_uint32 frameCount, voi
|
||||||
}
|
}
|
||||||
|
|
||||||
// Zero-fill excess.
|
// Zero-fill excess.
|
||||||
mal_uint32 totalFramesRemaining = (frameCount - framesRead);
|
ma_uint32 totalFramesRemaining = (frameCount - framesRead);
|
||||||
if (totalFramesRemaining > 0)
|
if (totalFramesRemaining > 0)
|
||||||
{
|
{
|
||||||
memset((unsigned char *)pFramesOut + (framesRead*frameSizeInBytes), 0, totalFramesRemaining*frameSizeInBytes);
|
memset((unsigned char *)pFramesOut + (framesRead*frameSizeInBytes), 0, totalFramesRemaining*frameSizeInBytes);
|
||||||
|
|
@ -453,16 +448,16 @@ static mal_uint32 OnAudioBufferDSPRead(mal_dsp *pDSP, mal_uint32 frameCount, voi
|
||||||
|
|
||||||
// This is the main mixing function. Mixing is pretty simple in this project - it's just an accumulation.
|
// This is the main mixing function. Mixing is pretty simple in this project - it's just an accumulation.
|
||||||
// NOTE: framesOut is both an input and an output. It will be initially filled with zeros outside of this function.
|
// NOTE: framesOut is both an input and an output. It will be initially filled with zeros outside of this function.
|
||||||
static void MixAudioFrames(float *framesOut, const float *framesIn, mal_uint32 frameCount, float localVolume)
|
static void MixAudioFrames(float *framesOut, const float *framesIn, ma_uint32 frameCount, float localVolume)
|
||||||
{
|
{
|
||||||
for (mal_uint32 iFrame = 0; iFrame < frameCount; ++iFrame)
|
for (ma_uint32 iFrame = 0; iFrame < frameCount; ++iFrame)
|
||||||
{
|
{
|
||||||
for (mal_uint32 iChannel = 0; iChannel < device.channels; ++iChannel)
|
for (ma_uint32 iChannel = 0; iChannel < device.playback.channels; ++iChannel)
|
||||||
{
|
{
|
||||||
float *frameOut = framesOut + (iFrame*device.channels);
|
float *frameOut = framesOut + (iFrame*device.playback.channels);
|
||||||
const float *frameIn = framesIn + (iFrame*device.channels);
|
const float *frameIn = framesIn + (iFrame*device.playback.channels);
|
||||||
|
|
||||||
frameOut[iChannel] += frameIn[iChannel]*masterVolume*localVolume;
|
frameOut[iChannel] += (frameIn[iChannel]*masterVolume*localVolume);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -474,54 +469,64 @@ static void MixAudioFrames(float *framesOut, const float *framesIn, mal_uint32 f
|
||||||
void InitAudioDevice(void)
|
void InitAudioDevice(void)
|
||||||
{
|
{
|
||||||
// Context.
|
// Context.
|
||||||
mal_context_config contextConfig = mal_context_config_init(OnLog);
|
ma_context_config contextConfig = ma_context_config_init();
|
||||||
mal_result result = mal_context_init(NULL, 0, &contextConfig, &context);
|
contextConfig.logCallback = OnLog;
|
||||||
if (result != MAL_SUCCESS)
|
ma_result result = ma_context_init(NULL, 0, &contextConfig, &context);
|
||||||
|
if (result != MA_SUCCESS)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "Failed to initialize audio context");
|
TraceLog(LOG_ERROR, "Failed to initialize audio context");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Device. Using the default device. Format is floating point because it simplifies mixing.
|
// Device. Using the default device. Format is floating point because it simplifies mixing.
|
||||||
mal_device_config deviceConfig = mal_device_config_init(DEVICE_FORMAT, DEVICE_CHANNELS, DEVICE_SAMPLE_RATE, NULL, OnSendAudioDataToDevice);
|
ma_device_config config = ma_device_config_init(ma_device_type_playback);
|
||||||
|
config.playback.pDeviceID = NULL; // NULL for the default playback device.
|
||||||
|
config.playback.format = DEVICE_FORMAT;
|
||||||
|
config.playback.channels = DEVICE_CHANNELS;
|
||||||
|
config.capture.pDeviceID = NULL; // NULL for the default capture device.
|
||||||
|
config.capture.format = ma_format_s16;
|
||||||
|
config.capture.channels = 1;
|
||||||
|
config.sampleRate = DEVICE_SAMPLE_RATE;
|
||||||
|
config.dataCallback = OnSendAudioDataToDevice;
|
||||||
|
config.pUserData = NULL;
|
||||||
|
|
||||||
result = mal_device_init(&context, mal_device_type_playback, NULL, &deviceConfig, NULL, &device);
|
result = ma_device_init(&context, &config, &device);
|
||||||
if (result != MAL_SUCCESS)
|
if (result != MA_SUCCESS)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "Failed to initialize audio playback device");
|
TraceLog(LOG_ERROR, "Failed to initialize audio playback device");
|
||||||
mal_context_uninit(&context);
|
ma_context_uninit(&context);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Keep the device running the whole time. May want to consider doing something a bit smarter and only have the device running
|
// Keep the device running the whole time. May want to consider doing something a bit smarter and only have the device running
|
||||||
// while there's at least one sound being played.
|
// while there's at least one sound being played.
|
||||||
result = mal_device_start(&device);
|
result = ma_device_start(&device);
|
||||||
if (result != MAL_SUCCESS)
|
if (result != MA_SUCCESS)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "Failed to start audio playback device");
|
TraceLog(LOG_ERROR, "Failed to start audio playback device");
|
||||||
mal_device_uninit(&device);
|
ma_device_uninit(&device);
|
||||||
mal_context_uninit(&context);
|
ma_context_uninit(&context);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Mixing happens on a seperate thread which means we need to synchronize. I'm using a mutex here to make things simple, but may
|
// Mixing happens on a seperate thread which means we need to synchronize. I'm using a mutex here to make things simple, but may
|
||||||
// want to look at something a bit smarter later on to keep everything real-time, if that's necessary.
|
// want to look at something a bit smarter later on to keep everything real-time, if that's necessary.
|
||||||
if (mal_mutex_init(&context, &audioLock) != MAL_SUCCESS)
|
if (ma_mutex_init(&context, &audioLock) != MA_SUCCESS)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "Failed to create mutex for audio mixing");
|
TraceLog(LOG_ERROR, "Failed to create mutex for audio mixing");
|
||||||
mal_device_uninit(&device);
|
ma_device_uninit(&device);
|
||||||
mal_context_uninit(&context);
|
ma_context_uninit(&context);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
TraceLog(LOG_INFO, "Audio device initialized successfully: %s", device.name);
|
TraceLog(LOG_INFO, "Audio device initialized successfully");
|
||||||
TraceLog(LOG_INFO, "Audio backend: mini_al / %s", mal_get_backend_name(context.backend));
|
TraceLog(LOG_INFO, "Audio backend: miniaudio / %s", ma_get_backend_name(context.backend));
|
||||||
TraceLog(LOG_INFO, "Audio format: %s -> %s", mal_get_format_name(device.format), mal_get_format_name(device.internalFormat));
|
TraceLog(LOG_INFO, "Audio format: %s -> %s", ma_get_format_name(device.playback.format), ma_get_format_name(device.playback.internalFormat));
|
||||||
TraceLog(LOG_INFO, "Audio channels: %d -> %d", device.channels, device.internalChannels);
|
TraceLog(LOG_INFO, "Audio channels: %d -> %d", device.playback.channels, device.playback.internalChannels);
|
||||||
TraceLog(LOG_INFO, "Audio sample rate: %d -> %d", device.sampleRate, device.internalSampleRate);
|
TraceLog(LOG_INFO, "Audio sample rate: %d -> %d", device.sampleRate, device.playback.internalSampleRate);
|
||||||
TraceLog(LOG_INFO, "Audio buffer size: %d", device.bufferSizeInFrames);
|
TraceLog(LOG_INFO, "Audio buffer size: %d", device.playback.internalBufferSizeInFrames);
|
||||||
|
|
||||||
isAudioInitialized = MAL_TRUE;
|
isAudioInitialized = MA_TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Close the audio device for all contexts
|
// Close the audio device for all contexts
|
||||||
|
|
@ -533,9 +538,9 @@ void CloseAudioDevice(void)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_mutex_uninit(&audioLock);
|
ma_mutex_uninit(&audioLock);
|
||||||
mal_device_uninit(&device);
|
ma_device_uninit(&device);
|
||||||
mal_context_uninit(&context);
|
ma_context_uninit(&context);
|
||||||
|
|
||||||
TraceLog(LOG_INFO, "Audio device closed successfully");
|
TraceLog(LOG_INFO, "Audio device closed successfully");
|
||||||
}
|
}
|
||||||
|
|
@ -560,9 +565,9 @@ void SetMasterVolume(float volume)
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
|
|
||||||
// Create a new audio buffer. Initially filled with silence
|
// Create a new audio buffer. Initially filled with silence
|
||||||
AudioBuffer *CreateAudioBuffer(mal_format format, mal_uint32 channels, mal_uint32 sampleRate, mal_uint32 bufferSizeInFrames, AudioBufferUsage usage)
|
AudioBuffer *CreateAudioBuffer(ma_format format, ma_uint32 channels, ma_uint32 sampleRate, ma_uint32 bufferSizeInFrames, AudioBufferUsage usage)
|
||||||
{
|
{
|
||||||
AudioBuffer *audioBuffer = (AudioBuffer *)calloc(sizeof(*audioBuffer) + (bufferSizeInFrames*channels*mal_get_bytes_per_sample(format)), 1);
|
AudioBuffer *audioBuffer = (AudioBuffer *)calloc(sizeof(*audioBuffer) + (bufferSizeInFrames*channels*ma_get_bytes_per_sample(format)), 1);
|
||||||
if (audioBuffer == NULL)
|
if (audioBuffer == NULL)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "CreateAudioBuffer() : Failed to allocate memory for audio buffer");
|
TraceLog(LOG_ERROR, "CreateAudioBuffer() : Failed to allocate memory for audio buffer");
|
||||||
|
|
@ -570,7 +575,7 @@ AudioBuffer *CreateAudioBuffer(mal_format format, mal_uint32 channels, mal_uint3
|
||||||
}
|
}
|
||||||
|
|
||||||
// We run audio data through a format converter.
|
// We run audio data through a format converter.
|
||||||
mal_dsp_config dspConfig;
|
ma_pcm_converter_config dspConfig;
|
||||||
memset(&dspConfig, 0, sizeof(dspConfig));
|
memset(&dspConfig, 0, sizeof(dspConfig));
|
||||||
dspConfig.formatIn = format;
|
dspConfig.formatIn = format;
|
||||||
dspConfig.formatOut = DEVICE_FORMAT;
|
dspConfig.formatOut = DEVICE_FORMAT;
|
||||||
|
|
@ -580,20 +585,21 @@ AudioBuffer *CreateAudioBuffer(mal_format format, mal_uint32 channels, mal_uint3
|
||||||
dspConfig.sampleRateOut = DEVICE_SAMPLE_RATE;
|
dspConfig.sampleRateOut = DEVICE_SAMPLE_RATE;
|
||||||
dspConfig.onRead = OnAudioBufferDSPRead;
|
dspConfig.onRead = OnAudioBufferDSPRead;
|
||||||
dspConfig.pUserData = audioBuffer;
|
dspConfig.pUserData = audioBuffer;
|
||||||
dspConfig.allowDynamicSampleRate = MAL_TRUE; // <-- Required for pitch shifting.
|
dspConfig.allowDynamicSampleRate = MA_TRUE; // <-- Required for pitch shifting.
|
||||||
mal_result resultMAL = mal_dsp_init(&dspConfig, &audioBuffer->dsp);
|
ma_result result = ma_pcm_converter_init(&dspConfig, &audioBuffer->dsp);
|
||||||
if (resultMAL != MAL_SUCCESS)
|
|
||||||
|
if (result != MA_SUCCESS)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "CreateAudioBuffer() : Failed to create data conversion pipeline");
|
TraceLog(LOG_ERROR, "CreateAudioBuffer() : Failed to create data conversion pipeline");
|
||||||
free(audioBuffer);
|
free(audioBuffer);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
audioBuffer->volume = 1;
|
audioBuffer->volume = 1.0f;
|
||||||
audioBuffer->pitch = 1;
|
audioBuffer->pitch = 1.0f;
|
||||||
audioBuffer->playing = 0;
|
audioBuffer->playing = false;
|
||||||
audioBuffer->paused = 0;
|
audioBuffer->paused = false;
|
||||||
audioBuffer->looping = 0;
|
audioBuffer->looping = false;
|
||||||
audioBuffer->usage = usage;
|
audioBuffer->usage = usage;
|
||||||
audioBuffer->bufferSizeInFrames = bufferSizeInFrames;
|
audioBuffer->bufferSizeInFrames = bufferSizeInFrames;
|
||||||
audioBuffer->frameCursorPos = 0;
|
audioBuffer->frameCursorPos = 0;
|
||||||
|
|
@ -696,7 +702,7 @@ void SetAudioBufferVolume(AudioBuffer *audioBuffer, float volume)
|
||||||
{
|
{
|
||||||
if (audioBuffer == NULL)
|
if (audioBuffer == NULL)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "SetAudioBufferVolume() : No audio buffer");
|
TraceLog(LOG_WARNING, "SetAudioBufferVolume() : No audio buffer");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -708,24 +714,24 @@ void SetAudioBufferPitch(AudioBuffer *audioBuffer, float pitch)
|
||||||
{
|
{
|
||||||
if (audioBuffer == NULL)
|
if (audioBuffer == NULL)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "SetAudioBufferPitch() : No audio buffer");
|
TraceLog(LOG_WARNING, "SetAudioBufferPitch() : No audio buffer");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
float pitchMul = pitch / audioBuffer->pitch;
|
float pitchMul = pitch/audioBuffer->pitch;
|
||||||
|
|
||||||
// Pitching is just an adjustment of the sample rate. Note that this changes the duration of the sound - higher pitches
|
// Pitching is just an adjustment of the sample rate. Note that this changes the duration of the sound - higher pitches
|
||||||
// will make the sound faster; lower pitches make it slower.
|
// will make the sound faster; lower pitches make it slower.
|
||||||
mal_uint32 newOutputSampleRate = (mal_uint32)((float)audioBuffer->dsp.src.config.sampleRateOut / pitchMul);
|
ma_uint32 newOutputSampleRate = (ma_uint32)((float)audioBuffer->dsp.src.config.sampleRateOut / pitchMul);
|
||||||
audioBuffer->pitch *= (float)audioBuffer->dsp.src.config.sampleRateOut / newOutputSampleRate;
|
audioBuffer->pitch *= (float)audioBuffer->dsp.src.config.sampleRateOut / newOutputSampleRate;
|
||||||
|
|
||||||
mal_dsp_set_output_sample_rate(&audioBuffer->dsp, newOutputSampleRate);
|
ma_pcm_converter_set_output_sample_rate(&audioBuffer->dsp, newOutputSampleRate);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Track audio buffer to linked list next position
|
// Track audio buffer to linked list next position
|
||||||
void TrackAudioBuffer(AudioBuffer *audioBuffer)
|
void TrackAudioBuffer(AudioBuffer *audioBuffer)
|
||||||
{
|
{
|
||||||
mal_mutex_lock(&audioLock);
|
ma_mutex_lock(&audioLock);
|
||||||
|
|
||||||
{
|
{
|
||||||
if (firstAudioBuffer == NULL) firstAudioBuffer = audioBuffer;
|
if (firstAudioBuffer == NULL) firstAudioBuffer = audioBuffer;
|
||||||
|
|
@ -738,13 +744,13 @@ void TrackAudioBuffer(AudioBuffer *audioBuffer)
|
||||||
lastAudioBuffer = audioBuffer;
|
lastAudioBuffer = audioBuffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_mutex_unlock(&audioLock);
|
ma_mutex_unlock(&audioLock);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Untrack audio buffer from linked list
|
// Untrack audio buffer from linked list
|
||||||
void UntrackAudioBuffer(AudioBuffer *audioBuffer)
|
void UntrackAudioBuffer(AudioBuffer *audioBuffer)
|
||||||
{
|
{
|
||||||
mal_mutex_lock(&audioLock);
|
ma_mutex_lock(&audioLock);
|
||||||
|
|
||||||
{
|
{
|
||||||
if (audioBuffer->prev == NULL) firstAudioBuffer = audioBuffer->next;
|
if (audioBuffer->prev == NULL) firstAudioBuffer = audioBuffer->next;
|
||||||
|
|
@ -757,7 +763,7 @@ void UntrackAudioBuffer(AudioBuffer *audioBuffer)
|
||||||
audioBuffer->next = NULL;
|
audioBuffer->next = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_mutex_unlock(&audioLock);
|
ma_mutex_unlock(&audioLock);
|
||||||
}
|
}
|
||||||
|
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
|
|
@ -828,7 +834,7 @@ Sound LoadSoundFromWave(Wave wave)
|
||||||
|
|
||||||
if (wave.data != NULL)
|
if (wave.data != NULL)
|
||||||
{
|
{
|
||||||
// When using mini_al we need to do our own mixing. To simplify this we need convert the format of each sound to be consistent with
|
// When using miniaudio we need to do our own mixing. To simplify this we need convert the format of each sound to be consistent with
|
||||||
// the format used to open the playback device. We can do this two ways:
|
// the format used to open the playback device. We can do this two ways:
|
||||||
//
|
//
|
||||||
// 1) Convert the whole sound in one go at load time (here).
|
// 1) Convert the whole sound in one go at load time (here).
|
||||||
|
|
@ -836,16 +842,16 @@ Sound LoadSoundFromWave(Wave wave)
|
||||||
//
|
//
|
||||||
// I have decided on the first option because it offloads work required for the format conversion to the to the loading stage.
|
// I have decided on the first option because it offloads work required for the format conversion to the to the loading stage.
|
||||||
// The downside to this is that it uses more memory if the original sound is u8 or s16.
|
// The downside to this is that it uses more memory if the original sound is u8 or s16.
|
||||||
mal_format formatIn = ((wave.sampleSize == 8)? mal_format_u8 : ((wave.sampleSize == 16)? mal_format_s16 : mal_format_f32));
|
ma_format formatIn = ((wave.sampleSize == 8)? ma_format_u8 : ((wave.sampleSize == 16)? ma_format_s16 : ma_format_f32));
|
||||||
mal_uint32 frameCountIn = wave.sampleCount/wave.channels;
|
ma_uint32 frameCountIn = wave.sampleCount/wave.channels;
|
||||||
|
|
||||||
mal_uint32 frameCount = (mal_uint32)mal_convert_frames(NULL, DEVICE_FORMAT, DEVICE_CHANNELS, DEVICE_SAMPLE_RATE, NULL, formatIn, wave.channels, wave.sampleRate, frameCountIn);
|
ma_uint32 frameCount = (ma_uint32)ma_convert_frames(NULL, DEVICE_FORMAT, DEVICE_CHANNELS, DEVICE_SAMPLE_RATE, NULL, formatIn, wave.channels, wave.sampleRate, frameCountIn);
|
||||||
if (frameCount == 0) TraceLog(LOG_WARNING, "LoadSoundFromWave() : Failed to get frame count for format conversion");
|
if (frameCount == 0) TraceLog(LOG_WARNING, "LoadSoundFromWave() : Failed to get frame count for format conversion");
|
||||||
|
|
||||||
AudioBuffer* audioBuffer = CreateAudioBuffer(DEVICE_FORMAT, DEVICE_CHANNELS, DEVICE_SAMPLE_RATE, frameCount, AUDIO_BUFFER_USAGE_STATIC);
|
AudioBuffer* audioBuffer = CreateAudioBuffer(DEVICE_FORMAT, DEVICE_CHANNELS, DEVICE_SAMPLE_RATE, frameCount, AUDIO_BUFFER_USAGE_STATIC);
|
||||||
if (audioBuffer == NULL) TraceLog(LOG_WARNING, "LoadSoundFromWave() : Failed to create audio buffer");
|
if (audioBuffer == NULL) TraceLog(LOG_WARNING, "LoadSoundFromWave() : Failed to create audio buffer");
|
||||||
|
|
||||||
frameCount = (mal_uint32)mal_convert_frames(audioBuffer->buffer, audioBuffer->dsp.formatConverterIn.config.formatIn, audioBuffer->dsp.formatConverterIn.config.channels, audioBuffer->dsp.src.config.sampleRateIn, wave.data, formatIn, wave.channels, wave.sampleRate, frameCountIn);
|
frameCount = (ma_uint32)ma_convert_frames(audioBuffer->buffer, audioBuffer->dsp.formatConverterIn.config.formatIn, audioBuffer->dsp.formatConverterIn.config.channels, audioBuffer->dsp.src.config.sampleRateIn, wave.data, formatIn, wave.channels, wave.sampleRate, frameCountIn);
|
||||||
if (frameCount == 0) TraceLog(LOG_WARNING, "LoadSoundFromWave() : Format conversion failed");
|
if (frameCount == 0) TraceLog(LOG_WARNING, "LoadSoundFromWave() : Format conversion failed");
|
||||||
|
|
||||||
sound.audioBuffer = audioBuffer;
|
sound.audioBuffer = audioBuffer;
|
||||||
|
|
@ -885,7 +891,7 @@ void UpdateSound(Sound sound, const void *data, int samplesCount)
|
||||||
StopAudioBuffer(audioBuffer);
|
StopAudioBuffer(audioBuffer);
|
||||||
|
|
||||||
// TODO: May want to lock/unlock this since this data buffer is read at mixing time.
|
// TODO: May want to lock/unlock this since this data buffer is read at mixing time.
|
||||||
memcpy(audioBuffer->buffer, data, samplesCount*audioBuffer->dsp.formatConverterIn.config.channels*mal_get_bytes_per_sample(audioBuffer->dsp.formatConverterIn.config.formatIn));
|
memcpy(audioBuffer->buffer, data, samplesCount*audioBuffer->dsp.formatConverterIn.config.channels*ma_get_bytes_per_sample(audioBuffer->dsp.formatConverterIn.config.formatIn));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Export wave data to file
|
// Export wave data to file
|
||||||
|
|
@ -999,12 +1005,12 @@ void SetSoundPitch(Sound sound, float pitch)
|
||||||
// Convert wave data to desired format
|
// Convert wave data to desired format
|
||||||
void WaveFormat(Wave *wave, int sampleRate, int sampleSize, int channels)
|
void WaveFormat(Wave *wave, int sampleRate, int sampleSize, int channels)
|
||||||
{
|
{
|
||||||
mal_format formatIn = ((wave->sampleSize == 8)? mal_format_u8 : ((wave->sampleSize == 16)? mal_format_s16 : mal_format_f32));
|
ma_format formatIn = ((wave->sampleSize == 8)? ma_format_u8 : ((wave->sampleSize == 16)? ma_format_s16 : ma_format_f32));
|
||||||
mal_format formatOut = (( sampleSize == 8)? mal_format_u8 : (( sampleSize == 16)? mal_format_s16 : mal_format_f32));
|
ma_format formatOut = (( sampleSize == 8)? ma_format_u8 : (( sampleSize == 16)? ma_format_s16 : ma_format_f32));
|
||||||
|
|
||||||
mal_uint32 frameCountIn = wave->sampleCount; // Is wave->sampleCount actually the frame count? That terminology needs to change, if so.
|
ma_uint32 frameCountIn = wave->sampleCount; // Is wave->sampleCount actually the frame count? That terminology needs to change, if so.
|
||||||
|
|
||||||
mal_uint32 frameCount = (mal_uint32)mal_convert_frames(NULL, formatOut, channels, sampleRate, NULL, formatIn, wave->channels, wave->sampleRate, frameCountIn);
|
ma_uint32 frameCount = (ma_uint32)ma_convert_frames(NULL, formatOut, channels, sampleRate, NULL, formatIn, wave->channels, wave->sampleRate, frameCountIn);
|
||||||
if (frameCount == 0)
|
if (frameCount == 0)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "WaveFormat() : Failed to get frame count for format conversion.");
|
TraceLog(LOG_ERROR, "WaveFormat() : Failed to get frame count for format conversion.");
|
||||||
|
|
@ -1013,7 +1019,7 @@ void WaveFormat(Wave *wave, int sampleRate, int sampleSize, int channels)
|
||||||
|
|
||||||
void *data = malloc(frameCount*channels*(sampleSize/8));
|
void *data = malloc(frameCount*channels*(sampleSize/8));
|
||||||
|
|
||||||
frameCount = (mal_uint32)mal_convert_frames(data, formatOut, channels, sampleRate, wave->data, formatIn, wave->channels, wave->sampleRate, frameCountIn);
|
frameCount = (ma_uint32)ma_convert_frames(data, formatOut, channels, sampleRate, wave->data, formatIn, wave->channels, wave->sampleRate, frameCountIn);
|
||||||
if (frameCount == 0)
|
if (frameCount == 0)
|
||||||
{
|
{
|
||||||
TraceLog(LOG_ERROR, "WaveFormat() : Format conversion failed.");
|
TraceLog(LOG_ERROR, "WaveFormat() : Format conversion failed.");
|
||||||
|
|
@ -1288,7 +1294,7 @@ void PlayMusicStream(Music music)
|
||||||
// // NOTE: In case window is minimized, music stream is stopped,
|
// // NOTE: In case window is minimized, music stream is stopped,
|
||||||
// // just make sure to play again on window restore
|
// // just make sure to play again on window restore
|
||||||
// if (IsMusicPlaying(music)) PlayMusicStream(music);
|
// if (IsMusicPlaying(music)) PlayMusicStream(music);
|
||||||
mal_uint32 frameCursorPos = audioBuffer->frameCursorPos;
|
ma_uint32 frameCursorPos = audioBuffer->frameCursorPos;
|
||||||
|
|
||||||
PlayAudioStream(music->stream); // <-- This resets the cursor position.
|
PlayAudioStream(music->stream); // <-- This resets the cursor position.
|
||||||
|
|
||||||
|
|
@ -1513,10 +1519,10 @@ AudioStream InitAudioStream(unsigned int sampleRate, unsigned int sampleSize, un
|
||||||
stream.channels = 1; // Fallback to mono channel
|
stream.channels = 1; // Fallback to mono channel
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_format formatIn = ((stream.sampleSize == 8)? mal_format_u8 : ((stream.sampleSize == 16)? mal_format_s16 : mal_format_f32));
|
ma_format formatIn = ((stream.sampleSize == 8)? ma_format_u8 : ((stream.sampleSize == 16)? ma_format_s16 : ma_format_f32));
|
||||||
|
|
||||||
// The size of a streaming buffer must be at least double the size of a period.
|
// The size of a streaming buffer must be at least double the size of a period.
|
||||||
unsigned int periodSize = device.bufferSizeInFrames/device.periods;
|
unsigned int periodSize = device.playback.internalBufferSizeInFrames/device.playback.internalPeriods;
|
||||||
unsigned int subBufferSize = AUDIO_BUFFER_SIZE;
|
unsigned int subBufferSize = AUDIO_BUFFER_SIZE;
|
||||||
if (subBufferSize < periodSize) subBufferSize = periodSize;
|
if (subBufferSize < periodSize) subBufferSize = periodSize;
|
||||||
|
|
||||||
|
|
@ -1557,7 +1563,7 @@ void UpdateAudioStream(AudioStream stream, const void *data, int samplesCount)
|
||||||
|
|
||||||
if (audioBuffer->isSubBufferProcessed[0] || audioBuffer->isSubBufferProcessed[1])
|
if (audioBuffer->isSubBufferProcessed[0] || audioBuffer->isSubBufferProcessed[1])
|
||||||
{
|
{
|
||||||
mal_uint32 subBufferToUpdate;
|
ma_uint32 subBufferToUpdate;
|
||||||
|
|
||||||
if (audioBuffer->isSubBufferProcessed[0] && audioBuffer->isSubBufferProcessed[1])
|
if (audioBuffer->isSubBufferProcessed[0] && audioBuffer->isSubBufferProcessed[1])
|
||||||
{
|
{
|
||||||
|
|
@ -1571,21 +1577,21 @@ void UpdateAudioStream(AudioStream stream, const void *data, int samplesCount)
|
||||||
subBufferToUpdate = (audioBuffer->isSubBufferProcessed[0])? 0 : 1;
|
subBufferToUpdate = (audioBuffer->isSubBufferProcessed[0])? 0 : 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
mal_uint32 subBufferSizeInFrames = audioBuffer->bufferSizeInFrames/2;
|
ma_uint32 subBufferSizeInFrames = audioBuffer->bufferSizeInFrames/2;
|
||||||
unsigned char *subBuffer = audioBuffer->buffer + ((subBufferSizeInFrames*stream.channels*(stream.sampleSize/8))*subBufferToUpdate);
|
unsigned char *subBuffer = audioBuffer->buffer + ((subBufferSizeInFrames*stream.channels*(stream.sampleSize/8))*subBufferToUpdate);
|
||||||
|
|
||||||
// Does this API expect a whole buffer to be updated in one go? Assuming so, but if not will need to change this logic.
|
// Does this API expect a whole buffer to be updated in one go? Assuming so, but if not will need to change this logic.
|
||||||
if (subBufferSizeInFrames >= (mal_uint32)samplesCount/stream.channels)
|
if (subBufferSizeInFrames >= (ma_uint32)samplesCount/stream.channels)
|
||||||
{
|
{
|
||||||
mal_uint32 framesToWrite = subBufferSizeInFrames;
|
ma_uint32 framesToWrite = subBufferSizeInFrames;
|
||||||
|
|
||||||
if (framesToWrite > ((mal_uint32)samplesCount/stream.channels)) framesToWrite = (mal_uint32)samplesCount/stream.channels;
|
if (framesToWrite > ((ma_uint32)samplesCount/stream.channels)) framesToWrite = (ma_uint32)samplesCount/stream.channels;
|
||||||
|
|
||||||
mal_uint32 bytesToWrite = framesToWrite*stream.channels*(stream.sampleSize/8);
|
ma_uint32 bytesToWrite = framesToWrite*stream.channels*(stream.sampleSize/8);
|
||||||
memcpy(subBuffer, data, bytesToWrite);
|
memcpy(subBuffer, data, bytesToWrite);
|
||||||
|
|
||||||
// Any leftover frames should be filled with zeros.
|
// Any leftover frames should be filled with zeros.
|
||||||
mal_uint32 leftoverFrameCount = subBufferSizeInFrames - framesToWrite;
|
ma_uint32 leftoverFrameCount = subBufferSizeInFrames - framesToWrite;
|
||||||
|
|
||||||
if (leftoverFrameCount > 0)
|
if (leftoverFrameCount > 0)
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -11,7 +11,7 @@
|
||||||
* - Manage raw audio context
|
* - Manage raw audio context
|
||||||
*
|
*
|
||||||
* DEPENDENCIES:
|
* DEPENDENCIES:
|
||||||
* mini_al.h - Audio device management lib (https://github.com/dr-soft/mini_al)
|
* miniaudio.h - Audio device management lib (https://github.com/dr-soft/miniaudio)
|
||||||
* stb_vorbis.h - Ogg audio files loading (http://www.nothings.org/stb_vorbis/)
|
* stb_vorbis.h - Ogg audio files loading (http://www.nothings.org/stb_vorbis/)
|
||||||
* dr_mp3.h - MP3 audio file loading (https://github.com/mackron/dr_libs)
|
* dr_mp3.h - MP3 audio file loading (https://github.com/mackron/dr_libs)
|
||||||
* dr_flac.h - FLAC audio file loading (https://github.com/mackron/dr_libs)
|
* dr_flac.h - FLAC audio file loading (https://github.com/mackron/dr_libs)
|
||||||
|
|
|
||||||
|
|
@ -1240,6 +1240,7 @@ RLAPI Color *GetImageData(Image image);
|
||||||
RLAPI Vector4 *GetImageDataNormalized(Image image); // Get pixel data from image as Vector4 array (float normalized)
|
RLAPI Vector4 *GetImageDataNormalized(Image image); // Get pixel data from image as Vector4 array (float normalized)
|
||||||
RLAPI int GetPixelDataSize(int width, int height, int format); // Get pixel data size in bytes (image or texture)
|
RLAPI int GetPixelDataSize(int width, int height, int format); // Get pixel data size in bytes (image or texture)
|
||||||
RLAPI Image GetTextureData(Texture2D texture); // Get pixel data from GPU texture and return an Image
|
RLAPI Image GetTextureData(Texture2D texture); // Get pixel data from GPU texture and return an Image
|
||||||
|
RLAPI Image GetScreenData(void); // Get pixel data from screen buffer and return an Image (screenshot)
|
||||||
RLAPI void UpdateTexture(Texture2D texture, const void *pixels); // Update GPU texture with new data
|
RLAPI void UpdateTexture(Texture2D texture, const void *pixels); // Update GPU texture with new data
|
||||||
|
|
||||||
// Image manipulation functions
|
// Image manipulation functions
|
||||||
|
|
@ -1352,6 +1353,7 @@ RLAPI void DrawCircle3D(Vector3 center, float radius, Vector3 rotationAxis, floa
|
||||||
RLAPI void DrawCube(Vector3 position, float width, float height, float length, Color color); // Draw cube
|
RLAPI void DrawCube(Vector3 position, float width, float height, float length, Color color); // Draw cube
|
||||||
RLAPI void DrawCubeV(Vector3 position, Vector3 size, Color color); // Draw cube (Vector version)
|
RLAPI void DrawCubeV(Vector3 position, Vector3 size, Color color); // Draw cube (Vector version)
|
||||||
RLAPI void DrawCubeWires(Vector3 position, float width, float height, float length, Color color); // Draw cube wires
|
RLAPI void DrawCubeWires(Vector3 position, float width, float height, float length, Color color); // Draw cube wires
|
||||||
|
RLAPI void DrawCubeWiresV(Vector3 position, Vector3 size, Color color); // Draw cube wires (Vector version)
|
||||||
RLAPI void DrawCubeTexture(Texture2D texture, Vector3 position, float width, float height, float length, Color color); // Draw cube textured
|
RLAPI void DrawCubeTexture(Texture2D texture, Vector3 position, float width, float height, float length, Color color); // Draw cube textured
|
||||||
RLAPI void DrawSphere(Vector3 centerPos, float radius, Color color); // Draw sphere
|
RLAPI void DrawSphere(Vector3 centerPos, float radius, Color color); // Draw sphere
|
||||||
RLAPI void DrawSphereEx(Vector3 centerPos, float radius, int rings, int slices, Color color); // Draw sphere with extended parameters
|
RLAPI void DrawSphereEx(Vector3 centerPos, float radius, int rings, int slices, Color color); // Draw sphere with extended parameters
|
||||||
|
|
|
||||||
|
|
@ -563,7 +563,10 @@ int GetPixelDataSize(int width, int height, int format);// Get pixel data size i
|
||||||
#define SUPPORT_VR_SIMULATOR
|
#define SUPPORT_VR_SIMULATOR
|
||||||
#define SUPPORT_DISTORTION_SHADER
|
#define SUPPORT_DISTORTION_SHADER
|
||||||
#else
|
#else
|
||||||
#include "config.h" // rlgl module configuration
|
// Check if config flags have been externally provided on compilation line
|
||||||
|
#if !defined(EXTERNAL_CONFIG_FLAGS)
|
||||||
|
#include "config.h" // Defines module configuration flags
|
||||||
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include <stdio.h> // Required for: fopen(), fclose(), fread()... [Used only on LoadText()]
|
#include <stdio.h> // Required for: fopen(), fclose(), fread()... [Used only on LoadText()]
|
||||||
|
|
|
||||||
|
|
@ -182,6 +182,15 @@ Image LoadImage(const char *fileName)
|
||||||
{
|
{
|
||||||
Image image = { 0 };
|
Image image = { 0 };
|
||||||
|
|
||||||
|
#if defined(SUPPORT_FILEFORMAT_PNG) || \
|
||||||
|
defined(SUPPORT_FILEFORMAT_BMP) || \
|
||||||
|
defined(SUPPORT_FILEFORMAT_TGA) || \
|
||||||
|
defined(SUPPORT_FILEFORMAT_GIF) || \
|
||||||
|
defined(SUPPORT_FILEFORMAT_PIC) || \
|
||||||
|
defined(SUPPORT_FILEFORMAT_PSD)
|
||||||
|
#define STBI_REQUIRED
|
||||||
|
#endif
|
||||||
|
|
||||||
#if defined(SUPPORT_FILEFORMAT_PNG)
|
#if defined(SUPPORT_FILEFORMAT_PNG)
|
||||||
if ((IsFileExtension(fileName, ".png"))
|
if ((IsFileExtension(fileName, ".png"))
|
||||||
#else
|
#else
|
||||||
|
|
@ -207,6 +216,7 @@ Image LoadImage(const char *fileName)
|
||||||
#endif
|
#endif
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
|
#if defined(STBI_REQUIRED)
|
||||||
int imgWidth = 0;
|
int imgWidth = 0;
|
||||||
int imgHeight = 0;
|
int imgHeight = 0;
|
||||||
int imgBpp = 0;
|
int imgBpp = 0;
|
||||||
|
|
@ -229,6 +239,7 @@ Image LoadImage(const char *fileName)
|
||||||
else if (imgBpp == 3) image.format = UNCOMPRESSED_R8G8B8;
|
else if (imgBpp == 3) image.format = UNCOMPRESSED_R8G8B8;
|
||||||
else if (imgBpp == 4) image.format = UNCOMPRESSED_R8G8B8A8;
|
else if (imgBpp == 4) image.format = UNCOMPRESSED_R8G8B8A8;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
#if defined(SUPPORT_FILEFORMAT_HDR)
|
#if defined(SUPPORT_FILEFORMAT_HDR)
|
||||||
else if (IsFileExtension(fileName, ".hdr"))
|
else if (IsFileExtension(fileName, ".hdr"))
|
||||||
|
|
@ -729,6 +740,20 @@ Image GetTextureData(Texture2D texture)
|
||||||
return image;
|
return image;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Get pixel data from GPU frontbuffer and return an Image (screenshot)
|
||||||
|
RLAPI Image GetScreenData(void)
|
||||||
|
{
|
||||||
|
Image image = { 0 };
|
||||||
|
|
||||||
|
image.width = GetScreenWidth();
|
||||||
|
image.height = GetScreenHeight();
|
||||||
|
image.mipmaps = 1;
|
||||||
|
image.format = UNCOMPRESSED_R8G8B8A8;
|
||||||
|
image.data = rlReadScreenPixels(image.width, image.height);
|
||||||
|
|
||||||
|
return image;
|
||||||
|
}
|
||||||
|
|
||||||
// Update GPU texture with new data
|
// Update GPU texture with new data
|
||||||
// NOTE: pixels data must match texture.format
|
// NOTE: pixels data must match texture.format
|
||||||
void UpdateTexture(Texture2D texture, const void *pixels)
|
void UpdateTexture(Texture2D texture, const void *pixels)
|
||||||
|
|
@ -1157,8 +1182,6 @@ void ImageAlphaPremultiply(Image *image)
|
||||||
ImageFormat(image, prevFormat);
|
ImageFormat(image, prevFormat);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#if defined(SUPPORT_IMAGE_MANIPULATION)
|
#if defined(SUPPORT_IMAGE_MANIPULATION)
|
||||||
// Load cubemap from image, multiple image cubemap layouts supported
|
// Load cubemap from image, multiple image cubemap layouts supported
|
||||||
TextureCubemap LoadTextureCubemap(Image image, int layoutType)
|
TextureCubemap LoadTextureCubemap(Image image, int layoutType)
|
||||||
|
|
@ -1387,22 +1410,56 @@ void ImageResizeNN(Image *image,int newWidth,int newHeight)
|
||||||
// NOTE: Resize offset is relative to the top-left corner of the original image
|
// NOTE: Resize offset is relative to the top-left corner of the original image
|
||||||
void ImageResizeCanvas(Image *image, int newWidth,int newHeight, int offsetX, int offsetY, Color color)
|
void ImageResizeCanvas(Image *image, int newWidth,int newHeight, int offsetX, int offsetY, Color color)
|
||||||
{
|
{
|
||||||
Image imTemp = GenImageColor(newWidth, newHeight, color);
|
|
||||||
Rectangle srcRec = { 0.0f, 0.0f, (float)image->width, (float)image->height };
|
|
||||||
Rectangle dstRec = { (float)offsetX, (float)offsetY, (float)srcRec.width, (float)srcRec.height };
|
|
||||||
|
|
||||||
// TODO: Review different scaling situations
|
// TODO: Review different scaling situations
|
||||||
|
|
||||||
if ((newWidth > image->width) && (newHeight > image->height))
|
if ((newWidth != image->width) || (newHeight != image->height))
|
||||||
{
|
{
|
||||||
ImageDraw(&imTemp, *image, srcRec, dstRec);
|
if ((newWidth > image->width) && (newHeight > image->height))
|
||||||
ImageFormat(&imTemp, image->format);
|
{
|
||||||
UnloadImage(*image);
|
Image imTemp = GenImageColor(newWidth, newHeight, color);
|
||||||
*image = imTemp;
|
|
||||||
}
|
Rectangle srcRec = { 0.0f, 0.0f, (float)image->width, (float)image->height };
|
||||||
else
|
Rectangle dstRec = { (float)offsetX, (float)offsetY, (float)srcRec.width, (float)srcRec.height };
|
||||||
{
|
|
||||||
// TODO: ImageCrop(), define proper cropping rectangle
|
ImageDraw(&imTemp, *image, srcRec, dstRec);
|
||||||
|
ImageFormat(&imTemp, image->format);
|
||||||
|
UnloadImage(*image);
|
||||||
|
*image = imTemp;
|
||||||
|
}
|
||||||
|
else if ((newWidth < image->width) && (newHeight < image->height))
|
||||||
|
{
|
||||||
|
Rectangle crop = { (float)offsetX, (float)offsetY, newWidth, newHeight };
|
||||||
|
ImageCrop(image, crop);
|
||||||
|
}
|
||||||
|
else // One side is bigger and the other is smaller
|
||||||
|
{
|
||||||
|
Image imTemp = GenImageColor(newWidth, newHeight, color);
|
||||||
|
|
||||||
|
Rectangle srcRec = { 0.0f, 0.0f, (float)image->width, (float)image->height };
|
||||||
|
Rectangle dstRec = { (float)offsetX, (float)offsetY, (float)newWidth, (float)newHeight };
|
||||||
|
|
||||||
|
if (newWidth < image->width)
|
||||||
|
{
|
||||||
|
srcRec.x = offsetX;
|
||||||
|
srcRec.width = newWidth;
|
||||||
|
|
||||||
|
dstRec.x = 0.0f;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (newHeight < image->height)
|
||||||
|
{
|
||||||
|
srcRec.y = offsetY;
|
||||||
|
srcRec.height = newHeight;
|
||||||
|
|
||||||
|
dstRec.y = 0.0f;
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: ImageDraw() could be buggy?
|
||||||
|
ImageDraw(&imTemp, *image, srcRec, dstRec);
|
||||||
|
ImageFormat(&imTemp, image->format);
|
||||||
|
UnloadImage(*image);
|
||||||
|
*image = imTemp;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -30,9 +30,13 @@
|
||||||
*
|
*
|
||||||
**********************************************************************************************/
|
**********************************************************************************************/
|
||||||
|
|
||||||
#include "config.h"
|
|
||||||
|
|
||||||
#include "raylib.h" // WARNING: Required for: LogType enum
|
#include "raylib.h" // WARNING: Required for: LogType enum
|
||||||
|
|
||||||
|
// Check if config flags have been externally provided on compilation line
|
||||||
|
#if !defined(EXTERNAL_CONFIG_FLAGS)
|
||||||
|
#include "config.h" // Defines module configuration flags
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "utils.h"
|
#include "utils.h"
|
||||||
|
|
||||||
#if defined(PLATFORM_ANDROID)
|
#if defined(PLATFORM_ANDROID)
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
# Define required raylib variables
|
# Define required raylib variables
|
||||||
# WARNING: To compile to HTML5, code must be redesigned to use emscripten.h and emscripten_set_main_loop()
|
# WARNING: To compile to HTML5, code must be redesigned to use emscripten.h and emscripten_set_main_loop()
|
||||||
PLATFORM ?= PLATFORM_DESKTOP
|
PLATFORM ?= PLATFORM_DESKTOP
|
||||||
RAYLIB_PATH = ../..
|
RAYLIB_PATH ?= ../..
|
||||||
PROJECT_NAME ?= advance_game
|
PROJECT_NAME ?= advance_game
|
||||||
|
|
||||||
# Default path for raylib on Raspberry Pi, if installed in different path, update it!
|
# Default path for raylib on Raspberry Pi, if installed in different path, update it!
|
||||||
|
|
@ -58,7 +58,7 @@ ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||||
ifeq ($(UNAMEOS),Linux)
|
ifeq ($(UNAMEOS),Linux)
|
||||||
PLATFORM_OS=LINUX
|
PLATFORM_OS=LINUX
|
||||||
endif
|
endif
|
||||||
ifeq ($(UNAMEOS),FreeBSD)
|
ifeq ($(UNAMEOS),FreeBSD)
|
||||||
PLATFORM_OS=BSD
|
PLATFORM_OS=BSD
|
||||||
endif
|
endif
|
||||||
ifeq ($(UNAMEOS),OpenBSD)
|
ifeq ($(UNAMEOS),OpenBSD)
|
||||||
|
|
@ -209,7 +209,7 @@ endif
|
||||||
LDFLAGS = -L. -L$(RAYLIB_RELEASE_PATH) -L$(RAYLIB_PATH)/src
|
LDFLAGS = -L. -L$(RAYLIB_RELEASE_PATH) -L$(RAYLIB_PATH)/src
|
||||||
|
|
||||||
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||||
ifeq ($(PLATFORM_OS),FREEBSD)
|
ifeq ($(PLATFORM_OS),BSD)
|
||||||
INCLUDE_PATHS += -I/usr/local/include
|
INCLUDE_PATHS += -I/usr/local/include
|
||||||
LDFLAGS += -L. -Lsrc -L/usr/local/lib
|
LDFLAGS += -L. -Lsrc -L/usr/local/lib
|
||||||
endif
|
endif
|
||||||
|
|
@ -249,8 +249,8 @@ ifeq ($(PLATFORM),PLATFORM_DESKTOP)
|
||||||
# NOTE: Required packages: libopenal-dev libegl1-mesa-dev
|
# NOTE: Required packages: libopenal-dev libegl1-mesa-dev
|
||||||
LDLIBS = -lraylib -framework OpenGL -framework OpenAL -framework Cocoa
|
LDLIBS = -lraylib -framework OpenGL -framework OpenAL -framework Cocoa
|
||||||
endif
|
endif
|
||||||
ifeq ($(PLATFORM_OS),FREEBSD)
|
ifeq ($(PLATFORM_OS),BSD)
|
||||||
# Libraries for FreeBSD desktop compiling
|
# Libraries for FreeBSD, OpenBSD, NetBSD, DragonFly desktop compiling
|
||||||
# NOTE: Required packages: mesa-libs
|
# NOTE: Required packages: mesa-libs
|
||||||
LDLIBS = -lraylib -lGL -lpthread -lm
|
LDLIBS = -lraylib -lGL -lpthread -lm
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -70,7 +70,9 @@ APP_KEYSTORE_PASS ?= raylib
|
||||||
|
|
||||||
# Library type used for raylib: STATIC (.a) or SHARED (.so/.dll)
|
# Library type used for raylib: STATIC (.a) or SHARED (.so/.dll)
|
||||||
RAYLIB_LIBTYPE ?= STATIC
|
RAYLIB_LIBTYPE ?= STATIC
|
||||||
RAYLIB_LIB_PATH = $(RAYLIB_PATH)\release\libs\android\$(ANDROID_ARCH_NAME)
|
|
||||||
|
# Library path for libraylib.s/libraylib.so
|
||||||
|
RAYLIB_LIB_PATH = $(RAYLIB_PATH)\src
|
||||||
|
|
||||||
# Shared libs must be added to APK if required
|
# Shared libs must be added to APK if required
|
||||||
# NOTE: Generated NativeLoader.java automatically load those libraries
|
# NOTE: Generated NativeLoader.java automatically load those libraries
|
||||||
|
|
@ -104,7 +106,7 @@ CFLAGS += -Wall -Wa,--noexecstack -Wformat -Werror=format-security -no-canonical
|
||||||
CFLAGS += -DANDROID -DPLATFORM_ANDROID -D__ANDROID_API__=$(ANDROID_API_VERSION)
|
CFLAGS += -DANDROID -DPLATFORM_ANDROID -D__ANDROID_API__=$(ANDROID_API_VERSION)
|
||||||
|
|
||||||
# Paths containing required header files
|
# Paths containing required header files
|
||||||
INCLUDE_PATHS = -I. -I$(RAYLIB_PATH)/release/include -I$(RAYLIB_PATH)/src/external/android/native_app_glue
|
INCLUDE_PATHS = -I. -I$(RAYLIB_PATH)/src -I$(RAYLIB_PATH)/src/external/android/native_app_glue
|
||||||
|
|
||||||
# Linker options
|
# Linker options
|
||||||
LDFLAGS = -Wl,-soname,lib$(PROJECT_LIBRARY_NAME).so -Wl,--exclude-libs,libatomic.a
|
LDFLAGS = -Wl,-soname,lib$(PROJECT_LIBRARY_NAME).so -Wl,--exclude-libs,libatomic.a
|
||||||
|
|
|
||||||
|
|
@ -70,7 +70,9 @@ APP_KEYSTORE_PASS ?= raylib
|
||||||
|
|
||||||
# Library type used for raylib: STATIC (.a) or SHARED (.so/.dll)
|
# Library type used for raylib: STATIC (.a) or SHARED (.so/.dll)
|
||||||
RAYLIB_LIBTYPE ?= STATIC
|
RAYLIB_LIBTYPE ?= STATIC
|
||||||
RAYLIB_LIB_PATH = $(RAYLIB_PATH)\release\libs\android\$(ANDROID_ARCH_NAME)
|
|
||||||
|
# Library path for libraylib.s/libraylib.so
|
||||||
|
RAYLIB_LIB_PATH = $(RAYLIB_PATH)\src
|
||||||
|
|
||||||
# Shared libs must be added to APK if required
|
# Shared libs must be added to APK if required
|
||||||
# NOTE: Generated NativeLoader.java automatically load those libraries
|
# NOTE: Generated NativeLoader.java automatically load those libraries
|
||||||
|
|
@ -104,7 +106,7 @@ CFLAGS += -Wall -Wa,--noexecstack -Wformat -Werror=format-security -no-canonical
|
||||||
CFLAGS += -DANDROID -DPLATFORM_ANDROID -D__ANDROID_API__=$(ANDROID_API_VERSION)
|
CFLAGS += -DANDROID -DPLATFORM_ANDROID -D__ANDROID_API__=$(ANDROID_API_VERSION)
|
||||||
|
|
||||||
# Paths containing required header files
|
# Paths containing required header files
|
||||||
INCLUDE_PATHS = -I. -I$(RAYLIB_PATH)/release/include -I$(RAYLIB_PATH)/src/external/android/native_app_glue
|
INCLUDE_PATHS = -I. -I$(RAYLIB_PATH)/src -I$(RAYLIB_PATH)/src/external/android/native_app_glue
|
||||||
|
|
||||||
# Linker options
|
# Linker options
|
||||||
LDFLAGS = -Wl,-soname,lib$(PROJECT_LIBRARY_NAME).so -Wl,--exclude-libs,libatomic.a
|
LDFLAGS = -Wl,-soname,lib$(PROJECT_LIBRARY_NAME).so -Wl,--exclude-libs,libatomic.a
|
||||||
|
|
|
||||||
|
|
@ -70,7 +70,9 @@ APP_KEYSTORE_PASS ?= raylib
|
||||||
|
|
||||||
# Library type used for raylib: STATIC (.a) or SHARED (.so/.dll)
|
# Library type used for raylib: STATIC (.a) or SHARED (.so/.dll)
|
||||||
RAYLIB_LIBTYPE ?= STATIC
|
RAYLIB_LIBTYPE ?= STATIC
|
||||||
RAYLIB_LIB_PATH = $(RAYLIB_PATH)\release\libs\android\$(ANDROID_ARCH_NAME)
|
|
||||||
|
# Library path for libraylib.s/libraylib.so
|
||||||
|
RAYLIB_LIB_PATH = $(RAYLIB_PATH)\src
|
||||||
|
|
||||||
# Shared libs must be added to APK if required
|
# Shared libs must be added to APK if required
|
||||||
# NOTE: Generated NativeLoader.java automatically load those libraries
|
# NOTE: Generated NativeLoader.java automatically load those libraries
|
||||||
|
|
@ -104,7 +106,7 @@ CFLAGS += -Wall -Wa,--noexecstack -Wformat -Werror=format-security -no-canonical
|
||||||
CFLAGS += -DANDROID -DPLATFORM_ANDROID -D__ANDROID_API__=$(ANDROID_API_VERSION)
|
CFLAGS += -DANDROID -DPLATFORM_ANDROID -D__ANDROID_API__=$(ANDROID_API_VERSION)
|
||||||
|
|
||||||
# Paths containing required header files
|
# Paths containing required header files
|
||||||
INCLUDE_PATHS = -I. -I$(RAYLIB_PATH)/release/include -I$(RAYLIB_PATH)/src/external/android/native_app_glue
|
INCLUDE_PATHS = -I. -I$(RAYLIB_PATH)/src -I$(RAYLIB_PATH)/src/external/android/native_app_glue
|
||||||
|
|
||||||
# Linker options
|
# Linker options
|
||||||
LDFLAGS = -Wl,-soname,lib$(PROJECT_LIBRARY_NAME).so -Wl,--exclude-libs,libatomic.a
|
LDFLAGS = -Wl,-soname,lib$(PROJECT_LIBRARY_NAME).so -Wl,--exclude-libs,libatomic.a
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user