From 6ead90c0f0e9b9a44c7c1f7137f437faa29fa750 Mon Sep 17 00:00:00 2001 From: tslil clingman <> Date: Sat, 30 Oct 2021 16:54:03 -0400 Subject: Switched to tracking zig-sfml-wrapper as submodule --- .gitmodules | 3 + README.md | 6 +- build.zig | 2 +- src/player.zig | 6 - src/sfml/LICENCE | 18 --- src/sfml/audio/Music.zig | 111 --------------- src/sfml/audio/Sound.zig | 107 -------------- src/sfml/audio/SoundBuffer.zig | 79 ----------- src/sfml/graphics/BlendMode.zig | 92 ------------ src/sfml/graphics/CircleShape.zig | 175 ----------------------- src/sfml/graphics/Font.zig | 51 ------- src/sfml/graphics/Image.zig | 103 -------------- src/sfml/graphics/RectangleShape.zig | 177 ----------------------- src/sfml/graphics/RenderStates.zig | 20 --- src/sfml/graphics/RenderTexture.zig | 177 ----------------------- src/sfml/graphics/RenderWindow.zig | 206 --------------------------- src/sfml/graphics/Shader.zig | 96 ------------- src/sfml/graphics/Sprite.zig | 156 --------------------- src/sfml/graphics/Text.zig | 209 --------------------------- src/sfml/graphics/VertexArray.zig | 36 ----- src/sfml/graphics/View.zig | 104 -------------- src/sfml/graphics/color.zig | 185 ------------------------ src/sfml/graphics/glsl.zig | 16 --- src/sfml/graphics/primitive_type.zig | 9 -- src/sfml/graphics/rect.zig | 161 --------------------- src/sfml/graphics/texture.zig | 265 ----------------------------------- src/sfml/graphics/vertex.zig | 9 -- src/sfml/sfml.zig | 77 ---------- src/sfml/sfml_errors.zig | 3 - src/sfml/sfml_import.zig | 8 -- src/sfml/sfml_tests.zig | 11 -- src/sfml/system/Clock.zig | 59 -------- src/sfml/system/Time.zig | 114 --------------- src/sfml/system/vector.zig | 141 ------------------- src/sfml/window/Style.zig | 5 - src/sfml/window/context_settings.zig | 28 ---- src/sfml/window/event.zig | 162 --------------------- src/sfml/window/keyboard.zig | 11 -- src/sfml/window/mouse.zig | 26 ---- src/zig-sfml-wrapper | 1 + 40 files changed, 8 insertions(+), 3217 deletions(-) create mode 100644 .gitmodules delete mode 100644 src/sfml/LICENCE delete mode 100644 src/sfml/audio/Music.zig delete mode 100644 src/sfml/audio/Sound.zig delete mode 100644 src/sfml/audio/SoundBuffer.zig delete mode 100644 src/sfml/graphics/BlendMode.zig delete mode 100644 src/sfml/graphics/CircleShape.zig delete mode 100644 src/sfml/graphics/Font.zig delete mode 100644 src/sfml/graphics/Image.zig delete mode 100644 src/sfml/graphics/RectangleShape.zig delete mode 100644 src/sfml/graphics/RenderStates.zig delete mode 100644 src/sfml/graphics/RenderTexture.zig delete mode 100644 src/sfml/graphics/RenderWindow.zig delete mode 100644 src/sfml/graphics/Shader.zig delete mode 100644 src/sfml/graphics/Sprite.zig delete mode 100644 src/sfml/graphics/Text.zig delete mode 100644 src/sfml/graphics/VertexArray.zig delete mode 100644 src/sfml/graphics/View.zig delete mode 100644 src/sfml/graphics/color.zig delete mode 100644 src/sfml/graphics/glsl.zig delete mode 100644 src/sfml/graphics/primitive_type.zig delete mode 100644 src/sfml/graphics/rect.zig delete mode 100644 src/sfml/graphics/texture.zig delete mode 100644 src/sfml/graphics/vertex.zig delete mode 100644 src/sfml/sfml.zig delete mode 100644 src/sfml/sfml_errors.zig delete mode 100644 src/sfml/sfml_import.zig delete mode 100644 src/sfml/sfml_tests.zig delete mode 100644 src/sfml/system/Clock.zig delete mode 100644 src/sfml/system/Time.zig delete mode 100644 src/sfml/system/vector.zig delete mode 100644 src/sfml/window/Style.zig delete mode 100644 src/sfml/window/context_settings.zig delete mode 100644 src/sfml/window/event.zig delete mode 100644 src/sfml/window/keyboard.zig delete mode 100644 src/sfml/window/mouse.zig create mode 160000 src/zig-sfml-wrapper diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..4c0d131 --- /dev/null +++ b/.gitmodules @@ -0,0 +1,3 @@ +[submodule "src/zig-sfml-wrapper"] + path = src/zig-sfml-wrapper + url = https://github.com/guigui220D/zig-sfml-wrapper diff --git a/README.md b/README.md index 25bd71f..2c9a94c 100644 --- a/README.md +++ b/README.md @@ -30,14 +30,14 @@ In particular alpha blending is implemented in software. This was the result of ## Build -Ensure you have a recent version of Zig (tested on `0.9.0-dev.866+6a6e2cd64`), and the `csfml` library somewhere we your linker can find it. Then run +Ensure you have cloned the `zig-sfml-wrapper` submodule (`git pull --recurse-submodules`), a recent version of Zig (tested on `0.9.0-dev.866+6a6e2cd64` and above), and the `csfml` library somewhere we your linker can find it. Then run `zig build -Drelease-fast run` -The default keybinds are FRST for Forward, Left Strafe, Backward, Right Strafe and the arrow keys for similar but turn instead of strafe. Escape exits. +The default keybindings are FRST for Forward, Left Strafe, Backward, Right Strafe and the arrow keys for similar but turn instead of strafe; mouse look works horizontally; escape exits. ## License The code is GPLv3+, the artwork is CC-BY-SA 4.0 -I make use of the zig-sfml library, which is Copyright (C) 2021 Guigui220D under the terms of the MIT license. For details see `src/sfml/LICENCE` +I make use of a Zig (C)SFML wrapper, which is Copyright (C) 2021 Guigui220D under the terms of the MIT license. For details see `src/zig-sfml-wrapper/LICENCE`. diff --git a/build.zig b/build.zig index b809432..fa1197b 100644 --- a/build.zig +++ b/build.zig @@ -7,7 +7,7 @@ pub fn build(b: *Builder) void { const exe = b.addExecutable("zirc", "src/main.zig"); exe.linkLibC(); - exe.addPackagePath("sfml", "src/sfml/sfml.zig"); + exe.addPackagePath("sfml", "src/zig-sfml-wrapper/src/sfml/sfml.zig"); exe.linkSystemLibrary("csfml-graphics"); exe.linkSystemLibrary("csfml-system"); exe.linkSystemLibrary("csfml-window"); diff --git a/src/player.zig b/src/player.zig index eef41a7..44488c5 100644 --- a/src/player.zig +++ b/src/player.zig @@ -17,12 +17,6 @@ const std = @import("std"); -const RenderWindow = @import("sfml").graphics.RenderWindow; -const Sprite = @import("sfml").graphics.Sprite; -const Texture = @import("sfml").graphics.Texture; -const Image = @import("sfml").graphics.Image; -const Colour = @import("sfml").graphics.Color; - const level = @import("level.zig"); const constants = @import("constants.zig"); diff --git a/src/sfml/LICENCE b/src/sfml/LICENCE deleted file mode 100644 index d6c7f74..0000000 --- a/src/sfml/LICENCE +++ /dev/null @@ -1,18 +0,0 @@ -Copyright (C) 2021 Guigui220D - -Permission to use, copy, modify, and/or distribute this software for any -purpose with or without fee is hereby granted, provided that the above -copyright notice and this permission notice appear in all copies. - -THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES -WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF -MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR -ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES -WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION -OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN -CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. - -This project does not contain the sources of CSFML. The licence of CSFML can be found in CSFML-LICENSE - -nice_music.ogg from https://www.bensound.com/ -cute_image.png from https://github.com/ziglang/logo \ No newline at end of file diff --git a/src/sfml/audio/Music.zig b/src/sfml/audio/Music.zig deleted file mode 100644 index d55a718..0000000 --- a/src/sfml/audio/Music.zig +++ /dev/null @@ -1,111 +0,0 @@ -//! Streamed music played from an audio file. - -const sf = @import("../sfml.zig"); - -const Music = @This(); - -// Constructor/destructor - -/// Loads music from a file -pub fn createFromFile(path: [:0]const u8) !Music { - var music = sf.c.sfMusic_createFromFile(path); - if (music == null) - return sf.Error.resourceLoadingError; - return Music{ ._ptr = music.? }; -} - -pub const initFromMemory = @compileError("Function is not implemented yet."); -pub const initFromStream = @compileError("Function is not implemented yet."); - -/// Destroys this music object -pub fn destroy(self: *Music) void { - sf.c.sfMusic_destroy(self._ptr); -} - -// Music control functions - -/// Plays the music -pub fn play(self: *Music) void { - sf.c.sfMusic_play(self._ptr); -} -/// Pauses the music -pub fn pause(self: *Music) void { - sf.c.sfMusic_pause(self._ptr); -} -/// Stops the music and resets the player position -pub fn stop(self: *Music) void { - sf.c.sfMusic_stop(self._ptr); -} - -// Getters / Setters - -/// Gets the total duration of the music -pub fn getDuration(self: Music) sf.Time { - return sf.Time._fromCSFML(sf.c.sfMusic_getDuration(self._ptr)); -} - -/// Gets the current stream position of the music -pub fn getPlayingOffset(self: Music) sf.Time { - return sf.Time._fromCSFML(sf.c.sfMusic_getPlayingOffset(self._ptr)); -} -/// Sets the current stream position of the music -pub fn setPlayingOffset(self: *Music, offset: sf.Time) void { - sf.c.sfMusic_setPlayingOffset(self._ptr, offset._toCSFML()); -} - -/// Gets the loop points of the music -pub fn getLoopPoints(self: Music) sf.TimeSpan { - return sf.TimeSpan._fromCSFML(sf.c.sfMusic_getLoopPoints(self._ptr)); -} -/// Gets the loop points of the music -pub fn setLoopPoints(self: *Music, span: sf.TimeSpan) void { - sf.c.sfMusic_setLoopPoints(self._ptr, span._toCSFML()); -} - -/// Tells whether or not this stream is in loop mode -pub fn getLoop(self: Music) bool { - return sf.c.sfMusic_getLoop(self._ptr) != 0; -} -/// Enable or disable auto loop -pub fn setLoop(self: *Music, loop: bool) void { - sf.c.sfMusic_setLoop(self._ptr, @boolToInt(loop)); -} - -/// Sets the pitch of the music -pub fn getPitch(self: Music) f32 { - return sf.c.sfMusic_getPitch(self._ptr); -} -/// Gets the pitch of the music -pub fn setPitch(self: *Music, pitch: f32) void { - sf.c.sfMusic_setPitch(self._ptr, pitch); -} - -/// Sets the volume of the music -pub fn getVolume(self: Music) f32 { - return sf.c.sfMusic_getVolume(self._ptr); -} -/// Gets the volume of the music -pub fn setVolume(self: *Music, volume: f32) void { - sf.c.sfMusic_setVolume(self._ptr, volume); -} - -/// Gets the sample rate of this music -pub fn getSampleRate(self: Music) usize { - return @intCast(usize, sf.c.sfMusic_getSampleRate(self._ptr)); -} - -/// Gets the channel count of the music -pub fn getChannelCount(self: Music) usize { - return @intCast(usize, sf.c.sfMusic_getChannelCount(self._ptr)); -} - -pub const getStatus = @compileError("Function is not implemented yet."); -pub const setRelativeToListener = @compileError("Function is not implemented yet."); -pub const isRelativeToListener = @compileError("Function is not implemented yet."); -pub const setMinDistance = @compileError("Function is not implemented yet."); -pub const setAttenuation = @compileError("Function is not implemented yet."); -pub const getMinDistance = @compileError("Function is not implemented yet."); -pub const getAttenuation = @compileError("Function is not implemented yet."); - -/// Pointer to the csfml music -_ptr: *sf.c.sfMusic, diff --git a/src/sfml/audio/Sound.zig b/src/sfml/audio/Sound.zig deleted file mode 100644 index 92acb46..0000000 --- a/src/sfml/audio/Sound.zig +++ /dev/null @@ -1,107 +0,0 @@ -//! Regular sound that can be played in the audio environment. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.audio; -}; - -const Sound = @This(); - -// Constructor/destructor - -/// Inits an empty sound -pub fn create() !Sound { - var sound = sf.c.sfSound_create(); - if (sound == null) - return sf.Error.nullptrUnknownReason; - return Sound{ ._ptr = sound.? }; -} - -/// Inits a sound with a SoundBuffer object -pub fn createFromBuffer(buffer: sf.SoundBuffer) !Sound { - var sound = try Sound.create(); - sound.setBuffer(buffer); - return sound; -} - -/// Destroys this sound object -pub fn destroy(self: *Sound) void { - sf.c.sfSound_destroy(self._ptr); -} - -// Sound control functions - -/// Plays the sound -pub fn play(self: *Sound) void { - sf.c.sfSound_play(self._ptr); -} -/// Pauses the sound -pub fn pause(self: *Sound) void { - sf.c.sfSound_pause(self._ptr); -} -/// Stops the sound and resets the player position -pub fn stop(self: *Sound) void { - sf.c.sfSound_stop(self._ptr); -} - -// Getters / Setters - -/// Gets the buffer this sound is attached to -pub fn getBuffer(self: Sound) ?sf.SoundBuffer { - var buf = sf.c.sfSound_getBuffer(self._ptr); - if (buf) |buffer| { - return .{ ._ptr = buffer }; - } else return null; -} - -/// Sets the buffer this sound will play -pub fn setBuffer(self: *Sound, buffer: sf.SoundBuffer) void { - sf.c.sfSound_setBuffer(self._ptr, buffer._ptr); -} - -/// Gets the current playing offset of the sound -pub fn getPlayingOffset(self: Sound) sf.Time { - return sf.Time._fromCSFML(sf.c.sfSound_getPlayingOffset(self._ptr)); -} -/// Sets the current playing offset of the sound -pub fn setPlayingOffset(self: *Sound, offset: sf.Time) void { - sf.c.sfSound_setPlayingOffset(self._ptr, offset._toCSFML()); -} - -/// Tells whether or not this sound is in loop mode -pub fn getLoop(self: Sound) bool { - return sf.c.sfSound_getLoop(self._ptr) != 0; -} -/// Enable or disable auto loop -pub fn setLoop(self: *Sound, loop: bool) void { - sf.c.sfSound_setLoop(self._ptr, @boolToInt(loop)); -} - -/// Sets the pitch of the sound -pub fn getPitch(self: Sound) f32 { - return sf.c.sfSound_getPitch(self._ptr); -} -/// Gets the pitch of the sound -pub fn setPitch(self: *Sound, pitch: f32) void { - sf.c.sfSound_setPitch(self._ptr, pitch); -} - -/// Sets the volume of the sound -pub fn getVolume(self: Sound) f32 { - return sf.c.sfSound_getVolume(self._ptr); -} -/// Gets the volume of the sound -pub fn setVolume(self: *Sound, volume: f32) void { - sf.c.sfSound_setVolume(self._ptr, volume); -} - -pub const getStatus = @compileError("Function is not implemented yet."); -pub const setRelativeToListener = @compileError("Function is not implemented yet."); -pub const isRelativeToListener = @compileError("Function is not implemented yet."); -pub const setMinDistance = @compileError("Function is not implemented yet."); -pub const setAttenuation = @compileError("Function is not implemented yet."); -pub const getMinDistance = @compileError("Function is not implemented yet."); -pub const getAttenuation = @compileError("Function is not implemented yet."); - -/// Pointer to the csfml sound -_ptr: *sf.c.sfSound, diff --git a/src/sfml/audio/SoundBuffer.zig b/src/sfml/audio/SoundBuffer.zig deleted file mode 100644 index 39ed082..0000000 --- a/src/sfml/audio/SoundBuffer.zig +++ /dev/null @@ -1,79 +0,0 @@ -//! Storage for audio samples defining a sound. - -const sf = @import("../sfml.zig"); - -const SoundBuffer = @This(); - -// Constructor/destructor -/// Loads music from a file -pub fn createFromFile(path: [:0]const u8) !SoundBuffer { - var sound = sf.c.sfSoundBuffer_createFromFile(path); - if (sound == null) - return sf.Error.resourceLoadingError; - return SoundBuffer{ ._ptr = sound.? }; -} -/// Creates a sound buffer from sample data -pub fn createFromSamples(samples: []const i16, channel_count: usize, sample_rate: usize) !SoundBuffer { - var sound = sf.c.sfSoundBuffer_createFromSamples(@ptrCast([*c]const c_short, samples.ptr), samples.len, @intCast(c_uint, channel_count), @intCast(c_uint, sample_rate)); - if (sound == null) - return sf.Error.resourceLoadingError; - return SoundBuffer{ ._ptr = sound.? }; -} - -pub const initFromMemory = @compileError("Function is not implemented yet."); -pub const initFromStream = @compileError("Function is not implemented yet."); - -/// Destroys this music object -pub fn destroy(self: *SoundBuffer) void { - sf.c.sfSoundBuffer_destroy(self._ptr); -} - -// Getters / Setters - -/// Gets the duration of the sound -pub fn getDuration(self: SoundBuffer) sf.system.Time { - return sf.system.Time._fromCSFML(sf.c.sfSoundBuffer_getDuration(self._ptr)); -} - -/// Gets the sample count of this sound -pub fn getSampleCount(self: SoundBuffer) usize { - return @intCast(usize, sf.c.sfSoundBuffer_getSampleCount(self._ptr)); -} - -/// Gets the sample rate of this sound (n° of samples per second, often 44100) -pub fn getSampleRate(self: SoundBuffer) usize { - return @intCast(usize, sf.c.sfSoundBuffer_getSampleRate(self._ptr)); -} - -/// Gets the channel count (2 is stereo for instance) -pub fn getChannelCount(self: SoundBuffer) usize { - return @intCast(usize, sf.c.sfSoundBuffer_getChannelCount(self._ptr)); -} - -// Misc - -/// Save the sound buffer to an audio file -pub fn saveToFile(self: SoundBuffer, path: [:0]const u8) !void { - if (sf.c.sfSoundBuffer_saveToFile(self._ptr, path) != 1) - return sf.Error.savingInFileFailed; -} - -/// Pointer to the csfml texture -_ptr: *sf.c.sfSoundBuffer, - -test "sound buffer: sane getter and setters" { - const std = @import("std"); - const tst = std.testing; - const allocator = std.heap.page_allocator; - - var samples = try allocator.alloc(i16, 44100 * 3); - defer allocator.free(samples); - - var buffer = try SoundBuffer.createFromSamples(samples, 1, 44100); - defer buffer.destroy(); - - try tst.expectApproxEqAbs(@as(f32, 3), buffer.getDuration().asSeconds(), 0.001); - try tst.expectEqual(@as(usize, 44100 * 3), buffer.getSampleCount()); - try tst.expectEqual(@as(usize, 44100), buffer.getSampleRate()); - try tst.expectEqual(@as(usize, 1), buffer.getChannelCount()); -} diff --git a/src/sfml/graphics/BlendMode.zig b/src/sfml/graphics/BlendMode.zig deleted file mode 100644 index d78d60d..0000000 --- a/src/sfml/graphics/BlendMode.zig +++ /dev/null @@ -1,92 +0,0 @@ -//! Blending modes for drawing (for render states) - -// Enums -pub const Factor = enum(c_int) { - zero, - one, - srcColor, - oneMinusSrcColor, - dstColor, - oneMinusDstColor, - srcAlpha, - oneMinusSrcAlpha, - dstAlpha, - oneMinusDstAlpha -}; - -pub const Equation = enum(c_int) { - add, - subtract, - reverseSubtract -}; - -const BlendMode = @This(); - -// Preset blend modes -pub const BlendAlpha = BlendMode{ - .color_src_factor = .srcAlpha, - .color_dst_factor = .oneMinusSrcAlpha, - .color_equation = .add, - .alpha_src_factor = .one, - .alpha_dst_factor = .oneMinusSrcAlpha, - .alpha_equation = .add -}; - -pub const BlendAdd = BlendMode{ - .color_src_factor = .srcAlpha, - .color_dst_factor = .one, - .color_equation = .add, - .alpha_src_factor = .one, - .alpha_dst_factor = .one, - .alpha_equation = .add -}; - -pub const BlendMultiply = BlendMode{ - .color_src_factor = .dstColor, - .color_dst_factor = .zero, - .color_equation = .add, - .alpha_src_factor = .dstColor, - .alpha_dst_factor = .zero, - .alpha_equation = .add -}; - -pub const BlendMin = BlendMode{ - .color_src_factor = .one, - .color_dst_factor = .one, - .color_equation = .min, - .alpha_src_factor = .one, - .alpha_dst_factor = .one, - .alpha_equation = .min -}; - -pub const BlendMax = BlendMode{ - .color_src_factor = .one, - .color_dst_factor = .one, - .color_equation = .max, - .alpha_src_factor = .one, - .alpha_dst_factor = .one, - .alpha_equation = .max -}; - -pub const BlendNone = BlendMode{ - .color_src_factor = .one, - .color_dst_factor = .zero, - .color_equation = .add, - .alpha_src_factor = .one, - .alpha_dst_factor = .zero, - .alpha_equation = .add -}; - -const sfBlendMode = @import("../sfml_import.zig").c.sfBlendMode; -/// Bitcasts this blendmode to the csfml struct -/// For inner workings -pub fn _toCSFML(self: BlendMode) sfBlendMode { - return @bitCast(sfBlendMode, self); -} - -color_src_factor: Factor, -color_dst_factor: Factor, -color_equation: Equation, -alpha_src_factor: Factor, -alpha_dst_factor: Factor, -alpha_equation: Equation \ No newline at end of file diff --git a/src/sfml/graphics/CircleShape.zig b/src/sfml/graphics/CircleShape.zig deleted file mode 100644 index ea66dcb..0000000 --- a/src/sfml/graphics/CircleShape.zig +++ /dev/null @@ -1,175 +0,0 @@ -//! Specialized shape representing a circle. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const CircleShape = @This(); - -// Constructor/destructor - -/// Inits a circle shape with a radius. The circle will be white and have 30 points -pub fn create(radius: f32) !CircleShape { - var circle = sf.c.sfCircleShape_create(); - if (circle == null) - return sf.Error.nullptrUnknownReason; - - sf.c.sfCircleShape_setFillColor(circle, sf.c.sfWhite); - sf.c.sfCircleShape_setRadius(circle, radius); - - return CircleShape{ ._ptr = circle.? }; -} - -/// Destroys a circle shape -pub fn destroy(self: *CircleShape) void { - sf.c.sfCircleShape_destroy(self._ptr); -} - -// Draw function -pub fn sfDraw(self: CircleShape, window: anytype, states: ?*sf.c.sfRenderStates) void { - switch (@TypeOf(window)) { - sf.RenderWindow => sf.c.sfRenderWindow_drawCircleShape(window._ptr, self._ptr, states), - sf.RenderTexture => sf.c.sfRenderTexture_drawCircleShape(window._ptr, self._ptr, states), - else => @compileError("window must be a render target"), - } -} - -// Getters/setters - -/// Gets the fill color of this circle shape -pub fn getFillColor(self: CircleShape) sf.Color { - return sf.Color._fromCSFML(sf.c.sfCircleShape_getFillColor(self._ptr)); -} -/// Sets the fill color of this circle shape -pub fn setFillColor(self: *CircleShape, color: sf.Color) void { - sf.c.sfCircleShape_setFillColor(self._ptr, color._toCSFML()); -} - -/// Gets the outline color of this circle shape -pub fn getOutlineColor(self: CircleShape) sf.Color { - return sf.Color._fromCSFML(sf.c.sfCircleShape_getOutlineColor(self._ptr)); -} -/// Sets the outline color of this circle shape -pub fn setOutlineColor(self: *CircleShape, color: sf.Color) void { - sf.c.sfCircleShape_setOutlineColor(self._ptr, color._toCSFML()); -} - -/// Gets the outline thickness of this circle shape -pub fn getOutlineThickness(self: CircleShape) f32 { - return sf.c.sfCircleShape_getOutlineThickness(self._ptr); -} -/// Sets the outline thickness of this circle shape -pub fn setOutlineThickness(self: *CircleShape, thickness: f32) void { - sf.c.sfCircleShape_setOutlineThickness(self._ptr, thickness); -} - -/// Gets the radius of this circle shape -pub fn getRadius(self: CircleShape) f32 { - return sf.c.sfCircleShape_getRadius(self._ptr); -} -/// Sets the radius of this circle shape -pub fn setRadius(self: *CircleShape, radius: f32) void { - sf.c.sfCircleShape_setRadius(self._ptr, radius); -} - -/// Gets the position of this circle shape -pub fn getPosition(self: CircleShape) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfCircleShape_getPosition(self._ptr)); -} -/// Sets the position of this circle shape -pub fn setPosition(self: *CircleShape, pos: sf.Vector2f) void { - sf.c.sfCircleShape_setPosition(self._ptr, pos._toCSFML()); -} -/// Adds the offset to this shape's position -pub fn move(self: *CircleShape, offset: sf.Vector2f) void { - sf.c.sfCircleShape_move(self._ptr, offset._toCSFML()); -} - -/// Gets the origin of this circle shape -pub fn getOrigin(self: CircleShape) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfCircleShape_getOrigin(self._ptr)); -} -/// Sets the origin of this circle shape -pub fn setOrigin(self: *CircleShape, origin: sf.Vector2f) void { - sf.c.sfCircleShape_setOrigin(self._ptr, origin._toCSFML()); -} - -/// Gets the rotation of this circle shape -pub fn getRotation(self: CircleShape) f32 { - return sf.c.sfCircleShape_getRotation(self._ptr); -} -/// Sets the rotation of this circle shape -pub fn setRotation(self: *CircleShape, angle: f32) void { - sf.c.sfCircleShape_setRotation(self._ptr, angle); -} -/// Rotates this shape by a given amount -pub fn rotate(self: *CircleShape, angle: f32) void { - sf.c.sfCircleShape_rotate(self._ptr, angle); -} - -/// Gets the texture of this shape -pub fn getTexture(self: CircleShape) ?sf.Texture { - const t = sf.c.sfCircleShape_getTexture(self._ptr); - if (t) |tex| { - return sf.Texture{ ._const_ptr = tex }; - } else return null; -} -/// Sets the texture of this shape -pub fn setTexture(self: *CircleShape, texture: ?sf.Texture) void { - var tex = if (texture) |t| t._get() else null; - sf.c.sfCircleShape_setTexture(self._ptr, tex, 0); -} -/// Gets the sub-rectangle of the texture that the shape will display -pub fn getTextureRect(self: CircleShape) sf.FloatRect { - return sf.FloatRect._fromCSFML(sf.c.sfCircleShape_getTextureRect(self._ptr)); -} -/// Sets the sub-rectangle of the texture that the shape will display -pub fn setTextureRect(self: *CircleShape, rect: sf.FloatRect) void { - sf.c.sfCircleShape_getCircleRect(self._ptr, rect._toCSFML()); -} - -/// Gets the bounds in the local coordinates system -pub fn getLocalBounds(self: CircleShape) sf.FloatRect { - return sf.FloatRect._fromCSFML(sf.c.sfCircleShape_getLocalBounds(self._ptr)); -} - -/// Gets the bounds in the global coordinates -pub fn getGlobalBounds(self: CircleShape) sf.FloatRect { - return sf.FloatRect._fromCSFML(sf.c.sfCircleShape_getGlobalBounds(self._ptr)); -} - -/// Pointer to the csfml structure -_ptr: *sf.c.sfCircleShape, - -test "circle shape: sane getters and setters" { - const tst = @import("std").testing; - - var circle = try CircleShape.create(30); - defer circle.destroy(); - - circle.setFillColor(sf.Color.Yellow); - circle.setOutlineColor(sf.Color.Red); - circle.setOutlineThickness(3); - circle.setRadius(50); - circle.setRotation(15); - circle.setPosition(.{ .x = 1, .y = 2 }); - circle.setOrigin(.{ .x = 20, .y = 25 }); - circle.setTexture(null); - - try tst.expectEqual(sf.Color.Yellow, circle.getFillColor()); - try tst.expectEqual(sf.Color.Red, circle.getOutlineColor()); - try tst.expectEqual(@as(f32, 3), circle.getOutlineThickness()); - try tst.expectEqual(@as(f32, 50), circle.getRadius()); - try tst.expectEqual(@as(f32, 15), circle.getRotation()); - try tst.expectEqual(sf.Vector2f{ .x = 1, .y = 2 }, circle.getPosition()); - try tst.expectEqual(sf.Vector2f{ .x = 20, .y = 25 }, circle.getOrigin()); - try tst.expectEqual(@as(?sf.Texture, null), circle.getTexture()); - - circle.rotate(5); - circle.move(.{ .x = -5, .y = 5 }); - - try tst.expectEqual(@as(f32, 20), circle.getRotation()); - try tst.expectEqual(sf.Vector2f{ .x = -4, .y = 7 }, circle.getPosition()); -} diff --git a/src/sfml/graphics/Font.zig b/src/sfml/graphics/Font.zig deleted file mode 100644 index ecc1a56..0000000 --- a/src/sfml/graphics/Font.zig +++ /dev/null @@ -1,51 +0,0 @@ -//! Class for loading and manipulating character fonts. - -const sf = @import("../sfml.zig"); - -const Font = @This(); - -// Constructor/destructor - -/// Loads a font from a file -pub fn createFromFile(path: [:0]const u8) !Font { - var font = sf.c.sfFont_createFromFile(path); - if (font == null) - return sf.Error.resourceLoadingError; - return Font{ ._ptr = font.? }; -} -/// Destroys a font -pub fn destroy(self: *Font) void { - sf.c.sfFont_destroy(self._ptr); -} - -/// Gets the family name of this font -/// Normally, this is done through getInfo, but as info only contains this data, this makes more sense -pub fn getFamily(self: Font) [*:0]const u8 { - return sf.c.sfFont_getInfo(self._ptr).family; -} - -/// Gets the kerning offset of two glyphs -pub fn getKerning(self: Font, first: u32, second: u32, character_size: usize) f32 { - return sf.c.sfFont_getKerning(self._ptr, first, second, @intCast(c_uint, character_size)); -} - -/// Gets the default spacing between two lines -pub fn getLineSpacing(self: Font, character_size: usize) f32 { - return sf.c.sfFont_getLineSpacing(self._ptr, @intCast(c_uint, character_size)); -} - -/// Gets the vertical offset of the underline -pub fn getUnderlinePosition(self: Font, character_size: usize) f32 { - return sf.c.sfFont_getUnderlinePosition(self._ptr, @intCast(c_uint, character_size)); -} -/// Gets the underline thickness -pub fn getUnderlineThickness(self: Font, character_size: usize) f32 { - return sf.c.sfFont_getUnderlineThickness(self._ptr, @intCast(c_uint, character_size)); -} - -pub const getGlyph = @compileError("Function is not implemented yet."); -pub const initFromMemory = @compileError("Function is not implemented yet."); -pub const initFromStream = @compileError("Function is not implemented yet."); - -/// Pointer to the csfml font -_ptr: *sf.c.sfFont, diff --git a/src/sfml/graphics/Image.zig b/src/sfml/graphics/Image.zig deleted file mode 100644 index 61dd027..0000000 --- a/src/sfml/graphics/Image.zig +++ /dev/null @@ -1,103 +0,0 @@ -//! Class for loading, manipulating and saving images. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const std = @import("std"); -const assert = std.debug.assert; - -const Image = @This(); - -// Constructor/destructor - -/// Creates a new image -pub fn create(size: sf.Vector2u, color: sf.Color) !Image { - var img = sf.c.sfImage_createFromColor(size.x, size.y, color._toCSFML()); - if (img == null) - return sf.Error.nullptrUnknownReason; - return Image{ ._ptr = img.? }; -} - -/// Creates an image from a pixel array -pub fn createFromPixels(size: sf.Vector2u, pixels: []const sf.Color) !Image { - // Check if there is enough data - if (pixels.len < size.x * size.y) - return sf.Error.notEnoughData; - - var img = sf.c.sfImage_createFromPixels(size.x, size.y, @ptrCast([*]const u8, pixels.ptr)); - - if (img == null) - return sf.Error.nullptrUnknownReason; - return Image{ ._ptr = img.? }; -} - -/// Loads an image from a file -pub fn createFromFile(path: [:0]const u8) !Image { - var img = sf.c.sfImage_createFromFile(path); - if (img == null) - return sf.Error.resourceLoadingError; - return Image{ ._ptr = img.? }; -} - -/// Destroys an image -pub fn destroy(self: *Image) void { - sf.c.sfImage_destroy(self._ptr); -} - -// Save an image to a file -pub fn saveToFile(self: Image, path: [:0]const u8) !void { - if (sf.c.sfImage_saveToFile(self._ptr, path) != 1) - return sf.Error.savingInFileFailed; -} - -// Getters/setters - -/// Gets a pixel from this image (bounds are only checked in an assertion) -pub fn getPixel(self: Image, pixel_pos: sf.Vector2u) sf.Color { - const size = self.getSize(); - assert(pixel_pos.x < size.x and pixel_pos.y < size.y); - - return sf.Color._fromCSFML(sf.c.sfImage_getPixel(self._ptr, pixel_pos.x, pixel_pos.y)); -} -/// Sets a pixel on this image (bounds are only checked in an assertion) -pub fn setPixel(self: *Image, pixel_pos: sf.Vector2u, color: sf.Color) void { - const size = self.getSize(); - assert(pixel_pos.x < size.x and pixel_pos.y < size.y); - - sf.c.sfImage_setPixel(self._ptr, pixel_pos.x, pixel_pos.y, color._toCSFML()); -} - -/// Gets the size of this image -pub fn getSize(self: Image) sf.Vector2u { - const size = sf.c.sfImage_getSize(self._ptr); - return sf.Vector2u{ .x = size.x, .y = size.y }; -} - -/// Pointer to the csfml texture -_ptr: *sf.c.sfImage, - -test "image: sane getters and setters" { - const tst = std.testing; - const allocator = std.heap.page_allocator; - - var pixel_data = try allocator.alloc(sf.Color, 30); - defer allocator.free(pixel_data); - - for (pixel_data) |*c, i| { - c.* = sf.Color.fromHSVA(@intToFloat(f32, i) / 30 * 360, 100, 100, 1); - } - - var img = try Image.createFromPixels(.{ .x = 5, .y = 6 }, pixel_data); - defer img.destroy(); - - try tst.expectEqual(sf.Vector2u{ .x = 5, .y = 6 }, img.getSize()); - - img.setPixel(.{ .x = 1, .y = 2 }, sf.Color.Cyan); - try tst.expectEqual(sf.Color.Cyan, img.getPixel(.{ .x = 1, .y = 2 })); - - var tex = try sf.Texture.createFromImage(img, null); - defer tex.destroy(); -} diff --git a/src/sfml/graphics/RectangleShape.zig b/src/sfml/graphics/RectangleShape.zig deleted file mode 100644 index 324199e..0000000 --- a/src/sfml/graphics/RectangleShape.zig +++ /dev/null @@ -1,177 +0,0 @@ -//! Specialized shape representing a rectangle. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const RectangleShape = @This(); - -// Constructor/destructor - -/// Creates a rectangle shape with a size. The rectangle will be white -pub fn create(size: sf.Vector2f) !RectangleShape { - var rect = sf.c.sfRectangleShape_create(); - if (rect == null) - return sf.Error.nullptrUnknownReason; - - sf.c.sfRectangleShape_setFillColor(rect, sf.c.sfWhite); - sf.c.sfRectangleShape_setSize(rect, size._toCSFML()); - - return RectangleShape{ ._ptr = rect.? }; -} - -/// Destroys a rectangle shape -pub fn destroy(self: *RectangleShape) void { - sf.c.sfRectangleShape_destroy(self._ptr); -} - -// Draw function -pub fn sfDraw(self: RectangleShape, window: anytype, states: ?*sf.c.sfRenderStates) void { - switch (@TypeOf(window)) { - sf.RenderWindow => sf.c.sfRenderWindow_drawRectangleShape(window._ptr, self._ptr, states), - sf.RenderTexture => sf.c.sfRenderTexture_drawRectangleShape(window._ptr, self._ptr, states), - else => @compileError("window must be a render target"), - } -} - -// Getters/setters - -/// Gets the fill color of this rectangle shape -pub fn getFillColor(self: RectangleShape) sf.Color { - return sf.Color._fromCSFML(sf.c.sfRectangleShape_getFillColor(self._ptr)); -} -/// Sets the fill color of this rectangle shape -pub fn setFillColor(self: *RectangleShape, color: sf.Color) void { - sf.c.sfRectangleShape_setFillColor(self._ptr, color._toCSFML()); -} - -/// Gets the outline color of this rectangle shape -pub fn getOutlineColor(self: RectangleShape) sf.Color { - return sf.Color._fromCSFML(sf.c.sfRectangleShape_getOutlineColor(self._ptr)); -} -/// Sets the outline color of this rectangle shape -pub fn setOutlineColor(self: *RectangleShape, color: sf.Color) void { - sf.c.sfRectangleShape_setOutlineColor(self._ptr, color._toCSFML()); -} - -/// Gets the outline thickness of this rectangle shape -pub fn getOutlineThickness(self: RectangleShape) f32 { - return sf.c.sfRectangleShape_getOutlineThickness(self._ptr); -} -/// Sets the outline thickness of this rectangle shape -pub fn setOutlineThickness(self: *RectangleShape, thickness: f32) void { - sf.c.sfRectangleShape_setOutlineThickness(self._ptr, thickness); -} - -/// Gets the size of this rectangle shape -pub fn getSize(self: RectangleShape) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfRectangleShape_getSize(self._ptr)); -} -/// Sets the size of this rectangle shape -pub fn setSize(self: *RectangleShape, size: sf.Vector2f) void { - sf.c.sfRectangleShape_setSize(self._ptr, size._toCSFML()); -} - -/// Gets the position of this rectangle shape -pub fn getPosition(self: RectangleShape) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfRectangleShape_getPosition(self._ptr)); -} -/// Sets the position of this rectangle shape -pub fn setPosition(self: *RectangleShape, pos: sf.Vector2f) void { - sf.c.sfRectangleShape_setPosition(self._ptr, pos._toCSFML()); -} -/// Adds the offset to this shape's position -pub fn move(self: *RectangleShape, offset: sf.Vector2f) void { - sf.c.sfRectangleShape_move(self._ptr, offset._toCSFML()); -} - -/// Gets the origin of this rectangle shape -pub fn getOrigin(self: RectangleShape) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfRectangleShape_getOrigin(self._ptr)); -} -/// Sets the origin of this rectangle shape -pub fn setOrigin(self: *RectangleShape, origin: sf.Vector2f) void { - sf.c.sfRectangleShape_setOrigin(self._ptr, origin._toCSFML()); -} - -/// Gets the rotation of this rectangle shape -pub fn getRotation(self: RectangleShape) f32 { - return sf.c.sfRectangleShape_getRotation(self._ptr); -} -/// Sets the rotation of this rectangle shape -pub fn setRotation(self: *RectangleShape, angle: f32) void { - sf.c.sfRectangleShape_setRotation(self._ptr, angle); -} -/// Rotates this shape by a given amount -pub fn rotate(self: *RectangleShape, angle: f32) void { - sf.c.sfRectangleShape_rotate(self._ptr, angle); -} - -/// Gets the texture of this shape -pub fn getTexture(self: RectangleShape) ?sf.Texture { - const t = sf.c.sfRectangleShape_getTexture(self._ptr); - if (t) |tex| { - return sf.Texture{ ._const_ptr = tex }; - } else return null; -} -/// Sets the texture of this shape -pub fn setTexture(self: *RectangleShape, texture: ?sf.Texture) void { - var tex = if (texture) |t| t._get() else null; - sf.c.sfRectangleShape_setTexture(self._ptr, tex, 0); -} -/// Gets the sub-rectangle of the texture that the shape will display -pub fn getTextureRect(self: RectangleShape) sf.FloatRect { - return sf.FloatRect._fromCSFML(sf.c.sfRectangleShape_getTextureRect(self._ptr)); -} -/// Sets the sub-rectangle of the texture that the shape will display -pub fn setTextureRect(self: *RectangleShape, rect: sf.FloatRect) void { - sf.c.sfRectangleShape_getTextureRect(self._ptr, rect._toCSFML()); -} - -/// Gets the bounds in the local coordinates system -pub fn getLocalBounds(self: RectangleShape) sf.FloatRect { - return sf.FloatRect._fromCSFML(sf.c.sfRectangleShape_getLocalBounds(self._ptr)); -} - -/// Gets the bounds in the global coordinates -pub fn getGlobalBounds(self: RectangleShape) sf.FloatRect { - return sf.FloatRect._fromCSFML(sf.c.sfRectangleShape_getGlobalBounds(self._ptr)); -} - -/// Pointer to the csfml structure -_ptr: *sf.c.sfRectangleShape, - -test "rectangle shape: sane getters and setters" { - const tst = @import("std").testing; - - var rect = try RectangleShape.create(sf.Vector2f{ .x = 30, .y = 50 }); - defer rect.destroy(); - - try tst.expectEqual(sf.Vector2f{ .x = 30, .y = 50 }, rect.getSize()); - - rect.setFillColor(sf.Color.Yellow); - rect.setOutlineColor(sf.Color.Red); - rect.setOutlineThickness(3); - rect.setSize(.{ .x = 15, .y = 510 }); - rect.setRotation(15); - rect.setPosition(.{ .x = 1, .y = 2 }); - rect.setOrigin(.{ .x = 20, .y = 25 }); - rect.setTexture(null); //Weirdly, getTexture if texture wasn't set gives a wrong pointer - - try tst.expectEqual(sf.Color.Yellow, rect.getFillColor()); - try tst.expectEqual(sf.Color.Red, rect.getOutlineColor()); - try tst.expectEqual(@as(f32, 3), rect.getOutlineThickness()); - try tst.expectEqual(sf.Vector2f{ .x = 15, .y = 510 }, rect.getSize()); - try tst.expectEqual(@as(f32, 15), rect.getRotation()); - try tst.expectEqual(sf.Vector2f{ .x = 1, .y = 2 }, rect.getPosition()); - try tst.expectEqual(sf.Vector2f{ .x = 20, .y = 25 }, rect.getOrigin()); - try tst.expectEqual(@as(?sf.Texture, null), rect.getTexture()); - - rect.rotate(5); - rect.move(.{ .x = -5, .y = 5 }); - - try tst.expectEqual(@as(f32, 20), rect.getRotation()); - try tst.expectEqual(sf.Vector2f{ .x = -4, .y = 7 }, rect.getPosition()); -} diff --git a/src/sfml/graphics/RenderStates.zig b/src/sfml/graphics/RenderStates.zig deleted file mode 100644 index e7234ae..0000000 --- a/src/sfml/graphics/RenderStates.zig +++ /dev/null @@ -1,20 +0,0 @@ -//! Defines settings for drawing things on a target - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.graphics; -}; - -blend_mode: sf.BlendMode = sf.BlendMode.BlendAlpha, -//transform: null, // TODO: implement transforms (#25) -texture: ?sf.Texture = null, -shader: ?sf.Shader = null, - -pub fn _toCSFML(self: @This()) sf.c.sfRenderStates { - return .{ - .blendMode = self.blend_mode._toCSFML(), - .transform = .{ .matrix = .{ 1, 0, 0, 0, 1, 0, 0, 0, 1} }, - .texture = if (self.texture) |t| t._get() else null, - .shader = if (self.shader) |s| s._ptr else null - }; -} \ No newline at end of file diff --git a/src/sfml/graphics/RenderTexture.zig b/src/sfml/graphics/RenderTexture.zig deleted file mode 100644 index 70b93ba..0000000 --- a/src/sfml/graphics/RenderTexture.zig +++ /dev/null @@ -1,177 +0,0 @@ -//! Target for off-screen 2D rendering into a texture. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const RenderTexture = @This(); - -// Constructor/destructor - -/// Inits a render texture with a size (use createWithDepthBuffer if you want a depth buffer) -pub fn create(size: sf.Vector2u) !RenderTexture { - var rtex = sf.c.sfRenderTexture_create(size.x, size.y, 0); //0 means no depth buffer - - if (rtex) |t| { - return RenderTexture{ ._ptr = t }; - } else return sf.Error.nullptrUnknownReason; -} -/// Inits a render texture with a size, it will have a depth buffer -pub fn createWithDepthBuffer(size: sf.Vector2u) !RenderTexture { - var rtex = sf.c.sfRenderTexture_create(size.x, size.y, 1); - - if (rtex) |t| { - return .{ ._ptr = t }; - } else return sf.Error.nullptrUnknownReason; -} - -/// Destroys this render texture -pub fn destroy(self: *RenderTexture) void { - sf.c.sfRenderTexture_destroy(self._ptr); -} - -// Drawing functions - -/// Clears the drawing target with a color -pub fn clear(self: *RenderTexture, color: sf.Color) void { - sf.c.sfRenderTexture_clear(self._ptr, color._toCSFML()); -} - -/// Updates the texture with what has been drawn on the render area -pub fn display(self: *RenderTexture) void { - sf.c.sfRenderTexture_display(self._ptr); -} - -/// Draw something on the texture (won't be visible until display is called) -/// Object must have a sfDraw function (look at CircleShape for reference) -/// You can pass a render state or null for default -pub fn draw(self: *RenderTexture, to_draw: anytype, states: ?sf.RenderStates) void { - const T = @TypeOf(to_draw); - if (comptime @import("std").meta.trait.hasFn("sfDraw")(T)) { - // Inline call of object's draw function - if (states) |s| { - var cstates = s._toCSFML(); - @call(.{ .modifier = .always_inline }, T.sfDraw, .{ to_draw, self.*, &cstates }); - } else - @call(.{ .modifier = .always_inline }, T.sfDraw, .{ to_draw, self.*, null }); - // to_draw.sfDraw(self, states); - } else @compileError("You must provide a drawable object (struct with \"sfDraw\" method)."); -} - -/// Gets a const reference to the target texture (the reference doesn't change) -pub fn getTexture(self: RenderTexture) sf.Texture { - const tex = sf.c.sfRenderTexture_getTexture(self._ptr); - return sf.Texture{ ._const_ptr = tex.? }; -} - -// Texture related stuff - -/// Generates a mipmap for the current texture data, returns true if the operation succeeded -pub fn generateMipmap(self: *RenderTexture) bool { - return sf.c.sfRenderTexture_generateMipmap(self._ptr) != 0; -} - -/// Tells whether or not the texture is to be smoothed -pub fn isSmooth(self: RenderTexture) bool { - return sf.c.sfRenderTexture_isSmooth(self._ptr) != 0; -} -/// Enables or disables texture smoothing -pub fn setSmooth(self: *RenderTexture, smooth: bool) void { - sf.c.sfRenderTexture_setSmooth(self._ptr, @boolToInt(smooth)); -} - -/// Tells whether or not the texture should repeat when rendering outside its bounds -pub fn isRepeated(self: RenderTexture) bool { - return sf.c.sfRenderTexture_isRepeated(self._ptr) != 0; -} -/// Enables or disables texture repeating -pub fn setRepeated(self: *RenderTexture, repeated: bool) void { - sf.c.sfRenderTexture_setRepeated(self._ptr, @boolToInt(repeated)); -} - -/// Gets the size of this window -pub fn getSize(self: RenderTexture) sf.Vector2u { - return sf.Vector2u._fromCSFML(sf.c.sfRenderTexture_getSize(self._ptr)); -} - -// Target related stuff - -/// Gets the current view of the target -/// Unlike in SFML, you don't get a const pointer but a copy -pub fn getView(self: RenderTexture) sf.View { - return sf.View._fromCSFML(sf.c.sfRenderTexture_getView(self._ptr).?); -} -/// Gets the default view of this target -/// Unlike in SFML, you don't get a const pointer but a copy -pub fn getDefaultView(self: RenderTexture) sf.View { - return sf.View._fromCSFML(sf.c.sfRenderTexture_getDefaultView(self._ptr).?); -} -/// Sets the view of this target -pub fn setView(self: *RenderTexture, view: sf.View) void { - var cview = view._toCSFML(); - defer sf.c.sfView_destroy(cview); - sf.c.sfRenderTexture_setView(self._ptr, cview); -} -/// Gets the viewport of this target -pub fn getViewport(self: RenderTexture, view: sf.View) sf.IntRect { - return sf.IntRect._fromCSFML(sf.c.sfRenderTexture_getViewPort(self._ptr, view._ptr)); -} - -/// Convert a point from target coordinates to world coordinates, using the current view (or the specified view) -pub fn mapPixelToCoords(self: RenderTexture, pixel: sf.Vector2i, view: ?sf.View) sf.Vector2f { - if (view) |v| { - var cview = v._toCSFML(); - defer sf.c.sfView_destroy(cview); - return sf.Vector2f._fromCSFML(sf.c.sfRenderTexture_mapPixelToCoords(self._ptr, pixel._toCSFML(), cview)); - } else return sf.Vector2f._fromCSFML(sf.c.sfRenderTexture_mapPixelToCoords(self._ptr, pixel._toCSFML(), null)); -} -/// Convert a point from world coordinates to target coordinates, using the current view (or the specified view) -pub fn mapCoordsToPixel(self: RenderTexture, coords: sf.Vector2f, view: ?sf.View) sf.Vector2i { - if (view) |v| { - var cview = v._toCSFML(); - defer sf.c.sfView_destroy(cview); - return sf.Vector2i._fromCSFML(sf.c.sfRenderTexture_mapCoordsToPixel(self._ptr, coords._toCSFML(), cview)); - } else return sf.Vector2i._fromCSFML(sf.c.sfRenderTexture_mapCoordsToPixel(self._ptr, coords._toCSFML(), null)); -} - -/// Pointer to the csfml structure -_ptr: *sf.c.sfRenderTexture, - -test "rendertexture tests" { - const tst = @import("std").testing; - - var rentex = try RenderTexture.create(.{ .x = 10, .y = 10 }); - defer rentex.destroy(); - - rentex.setRepeated(true); - rentex.setSmooth(true); - - rentex.clear(sf.Color.Red); - { - var rect = try sf.RectangleShape.create(.{ .x = 5, .y = 5 }); - defer rect.destroy(); - - rect.setFillColor(sf.Color.Blue); - - rentex.draw(rect, null); - } - rentex.display(); - - _ = rentex.generateMipmap(); - - try tst.expect(rentex.isRepeated()); - try tst.expect(rentex.isSmooth()); - - const tex = rentex.getTexture(); - - try tst.expectEqual(sf.Vector2u{ .x = 10, .y = 10 }, tex.getSize()); - try tst.expectEqual(sf.Vector2u{ .x = 10, .y = 10 }, rentex.getSize()); - - var img = tex.copyToImage(); - defer img.destroy(); - - try tst.expectEqual(sf.Color.Blue, img.getPixel(.{ .x = 1, .y = 1 })); - try tst.expectEqual(sf.Color.Red, img.getPixel(.{ .x = 6, .y = 3 })); -} diff --git a/src/sfml/graphics/RenderWindow.zig b/src/sfml/graphics/RenderWindow.zig deleted file mode 100644 index a88adbf..0000000 --- a/src/sfml/graphics/RenderWindow.zig +++ /dev/null @@ -1,206 +0,0 @@ -//! Window that can serve as a target for 2D drawing. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; - pub usingnamespace sf.window; -}; - -const RenderWindow = @This(); - -// Constructor/destructor - -/// Inits a render window with a size, a bits per pixel (most put 32), a title and a style -/// The window will have the default style -pub fn create(size: sf.Vector2u, bpp: usize, title: [:0]const u8, style: u32, settings: ?sf.ContextSettings) !RenderWindow { - var ret: RenderWindow = undefined; - - var mode: sf.c.sfVideoMode = .{ - .width = @intCast(c_uint, size.x), - .height = @intCast(c_uint, size.y), - .bitsPerPixel = @intCast(c_uint, bpp), - }; - - const c_settings = if (settings) |s| s._toCSFML() else null; - var window = sf.c.sfRenderWindow_create(mode, @ptrCast([*c]const u8, title), style, if (c_settings) |s| &s else null); - - if (window) |w| { - ret._ptr = w; - } else return sf.Error.windowCreationFailed; - - return ret; -} -/// Inits a render window with a size and a title -/// The window will have the default style -pub fn createDefault(size: sf.Vector2u, title: [:0]const u8) !RenderWindow { - var ret: RenderWindow = undefined; - - var mode: sf.c.sfVideoMode = .{ - .width = @intCast(c_uint, size.x), - .height = @intCast(c_uint, size.y), - .bitsPerPixel = 32, - }; - - var window = sf.c.sfRenderWindow_create(mode, @ptrCast([*c]const u8, title), sf.window.Style.defaultStyle, null); - - if (window) |w| { - ret._ptr = w; - } else return sf.Error.windowCreationFailed; - - return ret; -} -/// Inits a rendering plane from a window handle. The handle can actually be to any drawing surface. -pub fn createFromHandle(handle: sf.WindowHandle, settings: ?sf.ContextSettings) !RenderWindow { - const c_settings = if (settings) |s| s._toCSFML() else null; - const window = sf.c.sfRenderWindow_createFromHandle(handle, if (c_settings) |s| &s else null); - - if (window) |w| { - return .{ ._ptr = w }; - } else return sf.Error.windowCreationFailed; -} - -/// Destroys this window object -pub fn destroy(self: *RenderWindow) void { - sf.c.sfRenderWindow_destroy(self._ptr); -} - -// Event related - -/// Returns true if this window is still open -pub fn isOpen(self: RenderWindow) bool { - return sf.c.sfRenderWindow_isOpen(self._ptr) != 0; -} - -/// Closes this window -pub fn close(self: *RenderWindow) void { - sf.c.sfRenderWindow_close(self._ptr); -} - -/// Gets an event from the queue, returns null is theres none -/// Use while on this to get all the events in your game loop -pub fn pollEvent(self: *RenderWindow) ?sf.window.Event { - var event: sf.c.sfEvent = undefined; - if (sf.c.sfRenderWindow_pollEvent(self._ptr, &event) == 0) - return null; - - // Skip sfEvtMouseWheelMoved to avoid sending mouseWheelScrolled twice - if (event.type == sf.c.sfEvtMouseWheelMoved) { - return self.pollEvent(); - } - return sf.window.Event._fromCSFML(event); -} - -// Drawing functions - -/// Clears the drawing screen with a color -pub fn clear(self: *RenderWindow, color: sf.Color) void { - sf.c.sfRenderWindow_clear(self._ptr, color._toCSFML()); -} - -/// Displays what has been drawn on the render area -pub fn display(self: *RenderWindow) void { - sf.c.sfRenderWindow_display(self._ptr); -} - -/// Draw something on the screen (won't be visible until display is called) -/// Object must have a sfDraw function (look at CircleShape for reference) -/// You can pass a render state or null for default -pub fn draw(self: *RenderWindow, to_draw: anytype, states: ?sf.RenderStates) void { - const T = @TypeOf(to_draw); - if (comptime @import("std").meta.trait.hasFn("sfDraw")(T)) { - // Inline call of object's draw function - if (states) |s| { - var cstates = s._toCSFML(); - @call(.{ .modifier = .always_inline }, T.sfDraw, .{ to_draw, self.*, &cstates }); - } else - @call(.{ .modifier = .always_inline }, T.sfDraw, .{ to_draw, self.*, null }); - // to_draw.sfDraw(self, states); - } else @compileError("You must provide a drawable object (struct with \"sfDraw\" method)."); -} - -// Getters/setters - -/// Gets the current view of the window -/// Unlike in SFML, you don't get a const pointer but a copy -pub fn getView(self: RenderWindow) sf.View { - return sf.View._fromCSFML(sf.c.sfRenderWindow_getView(self._ptr).?); -} -/// Gets the default view of this window -/// Unlike in SFML, you don't get a const pointer but a copy -pub fn getDefaultView(self: RenderWindow) sf.View { - return sf.View._fromCSFML(sf.c.sfRenderWindow_getDefaultView(self._ptr).?); -} -/// Sets the view of this window -pub fn setView(self: *RenderWindow, view: sf.View) void { - var cview = view._toCSFML(); - defer sf.c.sfView_destroy(cview); - sf.c.sfRenderWindow_setView(self._ptr, cview); -} -/// Gets the viewport of this render target -pub fn getViewport(self: RenderWindow, view: sf.View) sf.IntRect { - return sf.IntRect._fromCSFML(sf.c.sfRenderWindow_getViewPort(self._ptr, view._ptr)); -} - -/// Set mouse cursor grabbing -pub fn setMouseCursorGrabbed(self : RenderWindow, grab : bool) void { - sf.c.sfRenderWindow_setMouseCursorGrabbed(self._ptr, if (grab) 1 else 0); -} - -/// Set mouse cursor visibility -pub fn setMouseCursorVisible(self : RenderWindow, visible : bool) void { - sf.c.sfRenderWindow_setMouseCursorVisible(self._ptr, if (visible) 1 else 0); -} - -/// Gets the size of this window -pub fn getSize(self: RenderWindow) sf.Vector2u { - return sf.Vector2u._fromCSFML(sf.c.sfRenderWindow_getSize(self._ptr)); -} -/// Sets the size of this window -pub fn setSize(self: *RenderWindow, size: sf.Vector2u) void { - sf.c.sfRenderWindow_setSize(self._ptr, size._toCSFML()); -} - -/// Gets the position of this window -pub fn getPosition(self: RenderWindow) sf.Vector2i { - return sf.Vector2i._fromCSFML(sf.c.sfRenderWindow_getPosition(self._ptr)); -} -/// Sets the position of this window -pub fn setPosition(self: *RenderWindow, pos: sf.Vector2i) void { - sf.c.sfRenderWindow_setPosition(self._ptr, pos._toCSFML()); -} - -// TODO : unicode title? -/// Sets the title of this window -pub fn setTitle(self: *RenderWindow, title: [:0]const u8) void { - sf.c.sfRenderWindow_setTitle(self._ptr, title); -} - -/// Sets the windows's framerate limit -pub fn setFramerateLimit(self: *RenderWindow, fps: c_uint) void { - sf.c.sfRenderWindow_setFramerateLimit(self._ptr, fps); -} -/// Enables or disables vertical sync -pub fn setVerticalSyncEnabled(self: *RenderWindow, enabled: bool) void { - sf.c.sfRenderWindow_setVerticalSyncEnabled(self._ptr, @boolToInt(enabled)); -} - -/// Convert a point from target coordinates to world coordinates, using the current view (or the specified view) -pub fn mapPixelToCoords(self: RenderWindow, pixel: sf.Vector2i, view: ?sf.View) sf.Vector2f { - if (view) |v| { - var cview = v._toCSFML(); - defer sf.c.sfView_destroy(cview); - return sf.Vector2f._fromCSFML(sf.c.sfRenderWindow_mapPixelToCoords(self._ptr, pixel._toCSFML(), cview)); - } else return sf.Vector2f._fromCSFML(sf.c.sfRenderWindow_mapPixelToCoords(self._ptr, pixel._toCSFML(), null)); -} -/// Convert a point from world coordinates to target coordinates, using the current view (or the specified view) -pub fn mapCoordsToPixel(self: RenderWindow, coords: sf.Vector2f, view: ?sf.View) sf.Vector2i { - if (view) |v| { - var cview = v._toCSFML(); - defer sf.c.sfView_destroy(cview); - return sf.Vector2i._fromCSFML(sf.c.sfRenderWindow_mapCoordsToPixel(self._ptr, coords._toCSFML(), cview)); - } else return sf.Vector2i._fromCSFML(sf.c.sfRenderWindow_mapCoordsToPixel(self._ptr, coords._toCSFML(), null)); -} - -/// Pointer to the csfml structure -_ptr: *sf.c.sfRenderWindow diff --git a/src/sfml/graphics/Shader.zig b/src/sfml/graphics/Shader.zig deleted file mode 100644 index ea5072c..0000000 --- a/src/sfml/graphics/Shader.zig +++ /dev/null @@ -1,96 +0,0 @@ -//! Shader class - -const sf = @import("../sfml.zig"); -const glsl = sf.graphics.glsl; - -const Shader = @This(); - -// Constructor/destructor - -/// Creates a shader object from shader files, you can omit some shader types by passing null -pub fn createFromFile( - vertex_shader_path: ?[:0]const u8, - geometry_shader_path: ?[:0]const u8, - fragment_shader_path: ?[:0]const u8 -) !Shader { - const shader = sf.c.sfShader_createFromFile( - if (vertex_shader_path) |vsp| @ptrCast([*c]const u8, vsp) else null, - if (geometry_shader_path) |gsp| @ptrCast([*c]const u8, gsp) else null, - if (fragment_shader_path) |fsp| @ptrCast([*c]const u8, fsp) else null - ); - if (shader) |s| { - return Shader{ ._ptr = s }; - } else return sf.Error.nullptrUnknownReason; -} -/// Create a shader object from glsl code as string, you can omit some shader types by passing null -pub fn createFromMemory( - vertex_shader: ?[:0]const u8, - geometry_shader: ?[:0]const u8, - fragment_shader: ?[:0]const u8 -) !Shader { - const shader = sf.c.sfShader_createFromMemory( - if (vertex_shader) |vs| @ptrCast([*c]const u8, vs) else null, - if (geometry_shader) |gs| @ptrCast([*c]const u8, gs) else null, - if (fragment_shader) |fs| @ptrCast([*c]const u8, fs) else null - ); - if (shader) |s| { - return Shader{ ._ptr = s }; - } else return sf.Error.nullptrUnknownReason; -} -/// Destroys this shader object -pub fn destroy(self: *Shader) void { - sf.c.sfShader_destroy(self._ptr); -} - -// Availability - -/// Checks whether or not shaders can be used in the system -pub fn isAvailable() bool { - return sf.c.sfShader_isAvailable(); -} -/// Checks whether or not geometry shaders can be used -pub fn isGeometryAvailable() bool { - return sf.c.sfShader_isAvailable(); -} - -const CurrentTextureT = struct{}; -/// Special value to pass to setUniform to have an uniform of the texture used for drawing -/// which cannot be known in advance -pub const CurrentTexture: CurrentTextureT = .{}; - -// Uniform - -/// Sets an uniform for the shader -/// Colors are vectors so if you want to pass a color use .toIVec4() or .toFVec4() -/// Pass CurrentTexture if you want to have the drawing texture as an uniform, which cannot be known in advance -pub fn setUniform(self: *Shader, name: [:0]const u8, value: anytype) void { - const T = @TypeOf(value); - switch (T) { - f32 => sf.c.sfShader_setFloatUniform(self._ptr, name, value), - c_int => sf.c.sfShader_setIntUniform(self._ptr, name, value), - bool => sf.c.sfShader_setBoolUniform(self._ptr, name, value), - glsl.FVec2 => sf.c.sfShader_setVec2Uniform(self._ptr, name, value._toCSFML()), - glsl.FVec3 => sf.c.sfShader_setVec3Uniform(self._ptr, name, value._toCSFML()), - glsl.FVec4 => sf.c.sfShader_setVec4Uniform(self._ptr, name, @bitCast(sf.c.sfGlslVec4, value)), - glsl.IVec2 => sf.c.sfShader_setIvec2Uniform(self._ptr, name, value._toCSFML()), - glsl.IVec3 => sf.c.sfShader_setIvec3Uniform(self._ptr, name, @bitCast(sf.c.sfGlslIvec3, value)), - glsl.IVec4 => sf.c.sfShader_setIvec4Uniform(self._ptr, name, @bitCast(sf.c.sfGlslIvec4, value)), - glsl.BVec2 => sf.c.sfShader_setBvec2Uniform(self._ptr, name, @bitCast(sf.c.sfGlslBvec2, value)), - glsl.BVec3 => sf.c.sfShader_setBvec3Uniform(self._ptr, name, @bitCast(sf.c.sfGlslBvec3, value)), - glsl.BVec4 => sf.c.sfShader_setBvec4Uniform(self._ptr, name, @bitCast(sf.c.sfGlslBvec4, value)), - glsl.Mat3 => sf.c.sfShader_setMat3Uniform(self._ptr, name, @ptrCast(*const sf.c.sfGlslMat3, @alignCast(4, &value))), - glsl.Mat4 => sf.c.sfShader_setMat4Uniform(self._ptr, name, @ptrCast(*const sf.c.sfGlslMat4, @alignCast(4, &value))), - sf.graphics.Texture => sf.c.sfShader_setTextureUniform(self._ptr, name, value._get()), - CurrentTextureT => sf.c.sfShader_setCurrentTextureUniform(self._ptr, name), - []const f32 => sf.c.sfShader_setFloatUniformArray(self._ptr, name, value.ptr, value.len), - []const glsl.FVec2 => sf.c.sfShader_setVec2UniformArray(self._ptr, name, @ptrCast(*sf.c.sfGlslVec2, value.ptr), value.len), - []const glsl.FVec3 => sf.c.sfShader_setVec3UniformArray(self._ptr, name, @ptrCast(*sf.c.sfGlslVec3, value.ptr), value.len), - []const glsl.FVec4 => sf.c.sfShader_setVec4UniformArray(self._ptr, name, @ptrCast(*sf.c.sfGlslVec4, value.ptr), value.len), - []const glsl.Mat3 => sf.c.sfShader_setMat3UniformArray(self._ptr, name, @ptrCast(*sf.c.sfGlslMat3, value.ptr), value.len), - []const glsl.Mat4 => sf.c.sfShader_setMat4UniformArray(self._ptr, name, @ptrCast(*sf.c.sfGlslVec4, value.ptr), value.len), - else => @compileError("Uniform of type \"" ++ @typeName(T) ++ "\" cannot be set inside shader.") - } -} - -/// Pointer to the CSFML structure -_ptr: *sf.c.sfShader \ No newline at end of file diff --git a/src/sfml/graphics/Sprite.zig b/src/sfml/graphics/Sprite.zig deleted file mode 100644 index 872c980..0000000 --- a/src/sfml/graphics/Sprite.zig +++ /dev/null @@ -1,156 +0,0 @@ -//! Drawable representation of a texture, with its own transformations, color, etc. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const Sprite = @This(); - -// Constructor/destructor - -/// Inits a sprite with no texture -pub fn create() !Sprite { - var sprite = sf.c.sfSprite_create(); - if (sprite == null) - return sf.Error.nullptrUnknownReason; - - return Sprite{ ._ptr = sprite.? }; -} - -/// Inits a sprite with a texture -pub fn createFromTexture(texture: sf.Texture) !Sprite { - var sprite = sf.c.sfSprite_create(); - if (sprite == null) - return sf.Error.nullptrUnknownReason; - - sf.c.sfSprite_setTexture(sprite, texture._get(), 1); - - return Sprite{ ._ptr = sprite.? }; -} - -/// Destroys this sprite -pub fn destroy(self: *Sprite) void { - sf.c.sfSprite_destroy(self._ptr); -} - -// Draw function -pub fn sfDraw(self: Sprite, window: anytype, states: ?*sf.c.sfRenderStates) void { - switch (@TypeOf(window)) { - sf.RenderWindow => sf.c.sfRenderWindow_drawSprite(window._ptr, self._ptr, states), - sf.RenderTexture => sf.c.sfRenderTexture_drawSprite(window._ptr, self._ptr, states), - else => @compileError("window must be a render target"), - } -} - -// Getters/setters - -/// Gets the position of this sprite -pub fn getPosition(self: Sprite) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfSprite_getPosition(self._ptr)); -} -/// Sets the position of this sprite -pub fn setPosition(self: *Sprite, pos: sf.Vector2f) void { - sf.c.sfSprite_setPosition(self._ptr, pos._toCSFML()); -} -/// Adds the offset to this shape's position -pub fn move(self: *Sprite, offset: sf.Vector2f) void { - sf.c.sfSprite_move(self._ptr, offset._toCSFML()); -} - -/// Gets the scale of this sprite -pub fn getScale(self: Sprite) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfSprite_getScale(self._ptr)); -} -/// Sets the scale of this sprite -pub fn setScale(self: *Sprite, factor: sf.Vector2f) void { - sf.c.sfSprite_setScale(self._ptr, factor._toCSFML()); -} -/// Scales this sprite -pub fn scale(self: *Sprite, factor: sf.Vector2f) void { - sf.c.sfSprite_scale(self._ptr, factor._toCSFML()); -} - -/// Gets the origin of this sprite -pub fn getOrigin(self: Sprite) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfSprite_getOrigin(self._ptr)); -} -/// Sets the origin of this sprite -pub fn setOrigin(self: *Sprite, origin: sf.Vector2f) void { - sf.c.sfSprite_setOrigin(self._ptr, origin._toCSFML()); -} - -/// Gets the rotation of this sprite -pub fn getRotation(self: Sprite) f32 { - return sf.c.sfSprite_getRotation(self._ptr); -} -/// Sets the rotation of this sprite -pub fn setRotation(self: *Sprite, angle: f32) void { - sf.c.sfSprite_setRotation(self._ptr, angle); -} -/// Rotates this shape by a given amount -pub fn rotate(self: *Sprite, angle: f32) void { - sf.c.sfSprite_rotate(self._ptr, angle); -} - -/// Gets the color of this sprite -pub fn getColor(self: Sprite) sf.Color { - return sf.Color._fromCSFML(sf.c.sfSprite_getColor(self._ptr)); -} -/// Sets the color of this sprite -pub fn setColor(self: *Sprite, color: sf.Color) void { - sf.c.sfSprite_setColor(self._ptr, color._toCSFML()); -} - -/// Gets the texture of this shape -pub fn getTexture(self: Sprite) ?sf.Texture { - const t = sf.c.sfSprite_getTexture(self._ptr); - if (t) |tex| { - return sf.Texture{ ._const_ptr = tex }; - } else return null; -} -/// Sets this sprite's texture (the sprite will take the texture's dimensions) -pub fn setTexture(self: *Sprite, texture: ?sf.Texture) void { - var tex = if (texture) |t| t._get() else null; - sf.c.sfSprite_setTexture(self._ptr, tex, 1); -} -/// Gets the sub-rectangle of the texture that the sprite will display -pub fn getTextureRect(self: Sprite) sf.IntRect { - return sf.IntRect._fromCSFML(sf.c.sfSprite_getTextureRect(self._ptr)); -} -/// Sets the sub-rectangle of the texture that the sprite will display -pub fn setTextureRect(self: *Sprite, rect: sf.IntRect) void { - sf.c.sfSprite_setTextureRect(self._ptr, rect._toCSFML()); -} - -/// Pointer to the csfml structure -_ptr: *sf.c.sfSprite, - -test "sprite: sane getters and setters" { - const tst = @import("std").testing; - - var spr = try Sprite.create(); - defer spr.destroy(); - - spr.setColor(sf.Color.Yellow); - spr.setRotation(15); - spr.setPosition(.{ .x = 1, .y = 2 }); - spr.setOrigin(.{ .x = 20, .y = 25 }); - spr.setScale(.{ .x = 2, .y = 2 }); - spr.setTexture(null); - - try tst.expectEqual(sf.Color.Yellow, spr.getColor()); - try tst.expectEqual(sf.Vector2f{ .x = 1, .y = 2 }, spr.getPosition()); - try tst.expectEqual(sf.Vector2f{ .x = 20, .y = 25 }, spr.getOrigin()); - try tst.expectEqual(@as(?sf.Texture, null), spr.getTexture()); - try tst.expectEqual(sf.Vector2f{ .x = 2, .y = 2 }, spr.getScale()); - - spr.rotate(5); - spr.move(.{ .x = -5, .y = 5 }); - spr.scale(.{ .x = 5, .y = 5 }); - - try tst.expectEqual(@as(f32, 20), spr.getRotation()); - try tst.expectEqual(sf.Vector2f{ .x = -4, .y = 7 }, spr.getPosition()); - try tst.expectEqual(sf.Vector2f{ .x = 10, .y = 10 }, spr.getScale()); -} diff --git a/src/sfml/graphics/Text.zig b/src/sfml/graphics/Text.zig deleted file mode 100644 index b64a2f4..0000000 --- a/src/sfml/graphics/Text.zig +++ /dev/null @@ -1,209 +0,0 @@ -//! Graphical text that can be drawn to a render target. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const Text = @This(); - -// Constructor/destructor - -/// Inits an empty text -pub fn create() !Text { - var text = sf.c.sfText_create(); - if (text == null) - return sf.Error.nullptrUnknownReason; - return Text{ ._ptr = text.? }; -} -/// Inits a text with content -pub fn createWithText(string: [:0]const u8, font: sf.Font, character_size: usize) !Text { - var text = sf.c.sfText_create(); - if (text == null) - return sf.Error.nullptrUnknownReason; - sf.c.sfText_setFont(text, font._ptr); - sf.c.sfText_setCharacterSize(text, @intCast(c_uint, character_size)); - sf.c.sfText_setString(text, string); - return Text{ ._ptr = text.? }; -} -/// Destroys a text -pub fn destroy(self: *Text) void { - sf.c.sfText_destroy(self._ptr); -} - -// Draw function -pub fn sfDraw(self: Text, window: anytype, states: ?*sf.c.sfRenderStates) void { - switch (@TypeOf(window)) { - sf.RenderWindow => sf.c.sfRenderWindow_drawText(window._ptr, self._ptr, states), - sf.RenderTexture => sf.c.sfRenderTexture_drawText(window._ptr, self._ptr, states), - else => @compileError("window must be a render target"), - } -} - -// Getters/setters - -/// Sets the content of this text -pub fn setString(self: *Text, string: [:0]const u8) void { - sf.c.sfText_setString(self._ptr, string); -} - -/// Sets the font of this text -pub fn setFont(self: *Text, font: sf.Font) void { - sf.c.sfText_setFont(self._ptr, font._ptr); -} - -/// Gets the character size of this text -pub fn getCharacterSize(self: Text) usize { - return @intCast(usize, sf.c.sfText_getCharacterSize(self._ptr)); -} -/// Sets the character size of this text -pub fn setCharacterSize(self: *Text, character_size: usize) void { - sf.c.sfText_setCharacterSize(self._ptr, @intCast(c_uint, character_size)); -} - -/// Gets the fill color of this text -pub fn getFillColor(self: Text) sf.Color { - return sf.Color._fromCSFML(sf.c.sfText_getFillColor(self._ptr)); -} -/// Sets the fill color of this text -pub fn setFillColor(self: *Text, color: sf.Color) void { - sf.c.sfText_setFillColor(self._ptr, color._toCSFML()); -} - -/// Gets the outline color of this text -pub fn getOutlineColor(self: Text) sf.Color { - return sf.Color._fromCSFML(sf.c.sfText_getOutlineColor(self._ptr)); -} -/// Sets the outline color of this text -pub fn setOutlineColor(self: *Text, color: sf.Color) void { - sf.c.sfText_setOutlineColor(self._ptr, color._toCSFML()); -} - -/// Gets the outline thickness of this text -pub fn getOutlineThickness(self: Text) f32 { - return sf.c.sfText_getOutlineThickness(self._ptr); -} -/// Sets the outline thickness of this text -pub fn setOutlineThickness(self: *Text, thickness: f32) void { - sf.c.sfText_setOutlineThickness(self._ptr, thickness); -} - -/// Gets the position of this text -pub fn getPosition(self: Text) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfText_getPosition(self._ptr)); -} -/// Sets the position of this text -pub fn setPosition(self: *Text, pos: sf.Vector2f) void { - sf.c.sfText_setPosition(self._ptr, pos._toCSFML()); -} -/// Adds the offset to this text -pub fn move(self: *Text, offset: sf.Vector2f) void { - sf.c.sfText_move(self._ptr, offset._toCSFML()); -} - -/// Gets the origin of this text -pub fn getOrigin(self: Text) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfText_getOrigin(self._ptr)); -} -/// Sets the origin of this text -pub fn setOrigin(self: *Text, origin: sf.Vector2f) void { - sf.c.sfText_setOrigin(self._ptr, origin._toCSFML()); -} - -/// Gets the rotation of this text -pub fn getRotation(self: Text) f32 { - return sf.c.sfText_getRotation(self._ptr); -} -/// Sets the rotation of this text -pub fn setRotation(self: *Text, angle: f32) void { - sf.c.sfText_setRotation(self._ptr, angle); -} -/// Rotates this text by a given amount -pub fn rotate(self: *Text, angle: f32) void { - sf.c.sfText_rotate(self._ptr, angle); -} - -/// Gets the scale of this text -pub fn getScale(self: Text) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfText_getScale(self._ptr)); -} -/// Sets the scale of this text -pub fn setScale(self: *Text, factor: sf.Vector2f) void { - sf.c.sfText_setScale(self._ptr, factor._toCSFML()); -} -/// Scales this text -pub fn scale(self: *Text, factor: sf.Vector2f) void { - sf.c.sfText_scale(self._ptr, factor._toCSFML()); -} - -/// return the position of the index-th character -pub fn findCharacterPos(self: Text, index: usize) sf.Vector2f { - return sf.Vector2f._fromCSFML(sf.c.sfText_findCharacterPos(self._ptr, index)); -} - -/// Gets the letter spacing factor -pub fn getLetterSpacing(self: Text) f32 { - return sf.c.sfText_getLetterSpacing(self._ptr); -} -/// Sets the letter spacing factor -pub fn setLetterSpacing(self: *Text, spacing_factor: f32) void { - sf.c.sfText_setLetterSpacing(self._ptr, spacing_factor); -} - -/// Gets the line spacing factor -pub fn getLineSpacing(self: Text) f32 { - return sf.c.sfText_getLineSpacing(self._ptr); -} -/// Sets the line spacing factor -pub fn setLineSpacing(self: *Text, spacing_factor: f32) void { - sf.c.sfText_setLineSpacing(self._ptr, spacing_factor); -} - -/// Gets the local bounding rectangle of the text -pub fn getLocalBounds(self: Text) sf.FloatRect { - return sf.FloatRect._fromCSFML(sf.c.sfText_getLocalBounds(self._ptr)); -} -/// Gets the global bounding rectangle of the text -pub fn getGlobalBounds(self: Text) sf.FloatRect { - return sf.FloatRect._fromCSFML(sf.c.sfText_getGlobalBounds(self._ptr)); -} - -pub const getTransform = @compileError("Function is not implemented yet."); -pub const getInverseTransform = @compileError("Function is not implemented yet."); - -/// Pointer to the csfml font -_ptr: *sf.c.sfText, - -test "text: sane getters and setters" { - const tst = @import("std").testing; - - var text = try Text.create(); - defer text.destroy(); - - text.setString("hello"); - text.setFillColor(sf.Color.Yellow); - text.setOutlineColor(sf.Color.Red); - text.setOutlineThickness(2); - text.setCharacterSize(10); - text.setRotation(15); - text.setPosition(.{ .x = 1, .y = 2 }); - text.setOrigin(.{ .x = 20, .y = 25 }); - text.setScale(.{ .x = 2, .y = 2 }); - - text.rotate(5); - text.move(.{ .x = -5, .y = 5 }); - text.scale(.{ .x = 2, .y = 3 }); - - try tst.expectEqual(sf.Color.Yellow, text.getFillColor()); - try tst.expectEqual(sf.Color.Red, text.getOutlineColor()); - try tst.expectEqual(@as(f32, 2), text.getOutlineThickness()); - try tst.expectEqual(@as(usize, 10), text.getCharacterSize()); - try tst.expectEqual(@as(f32, 20), text.getRotation()); - try tst.expectEqual(sf.Vector2f{ .x = -4, .y = 7 }, text.getPosition()); - try tst.expectEqual(sf.Vector2f{ .x = 20, .y = 25 }, text.getOrigin()); - try tst.expectEqual(sf.Vector2f{ .x = 4, .y = 6 }, text.getScale()); - - _ = text.getLocalBounds(); - _ = text.getGlobalBounds(); -} diff --git a/src/sfml/graphics/VertexArray.zig b/src/sfml/graphics/VertexArray.zig deleted file mode 100644 index d340600..0000000 --- a/src/sfml/graphics/VertexArray.zig +++ /dev/null @@ -1,36 +0,0 @@ -//! Define a set of one or more 2D primitives. - -const sf = @import("../sfml.zig"); - -// CONSTRUCTION ZONE - -const VertexArray = @This(); - -/// Creates a vertex array from a slice of vertices -pub fn createFromSlice(vertex: []const sf.graphics.Vertex, primitive: sf.graphics.PrimitiveType) !VertexArray { - var va = sf.c.sfVertexArray_create(); - if (va) |vert| { - sf.c.sfVertexArray_setPrimitiveType(vert, @enumToInt(primitive)); - sf.c.sfVertexArray_resize(vert, vertex.len); - for (vertex) |v, i| - sf.c.sfVertexArray_getVertex(vert, i).* = @bitCast(sf.c.sfVertex, v); - return VertexArray{ ._ptr = vert }; - } else return sf.Error.nullptrUnknownReason; -} - -/// Destroys a vertex array -pub fn destroy(self: *VertexArray) void { - sf.c.sfVertexArray_destroy(self._ptr); -} - -// Draw function -pub fn sfDraw(self: VertexArray, window: anytype, states: ?*sf.c.sfRenderStates) void { - switch (@TypeOf(window)) { - sf.graphics.RenderWindow => sf.c.sfRenderWindow_drawVertexArray(window._ptr, self._ptr, states), - sf.graphics.RenderTexture => sf.c.sfRenderTexture_drawVertexArray(window._ptr, self._ptr, states), - else => @compileError("window must be a render target"), - } -} - -/// Pointer to the csfml structure -_ptr: *sf.c.sfVertexArray, diff --git a/src/sfml/graphics/View.zig b/src/sfml/graphics/View.zig deleted file mode 100644 index 130bb66..0000000 --- a/src/sfml/graphics/View.zig +++ /dev/null @@ -1,104 +0,0 @@ -//! 2D camera that defines what region is shown on screen. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const View = @This(); - -/// Creates a view from a rectangle -pub fn fromRect(rect: sf.FloatRect) View { - var ret: View = undefined; - ret.center = rect.getCorner(); - ret.size = rect.getSize(); - ret.center = ret.center.add(ret.size.scale(0.5)); - ret.viewport = sf.FloatRect.init(0, 0, 1, 1); - return ret; -} - -/// Creates a view from a CSFML object -/// This is mainly for the inner workings of this wrapper -pub fn _fromCSFML(view: *const sf.c.sfView) View { - var ret: View = undefined; - ret.center = sf.Vector2f._fromCSFML(sf.c.sfView_getCenter(view)); - ret.size = sf.Vector2f._fromCSFML(sf.c.sfView_getSize(view)); - ret.viewport = sf.FloatRect._fromCSFML(sf.c.sfView_getViewport(view)); - return ret; -} - -/// Creates a CSFML view from this view -/// This is mainly for the inner workings of this wrapper -/// The resulting view must be destroyed! -pub fn _toCSFML(self: View) *sf.c.sfView { - var view = sf.c.sfView_create().?; - sf.c.sfView_setCenter(view, self.center._toCSFML()); - sf.c.sfView_setSize(view, self.size._toCSFML()); - sf.c.sfView_setViewport(view, self.viewport._toCSFML()); - return view; -} - -pub fn getRect(self: View) sf.FloatRect { - return sf.FloatRect.init( - self.center.x - self.size.x / 2, - self.center.y - self.size.y / 2, - self.size.x, - self.size.y, - ); -} - -pub fn setSize(self: *View, size: sf.Vector2f) void { - self.size = size; -} - -pub fn setCenter(self: *View, center: sf.Vector2f) void { - self.center = center; -} - -pub fn zoom(self: *View, factor: f32) void { - self.size = .{ .x = self.size.x * factor, .y = self.size.y * factor }; -} - -// View variables -/// Center of the view, what this view "looks" at -center: sf.Vector2f, -/// Width and height of the view -size: sf.Vector2f, -/// The viewport of this view -viewport: sf.FloatRect, - -test "view: from rect" { - const tst = @import("std").testing; - - // Testing if the view from rect initialization works - var rect = sf.FloatRect.init(10, -15, 700, 600); - - var view = sf.c.sfView_createFromRect(rect._toCSFML()); - defer sf.c.sfView_destroy(view); - - var view2 = View.fromRect(rect); - - var center = sf.Vector2f._fromCSFML(sf.c.sfView_getCenter(view)); - var size = sf.Vector2f._fromCSFML(sf.c.sfView_getSize(view)); - - try tst.expectApproxEqAbs(center.x, view2.center.x, 0.00001); - try tst.expectApproxEqAbs(center.y, view2.center.y, 0.00001); - try tst.expectApproxEqAbs(size.x, view2.size.x, 0.00001); - try tst.expectApproxEqAbs(size.y, view2.size.y, 0.00001); - - var rect_ret = view2.getRect(); - - try tst.expectApproxEqAbs(rect.left, rect_ret.left, 0.00001); - try tst.expectApproxEqAbs(rect.top, rect_ret.top, 0.00001); - try tst.expectApproxEqAbs(rect.width, rect_ret.width, 0.00001); - try tst.expectApproxEqAbs(rect.height, rect_ret.height, 0.00001); - - view2.setCenter(.{ .x = 400, .y = 300 }); - view2.setSize(.{ .x = 800, .y = 600 }); - rect_ret = view2.getRect(); - try tst.expectApproxEqAbs(@as(f32, 0), rect_ret.left, 0.00001); - try tst.expectApproxEqAbs(@as(f32, 0), rect_ret.top, 0.00001); - try tst.expectApproxEqAbs(@as(f32, 800), rect_ret.width, 0.00001); - try tst.expectApproxEqAbs(@as(f32, 600), rect_ret.height, 0.00001); -} diff --git a/src/sfml/graphics/color.zig b/src/sfml/graphics/color.zig deleted file mode 100644 index bea5666..0000000 --- a/src/sfml/graphics/color.zig +++ /dev/null @@ -1,185 +0,0 @@ -//! Utility class for manipulating RGBA colors. - -const sf = @import("../sfml_import.zig"); -const math = @import("std").math; - -pub const Color = packed struct { - /// Converts a color from a csfml object - /// For inner workings - pub fn _fromCSFML(col: sf.c.sfColor) Color { - return @bitCast(Color, col); - } - - /// Converts this color to a csfml one - /// For inner workings - pub fn _toCSFML(self: Color) sf.c.sfColor { - return @bitCast(sf.c.sfColor, self); - } - - /// Inits a color with rgb components - pub fn fromRGB(red: u8, green: u8, blue: u8) Color { - return Color{ - .r = red, - .g = green, - .b = blue, - .a = 0xff, - }; - } - - /// Inits a color with rgba components - pub fn fromRGBA(red: u8, green: u8, blue: u8, alpha: u8) Color { - return Color{ - .r = red, - .g = green, - .b = blue, - .a = alpha, - }; - } - - /// Inits a color from a 32bits value (RGBA in that order) - pub fn fromInteger(int: u32) Color { - return Color{ - .r = @truncate(u8, (int & 0xff000000) >> 24), - .g = @truncate(u8, (int & 0x00ff0000) >> 16), - .b = @truncate(u8, (int & 0x0000ff00) >> 8), - .a = @truncate(u8, (int & 0x000000ff) >> 0), - }; - } - - /// Gets a 32 bit integer representing the color - pub fn toInteger(self: Color) u32 { - return (@intCast(u32, self.r) << 24) | - (@intCast(u32, self.g) << 16) | - (@intCast(u32, self.b) << 8) | - (@intCast(u32, self.a) << 0); - } - - /// Creates a color with rgba floats from 0 to 1 - fn fromFloats(red: f32, green: f32, blue: f32, alpha: f32) Color { - return Color{ - .r = @floatToInt(u8, math.clamp(red, 0.0, 1.0) * 255.0), - .g = @floatToInt(u8, math.clamp(green, 0.0, 1.0) * 255.0), - .b = @floatToInt(u8, math.clamp(blue, 0.0, 1.0) * 255.0), - .a = @floatToInt(u8, math.clamp(alpha, 0.0, 1.0) * 255.0), - }; - } - - /// Creates a color from HSV and transparency components (this is not part of the SFML) - /// hue is in degrees, saturation and value are in percents - pub fn fromHSVA(hue: f32, saturation: f32, value: f32, alpha: f32) Color { - const h = hue; - const s = saturation / 100; - const v = value / 100; - const a = alpha; - - var hh: f32 = h; - - if (v <= 0.0) - return fromFloats(0, 0, 0, a); - - if (hh >= 360.0) - hh = 0; - hh /= 60.0; - - var ff: f32 = hh - math.floor(hh); - - var p: f32 = v * (1.0 - s); - var q: f32 = v * (1.0 - (s * ff)); - var t: f32 = v * (1.0 - (s * (1.0 - ff))); - - return switch (@floatToInt(usize, hh)) { - 0 => fromFloats(v, t, p, a), - 1 => fromFloats(q, v, p, a), - 2 => fromFloats(p, v, t, a), - 3 => fromFloats(p, q, v, a), - 4 => fromFloats(t, p, v, a), - else => fromFloats(v, p, q, a), - }; - } - - /// Get a GLSL float vector for this color (for shaders) - pub fn toFVec4(self: Color) sf.graphics.glsl.FVec4 { - return .{ - .x = @intToFloat(f32, self.r) / 255.0, - .y = @intToFloat(f32, self.g) / 255.0, - .z = @intToFloat(f32, self.b) / 255.0, - .w = @intToFloat(f32, self.a) / 255.0 - }; - } - /// Get a GLSL int vector for this color (for shaders) - pub fn toIVec4(self: Color) sf.graphcis.glsl.IVec4 { - return .{ - .x = self.r, - .y = self.g, - .z = self.b, - .w = self.a - }; - } - - // Colors - /// Black color - pub const Black = Color.fromRGB(0, 0, 0); - /// White color - pub const White = Color.fromRGB(255, 255, 255); - /// Red color - pub const Red = Color.fromRGB(255, 0, 0); - /// Green color - pub const Green = Color.fromRGB(0, 255, 0); - /// Blue color - pub const Blue = Color.fromRGB(0, 0, 255); - /// Yellow color - pub const Yellow = Color.fromRGB(255, 255, 0); - /// Magenta color - pub const Magenta = Color.fromRGB(255, 0, 255); - /// Cyan color - pub const Cyan = Color.fromRGB(0, 255, 255); - /// Transparent color - pub const Transparent = Color.fromRGBA(0, 0, 0, 0); - - /// Red component - r: u8, - /// Green component - g: u8, - /// Blue component - b: u8, - /// Alpha (opacity) component - a: u8, -}; - -test "color: conversions" { - const tst = @import("std").testing; - - var code: u32 = 0x4BDA9CFF; - var col = Color.fromInteger(code); - - try tst.expectEqual(Color.fromRGB(75, 218, 156), col); - try tst.expectEqual(code, col.toInteger()); - - var csfml_col = sf.c.sfColor_fromInteger(@as(c_uint, code)); - - try tst.expectEqual(Color._fromCSFML(csfml_col), col); -} - -test "color: hsv to rgb" { - const tst = @import("std").testing; - - var col = Color.fromHSVA(10, 20, 100, 255); - - try tst.expectEqual(Color.fromRGB(255, 212, 204), col); -} - -test "color: sane from/to CSFML color" { - const tst = @import("std").testing; - - const col = Color.fromRGBA(5, 12, 28, 127); - const ccol = col._toCSFML(); - - try tst.expectEqual(col.r, ccol.r); - try tst.expectEqual(col.g, ccol.g); - try tst.expectEqual(col.b, ccol.b); - try tst.expectEqual(col.a, ccol.a); - - const col2 = Color._fromCSFML(ccol); - - try tst.expectEqual(col, col2); -} diff --git a/src/sfml/graphics/glsl.zig b/src/sfml/graphics/glsl.zig deleted file mode 100644 index aa00ffa..0000000 --- a/src/sfml/graphics/glsl.zig +++ /dev/null @@ -1,16 +0,0 @@ -const sf = @import("../sfml.zig").system; - -pub const FVec2 = sf.Vector2(f32); -pub const FVec3 = sf.Vector3(f32); -pub const FVec4 = sf.Vector4(f32); - -pub const IVec2 = sf.Vector2(c_int); -pub const IVec3 = sf.Vector3(c_int); -pub const IVec4 = sf.Vector4(c_int); - -pub const BVec2 = sf.Vector2(bool); -pub const BVec3 = sf.Vector3(bool); -pub const BVec4 = sf.Vector4(bool); - -pub const Mat3 = [3 * 3]f32; -pub const Mat4 = [4 * 4]f32; \ No newline at end of file diff --git a/src/sfml/graphics/primitive_type.zig b/src/sfml/graphics/primitive_type.zig deleted file mode 100644 index 9e191a5..0000000 --- a/src/sfml/graphics/primitive_type.zig +++ /dev/null @@ -1,9 +0,0 @@ -pub const PrimitiveType = enum(c_uint) { - Points, - Lines, - LineStrip, - Triangles, - TriangleStrip, - TriangleFan, - Quads, -}; diff --git a/src/sfml/graphics/rect.zig b/src/sfml/graphics/rect.zig deleted file mode 100644 index 2d7d0ef..0000000 --- a/src/sfml/graphics/rect.zig +++ /dev/null @@ -1,161 +0,0 @@ -//! Utility class for manipulating 2D axis aligned rectangles. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; -}; -const math = @import("std").math; - -pub fn Rect(comptime T: type) type { - return packed struct { - const Self = @This(); - - /// The CSFML vector type equivalent - const CsfmlEquivalent = switch (T) { - c_int => sf.c.sfIntRect, - f32 => sf.c.sfFloatRect, - else => void, - }; - - /// Creates a rect (just for convinience) - pub fn init(left: T, top: T, width: T, height: T) Self { - return Self{ - .left = left, - .top = top, - .width = width, - .height = height, - }; - } - - /// Makes a CSFML rect with this rect (only if the corresponding type exists) - /// This is mainly for the inner workings of this wrapper - pub fn _toCSFML(self: Self) CsfmlEquivalent { - if (CsfmlEquivalent == void) @compileError("This rectangle type doesn't have a CSFML equivalent."); - return @bitCast(CsfmlEquivalent, self); - } - - /// Creates a rect from a CSFML one (only if the corresponding type exists) - /// This is mainly for the inner workings of this wrapper - pub fn _fromCSFML(rect: CsfmlEquivalent) Self { - if (CsfmlEquivalent == void) @compileError("This rectangle type doesn't have a CSFML equivalent."); - return @bitCast(Self, rect); - } - - /// Checks if a point is inside this recangle - pub fn contains(self: Self, vec: sf.Vector2(T)) bool { - // Shamelessly stolen - var min_x: T = math.min(self.left, self.left + self.width); - var max_x: T = math.max(self.left, self.left + self.width); - var min_y: T = math.min(self.top, self.top + self.height); - var max_y: T = math.max(self.top, self.top + self.height); - - return (vec.x >= min_x and - vec.x < max_x and - vec.y >= min_y and - vec.y < max_y); - } - - /// Checks if two rectangles have a common intersection, if yes returns that zone, if not returns null - pub fn intersects(self: Self, other: Self) ?Self { - // Shamelessly stolen too - var r1_min_x: T = math.min(self.left, self.left + self.width); - var r1_max_x: T = math.max(self.left, self.left + self.width); - var r1_min_y: T = math.min(self.top, self.top + self.height); - var r1_max_y: T = math.max(self.top, self.top + self.height); - - var r2_min_x: T = math.min(other.left, other.left + other.width); - var r2_max_x: T = math.max(other.left, other.left + other.width); - var r2_min_y: T = math.min(other.top, other.top + other.height); - var r2_max_y: T = math.max(other.top, other.top + other.height); - - var inter_left: T = math.max(r1_min_x, r2_min_x); - var inter_top: T = math.max(r1_min_y, r2_min_y); - var inter_right: T = math.min(r1_max_x, r2_max_x); - var inter_bottom: T = math.min(r1_max_y, r2_max_y); - - if (inter_left < inter_right and inter_top < inter_bottom) { - return Self.init(inter_left, inter_top, inter_right - inter_left, inter_bottom - inter_top); - } else { - return null; - } - } - - /// Checks if two rectangles are the same - pub fn equals(self: Self, other: Self) bool { - return (self.left == other.left and - self.top == other.top and - self.width == other.width and - self.height == other.height); - } - - /// Gets a vector with left and top components inside - pub fn getCorner(self: Self) sf.Vector2(T) { - return sf.Vector2(T){ .x = self.left, .y = self.top }; - } - /// Gets a vector with the bottom right corner coordinates - pub fn getOtherCorner(self: Self) sf.Vector2(T) { - return self.getCorner().add(self.getSize()); - } - /// Gets a vector with width and height components inside - pub fn getSize(self: Self) sf.Vector2(T) { - return sf.Vector2(T){ .x = self.width, .y = self.height }; - } - - /// x component of the top left corner - left: T, - /// x component of the top left corner - top: T, - /// width of the rectangle - width: T, - /// height of the rectangle - height: T - }; -} - -test "rect: intersect" { - const tst = @import("std").testing; - - var r1 = Rect(c_int).init(0, 0, 10, 10); - var r2 = Rect(c_int).init(6, 6, 20, 20); - var r3 = Rect(c_int).init(-5, -5, 10, 10); - - try tst.expectEqual(@as(?Rect(c_int), null), r2.intersects(r3)); - - var inter1: sf.c.sfIntRect = undefined; - var inter2: sf.c.sfIntRect = undefined; - - try tst.expectEqual(sf.c.sfIntRect_intersects(&r1._toCSFML(), &r2._toCSFML(), &inter1), 1); - try tst.expectEqual(sf.c.sfIntRect_intersects(&r1._toCSFML(), &r3._toCSFML(), &inter2), 1); - - try tst.expectEqual(Rect(c_int)._fromCSFML(inter1), r1.intersects(r2).?); - try tst.expectEqual(Rect(c_int)._fromCSFML(inter2), r1.intersects(r3).?); -} - -test "rect: contains" { - const tst = @import("std").testing; - - var r1 = Rect(f32).init(0, 0, 10, 10); - - try tst.expect(r1.contains(.{ .x = 0, .y = 0 })); - try tst.expect(r1.contains(.{ .x = 9, .y = 9 })); - try tst.expect(!r1.contains(.{ .x = 5, .y = -1 })); - try tst.expect(!r1.contains(.{ .x = 10, .y = 5 })); -} - -test "rect: sane from/to CSFML rect" { - const tst = @import("std").testing; - - inline for ([_]type{ c_int, f32 }) |T| { - const rect = Rect(T).init(1, 3, 5, 10); - const crect = rect._toCSFML(); - - try tst.expectEqual(rect.left, crect.left); - try tst.expectEqual(rect.top, crect.top); - try tst.expectEqual(rect.width, crect.width); - try tst.expectEqual(rect.height, crect.height); - - const rect2 = Rect(T)._fromCSFML(crect); - - try tst.expectEqual(rect, rect2); - } -} diff --git a/src/sfml/graphics/texture.zig b/src/sfml/graphics/texture.zig deleted file mode 100644 index 55de1ae..0000000 --- a/src/sfml/graphics/texture.zig +++ /dev/null @@ -1,265 +0,0 @@ -//! Image living on the graphics card that can be used for drawing. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const std = @import("std"); -const assert = std.debug.assert; - -const TextureType = enum { _ptr, _const_ptr }; - -pub const Texture = union(TextureType) { - // Constructor/destructor - - /// Creates a texture from nothing - pub fn create(size: sf.Vector2u) !Texture { - const tex = sf.c.sfTexture_create(@intCast(c_uint, size.x), @intCast(c_uint, size.y)); - if (tex == null) - return sf.Error.nullptrUnknownReason; - return Texture{ ._ptr = tex.? }; - } - /// Loads a texture from a file - pub fn createFromFile(path: [:0]const u8) !Texture { - const tex = sf.c.sfTexture_createFromFile(path, null); - if (tex == null) - return sf.Error.resourceLoadingError; - return Texture{ ._ptr = tex.? }; - } - /// Creates an texture from an image - pub fn createFromImage(image: sf.Image, area: ?sf.IntRect) !Texture { - const tex = if (area) |a| - sf.c.sfTexture_createFromImage(image._ptr, &a._toCSFML()) - else - sf.c.sfTexture_createFromImage(image._ptr, null); - - if (tex == null) - return sf.Error.nullptrUnknownReason; - return Texture{ ._ptr = tex.? }; - } - - /// Destroys a texture - /// Be careful, you can only destroy non const textures - pub fn destroy(self: *Texture) void { - // TODO : is it possible to detect that comptime? - // Should this panic? - if (self.* == ._const_ptr) - @panic("Can't destroy a const texture pointer"); - sf.c.sfTexture_destroy(self._ptr); - } - - // Getters/Setters - - /// Gets a const pointer to this texture - /// For inner workings - pub fn _get(self: Texture) *const sf.c.sfTexture { - return switch (self) { - ._ptr => self._ptr, - ._const_ptr => self._const_ptr, - }; - } - - /// Clones this texture (the clone won't be const) - pub fn copy(self: Texture) !Texture { - const cpy = sf.c.sfTexture_copy(self._get()); - if (cpy == null) - return sf.Error.nullptrUnknownReason; - return Texture{ ._ptr = cpy.? }; - } - /// Copy this texture to an image in ram - pub fn copyToImage(self: Texture) sf.Image { - return .{ ._ptr = sf.c.sfTexture_copyToImage(self._get()).? }; - } - - /// Makes this texture constant (I don't know why you would do that) - pub fn makeConst(self: *Texture) void { - self.* = Texture{ ._const_ptr = self._get() }; - } - - /// Gets the size of this image - pub fn getSize(self: Texture) sf.Vector2u { - const size = sf.c.sfTexture_getSize(self._get()); - return sf.Vector2u{ .x = size.x, .y = size.y }; - } - /// Gets the pixel count of this image - pub fn getPixelCount(self: Texture) usize { - const dim = self.getSize(); - return dim.x * dim.y; - } - - /// Updates the pixels of the image from an array of pixels (colors) - pub fn updateFromPixels(self: *Texture, pixels: []const sf.Color, zone: ?sf.Rect(c_uint)) !void { - if (self.* == ._const_ptr) - @panic("Can't set pixels on a const texture"); - if (self.isSrgb()) - @panic("Updating an srgb from a pixel array isn't implemented"); - - var real_zone: sf.Rect(c_uint) = undefined; - var size = self.getSize(); - - if (zone) |z| { - // Check if the given zone is fully inside the image - var intersection = z.intersects(sf.Rect(c_uint).init(0, 0, size.x, size.y)); - - if (intersection) |i| { - if (!i.equals(z)) - return sf.Error.areaDoesNotFit; - } else return sf.Error.areaDoesNotFit; - - real_zone = z; - } else { - real_zone.left = 0; - real_zone.top = 0; - real_zone.width = size.x; - real_zone.height = size.y; - } - // Check if there is enough data - if (pixels.len < real_zone.width * real_zone.height) - return sf.Error.notEnoughData; - - sf.c.sfTexture_updateFromPixels(self._ptr, @ptrCast([*]const u8, pixels.ptr), real_zone.width, real_zone.height, real_zone.left, real_zone.top); - } - /// Updates the pixels of the image from an other texture - pub fn updateFromTexture(self: *Texture, other: Texture, copy_pos: ?sf.Vector2u) void { - if (self == ._const_ptr) - @panic("Can't set pixels on a const texture"); - - var pos = if (copy_pos) |a| a else sf.Vector2u{ .x = 0, .y = 0 }; - var max = other.getSize().add(pos); - var size = self.getSize(); - - assert(max.x <= size.x and max.y <= size.y); - - sf.c.sfTexture_updateFromTexture(self._ptr, other._get(), pos.x, pos.y); - } - /// Updates the pixels of the image from an image - pub fn updateFromImage(self: *Texture, image: sf.Image, copy_pos: ?sf.Vector2u) void { - if (self.* == ._const_ptr) - @panic("Can't set pixels on a const texture"); - - var pos = if (copy_pos) |a| a else sf.Vector2u{ .x = 0, .y = 0 }; - var max = image.getSize().add(pos); - var size = self.getSize(); - - assert(max.x <= size.x and max.y <= size.y); - - sf.c.sfTexture_updateFromImage(self._ptr, image._ptr, pos.x, pos.y); - } - - /// Tells whether or not this texture is to be smoothed - pub fn isSmooth(self: Texture) bool { - return sf.c.sfTexture_isSmooth(self._ptr) != 0; - } - /// Enables or disables texture smoothing - pub fn setSmooth(self: *Texture, smooth: bool) void { - if (self.* == ._const_ptr) - @panic("Can't set properties on a const texture"); - - sf.c.sfTexture_setSmooth(self._ptr, @boolToInt(smooth)); - } - - /// Tells whether or not this texture should repeat when rendering outside its bounds - pub fn isRepeated(self: Texture) bool { - return sf.c.sfTexture_isRepeated(self._ptr) != 0; - } - /// Enables or disables texture repeating - pub fn setRepeated(self: *Texture, repeated: bool) void { - if (self.* == ._const_ptr) - @panic("Can't set properties on a const texture"); - - sf.c.sfTexture_setRepeated(self._ptr, @boolToInt(repeated)); - } - - /// Tells whether or not this texture has colors in the SRGB format - /// SRGB functions arent implemented yet - pub fn isSrgb(self: Texture) bool { - return sf.c.sfTexture_isSrgb(self._ptr) != 0; - } - /// Enables or disables SRGB - pub fn setSrgb(self: *Texture, srgb: bool) void { - if (self.* == ._const_ptr) - @panic("Can't set properties on a const texture"); - - sf.c.sfTexture_setSrgb(self._ptr, @boolToInt(srgb)); - } - - /// Swaps this texture's contents with an other texture - pub fn swap(self: *Texture, other: *Texture) void { - if (self.* == ._const_ptr or other.* == ._const_ptr) - @panic("Texture swapping must be done between two non const textures"); - - sf.c.sfTexture_swap(self._ptr, other._ptr); - } - - // Others - - /// Generates a mipmap for the current texture data, returns true if the operation succeeded - pub fn generateMipmap(self: *Texture) bool { - if (self == ._const_ptr) - @panic("Can't act on a const texture"); - - return sf.c.sfTexture_generateMipmap(self._ptr) != 0; - } - - /// Pointer to the csfml texture - _ptr: *sf.c.sfTexture, - /// Const pointer to the csfml texture - _const_ptr: *const sf.c.sfTexture -}; - -test "texture: sane getters and setters" { - const tst = std.testing; - const allocator = std.heap.page_allocator; - - var tex = try Texture.create(.{ .x = 12, .y = 10 }); - defer tex.destroy(); - - var size = tex.getSize(); - - tex.setSrgb(false); - tex.setSmooth(true); - tex.setRepeated(true); - - try tst.expectEqual(@as(u32, 12), size.x); - try tst.expectEqual(@as(u32, 10), size.y); - try tst.expectEqual(@as(usize, 120), tex.getPixelCount()); - - var pixel_data = try allocator.alloc(sf.Color, 120); - defer allocator.free(pixel_data); - - for (pixel_data) |*c, i| { - c.* = sf.graphics.Color.fromHSVA(@intToFloat(f32, i) / 144 * 360, 100, 100, 1); - } - - pixel_data[0] = sf.Color.Green; - - try tex.updateFromPixels(pixel_data, null); - - try tst.expect(!tex.isSrgb()); - try tst.expect(tex.isSmooth()); - try tst.expect(tex.isRepeated()); - - var img = tex.copyToImage(); - defer img.destroy(); - - try tst.expectEqual(sf.Color.Green, img.getPixel(.{ .x = 0, .y = 0 })); - - tex.updateFromImage(img, null); - - var t = tex; - t.makeConst(); - - var copy = try t.copy(); - - try tst.expectEqual(@as(usize, 120), copy.getPixelCount()); - - var tex2 = try Texture.create(.{ .x = 100, .y = 100 }); - defer tex2.destroy(); - - copy.swap(&tex2); - - try tst.expectEqual(@as(usize, 100 * 100), copy.getPixelCount()); - try tst.expectEqual(@as(usize, 120), tex2.getPixelCount()); -} diff --git a/src/sfml/graphics/vertex.zig b/src/sfml/graphics/vertex.zig deleted file mode 100644 index 97b25f5..0000000 --- a/src/sfml/graphics/vertex.zig +++ /dev/null @@ -1,9 +0,0 @@ -//! Define a point with color and texture coordinates. - -const sf = @import("../sfml.zig"); - -pub const Vertex = packed struct { - position: sf.system.Vector2f, - color: sf.graphics.Color, - tex_coords: sf.system.Vector2f, -}; diff --git a/src/sfml/sfml.zig b/src/sfml/sfml.zig deleted file mode 100644 index 2cf51f2..0000000 --- a/src/sfml/sfml.zig +++ /dev/null @@ -1,77 +0,0 @@ -//! Import this to get all the sfml wrapper classes - -pub const c = @import("sfml_import.zig").c; - -pub const Error = @import("sfml_errors.zig").Error; - -pub const system = struct { - const vector = @import("system/vector.zig"); - pub const Vector2 = vector.Vector2; - pub const Vector3 = vector.Vector3; - pub const Vector4 = vector.Vector4; - pub const Vector2i = Vector2(c_int); - pub const Vector2u = Vector2(c_uint); - pub const Vector2f = Vector2(f32); - pub const Vector3f = Vector3(f32); - - pub const Time = @import("system/Time.zig"); - pub const Clock = @import("system/Clock.zig"); -}; - -pub const window = struct { - pub const Event = @import("window/event.zig").Event; - pub const Style = @import("window/Style.zig"); - pub const WindowHandle = c.sfWindowHandle; - pub const ContextSettings = @import("window/context_settings.zig").ContextSettings; - pub const keyboard = @import("window/keyboard.zig"); - pub const mouse = @import("window/mouse.zig"); -}; - -pub const graphics = struct { - pub const Color = @import("graphics/color.zig").Color; - - pub const RenderWindow = @import("graphics/RenderWindow.zig"); - pub const RenderTexture = @import("graphics/RenderTexture.zig"); - - pub const View = @import("graphics/View.zig"); - - pub const Image = @import("graphics/Image.zig"); - pub const Texture = @import("graphics/texture.zig").Texture; - - pub const Sprite = @import("graphics/Sprite.zig"); - pub const CircleShape = @import("graphics/CircleShape.zig"); - pub const RectangleShape = @import("graphics/RectangleShape.zig"); - - pub const Vertex = @import("graphics/vertex.zig").Vertex; - pub const VertexArray = @import("graphics/VertexArray.zig"); - pub const PrimitiveType = @import("graphics/primitive_type.zig").PrimitiveType; - - pub const Rect = @import("graphics/rect.zig").Rect; - pub const IntRect = Rect(c_int); - pub const FloatRect = Rect(f32); - - pub const Font = @import("graphics/Font.zig"); - pub const Text = @import("graphics/Text.zig"); - - pub const glsl = @import("graphics/glsl.zig"); - pub const Shader = @import("graphics/Shader.zig"); - pub const BlendMode = @import("graphics/BlendMode.zig"); - pub const RenderStates = @import("graphics/RenderStates.zig"); -}; - -pub const audio = struct { - pub const Music = @import("audio/Music.zig"); - pub const SoundBuffer = @import("audio/SoundBuffer.zig"); - pub const Sound = @import("audio/Sound.zig"); -}; - -pub const network = @compileError("network module: to be implemented one day"); - -pub const VertexBuffer = @compileError("VertexArray not available yet"); -pub const Transform = @compileError("Transform not available yet"); - -pub const touch = @compileError("touch not available yet"); -pub const joystick = @compileError("Joystick not available yet"); -pub const sensor = @compileError("Sensor not available yet"); -pub const clipboard = @compileError("Clipboard not available yet"); -pub const Cursor = @compileError("Cursor not available yet"); diff --git a/src/sfml/sfml_errors.zig b/src/sfml/sfml_errors.zig deleted file mode 100644 index d09da43..0000000 --- a/src/sfml/sfml_errors.zig +++ /dev/null @@ -1,3 +0,0 @@ -//! Errors for the wrapper - -pub const Error = error{ nullptrUnknownReason, windowCreationFailed, resourceLoadingError, notEnoughData, areaDoesNotFit, outOfBounds, savingInFileFailed }; diff --git a/src/sfml/sfml_import.zig b/src/sfml/sfml_import.zig deleted file mode 100644 index be21671..0000000 --- a/src/sfml/sfml_import.zig +++ /dev/null @@ -1,8 +0,0 @@ -//! Imports the csfml c headers - -pub const c = @cImport({ - @cInclude("SFML/Graphics.h"); - @cInclude("SFML/Window.h"); - @cInclude("SFML/System.h"); - @cInclude("SFML/Audio.h"); -}); diff --git a/src/sfml/sfml_tests.zig b/src/sfml/sfml_tests.zig deleted file mode 100644 index 5977a07..0000000 --- a/src/sfml/sfml_tests.zig +++ /dev/null @@ -1,11 +0,0 @@ -//! Test suite. Most tests are fairly basic, as they're not testing the SFML itself - -const std = @import("std"); - -test "all sfml tests" { - const sf = @import("sfml.zig"); - std.testing.refAllDecls(sf.system); - std.testing.refAllDecls(sf.window); - std.testing.refAllDecls(sf.graphics); - std.testing.refAllDecls(sf.audio); -} diff --git a/src/sfml/system/Clock.zig b/src/sfml/system/Clock.zig deleted file mode 100644 index 74b73ab..0000000 --- a/src/sfml/system/Clock.zig +++ /dev/null @@ -1,59 +0,0 @@ -//! Utility class that measures the elapsed time. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; - pub usingnamespace sf.graphics; -}; - -const Clock = @This(); - -// Constructor/destructor - -/// Inits a clock. The clock will have its time set at 0 at this point, and automatically starts -/// Std.time timer also is a good alternative -pub fn create() !Clock { - var clock = sf.c.sfClock_create(); - if (clock == null) - return sf.Error.nullptrUnknownReason; - - return Clock{ ._ptr = clock.? }; -} - -/// Destroys this clock -pub fn destroy(self: *Clock) void { - sf.c.sfClock_destroy(self._ptr); -} - -// Clock control -/// Gets the elapsed seconds -pub fn getElapsedTime(self: Clock) sf.Time { - var time = sf.c.sfClock_getElapsedTime(self._ptr).microseconds; - return sf.Time{ .us = time }; -} - -/// Gets the elapsed seconds and restarts the timer -pub fn restart(self: *Clock) sf.Time { - var time = sf.c.sfClock_restart(self._ptr).microseconds; - return sf.Time{ .us = time }; -} - -/// Pointer to the csfml structure -_ptr: *sf.c.sfClock, - -test "clock: sleep test" { - const tst = @import("std").testing; - - // This tests just sleeps and check what the timer measured (not very accurate but eh) - var clk = try Clock.create(); - defer clk.destroy(); - - sf.Time.milliseconds(500).sleep(); - - try tst.expectApproxEqAbs(@as(f32, 0.5), clk.getElapsedTime().asSeconds(), 0.1); - - sf.Time.sleep(sf.Time.seconds(0.2)); - - try tst.expectApproxEqAbs(@as(f32, 0.7), clk.restart().asSeconds(), 0.1); - try tst.expectApproxEqAbs(@as(f32, 0), clk.getElapsedTime().asSeconds(), 0.01); -} diff --git a/src/sfml/system/Time.zig b/src/sfml/system/Time.zig deleted file mode 100644 index ae5152a..0000000 --- a/src/sfml/system/Time.zig +++ /dev/null @@ -1,114 +0,0 @@ -//! Represents a time value. - -const sf = @import("../sfml.zig"); - -const Time = @This(); - -// Constructors - -/// Converts a time from a csfml object -/// For inner workings -pub fn _fromCSFML(time: sf.c.sfTime) Time { - return Time{ .us = time.microseconds }; -} - -/// Converts a time to a csfml object -/// For inner workings -pub fn _toCSFML(self: Time) sf.c.sfTime { - return sf.c.sfTime{ .microseconds = self.us }; -} - -/// Creates a time object from a seconds count -pub fn seconds(s: f32) Time { - return Time{ .us = @floatToInt(i64, s * 1_000) * 1_000 }; -} - -/// Creates a time object from milliseconds -pub fn milliseconds(ms: i32) Time { - return Time{ .us = @intCast(i64, ms) * 1_000 }; -} - -/// Creates a time object from microseconds -pub fn microseconds(us: i64) Time { - return Time{ .us = us }; -} - -// Getters - -/// Gets this time measurement as microseconds -pub fn asMicroseconds(self: Time) i64 { - return self.us; -} - -/// Gets this time measurement as milliseconds -pub fn asMilliseconds(self: Time) i32 { - return @truncate(i32, @divFloor(self.us, 1_000)); -} - -/// Gets this time measurement as seconds (as a float) -pub fn asSeconds(self: Time) f32 { - return @intToFloat(f32, self.us) / 1_000_000; -} - -// Misc - -/// Sleeps the amount of time specified -pub fn sleep(time: Time) void { - sf.c.sfSleep(time._toCSFML()); -} - -/// A time of zero -pub const Zero = microseconds(0); - -us: i64, - -pub const TimeSpan = struct { - // Constructors - - /// Construcs a time span - pub fn init(begin: Time, length: Time) TimeSpan { - return TimeSpan{ - .offset = begin, - .length = length, - }; - } - - /// Converts a timespan from a csfml object - /// For inner workings - pub fn _fromCSFML(span: sf.c.sfTimeSpan) TimeSpan { - return TimeSpan{ - .offset = Time._fromCSFML(span.offset), - .length = Time._fromCSFML(span.length), - }; - } - - /// Converts a timespan to a csfml object - /// For inner workings - pub fn _toCSFML(self: TimeSpan) sf.c.sfTimeSpan { - return sf.c.sfTimeSpan{ - .offset = self.offset._toCSFML(), - .length = self.length._toCSFML(), - }; - } - - /// The beginning of this span - offset: Time, - /// The length of this time span - length: Time, -}; - -test "time: conversion" { - const tst = @import("std").testing; - - var t = Time.microseconds(5_120_000); - - try tst.expectEqual(@as(i32, 5_120), t.asMilliseconds()); - try tst.expectApproxEqAbs(@as(f32, 5.12), t.asSeconds(), 0.0001); - - t = Time.seconds(12); - - try tst.expectApproxEqAbs(@as(f32, 12), t.asSeconds(), 0.0001); - - t = Time.microseconds(800); - try tst.expectApproxEqAbs(@as(f32, 0.0008), t.asSeconds(), 0.0001); -} diff --git a/src/sfml/system/vector.zig b/src/sfml/system/vector.zig deleted file mode 100644 index 3190d59..0000000 --- a/src/sfml/system/vector.zig +++ /dev/null @@ -1,141 +0,0 @@ -//! Utility struct for manipulating 2-dimensional vectors. - -const sf = @import("../sfml_import.zig"); - -/// Template for a 2 dimensional vector -pub fn Vector2(comptime T: type) type { - return packed struct { - const Self = @This(); - - /// The CSFML vector type equivalent - const CsfmlEquivalent = switch (T) { - c_uint => sf.c.sfVector2u, - c_int => sf.c.sfVector2i, - f32 => sf.c.sfVector2f, - else => void, - }; - - /// Makes a CSFML vector with this vector (only if the corresponding type exists) - /// This is mainly for the inner workings of this wrapper - pub fn _toCSFML(self: Self) CsfmlEquivalent { - if (CsfmlEquivalent == void) @compileError("This vector type doesn't have a CSFML equivalent."); - return @bitCast(CsfmlEquivalent, self); - } - - /// Creates a vector from a CSFML one (only if the corresponding type exists) - /// This is mainly for the inner workings of this wrapper - pub fn _fromCSFML(vec: CsfmlEquivalent) Self { - if (CsfmlEquivalent == void) @compileError("This vector type doesn't have a CSFML equivalent."); - return @bitCast(Self, vec); - } - - /// Adds two vectors - pub fn add(self: Self, other: Self) Self { - return Self{ .x = self.x + other.x, .y = self.y + other.y }; - } - - /// Substracts two vectors - pub fn substract(self: Self, other: Self) Self { - return Self{ .x = self.x - other.x, .y = self.y - other.y }; - } - - /// Scales a vector - pub fn scale(self: Self, scalar: T) Self { - return Self{ .x = self.x * scalar, .y = self.y * scalar }; - } - - /// x component of the vector - x: T, - /// y component of the vector - y: T - }; -} - -/// Template for a 3 dimensional vector -pub fn Vector3(comptime T: type) type { - return packed struct { - const Self = @This(); - - /// Makes a CSFML vector with this vector (only if the corresponding type exists) - /// This is mainly for the inner workings of this wrapper - pub fn _toCSFML(self: Self) sf.c.sfVector3f { - if (T != f32) @compileError("This vector type doesn't have a CSFML equivalent."); - return @bitCast(sf.c.sfVector3f, self); - } - - /// Creates a vector from a CSFML one (only if the corresponding type exists) - /// This is mainly for the inner workings of this wrapper - pub fn _fromCSFML(vec: sf.c.sfVector3f) Self { - if (T != f32) @compileError("This vector type doesn't have a CSFML equivalent."); - return @bitCast(Self, vec); - } - - /// Adds two vectors - pub fn add(self: Self, other: Self) Self { - return Self{ .x = self.x + other.x, .y = self.y + other.y, .z = self.z + other.z }; - } - - /// Substracts two vectors - pub fn substract(self: Self, other: Self) Self { - return Self{ .x = self.x - other.x, .y = self.y - other.y, .z = self.z - other.z }; - } - - /// Scales a vector - pub fn scale(self: Self, scalar: T) Self { - return Self{ .x = self.x * scalar, .y = self.y * scalar, .z = self.z * scalar }; - } - - /// x component of the vector - x: T, - /// y component of the vector - y: T, - /// z component of the vector - z: T - }; -} - -/// Template for a 4 dimensional vector -/// SFML doesn't really have this but as shaders use such vectors it can be here anyways -pub fn Vector4(comptime T: type) type { - return packed struct { - const Self = @This(); - /// x component of the vector - x: T, - /// y component of the vector - y: T, - /// z component of the vector - z: T, - /// w component of the vector - w: T - }; -} - -test "vector: sane from/to CSFML vectors" { - const tst = @import("std").testing; - - inline for ([_]type{ c_int, c_uint, f32 }) |T| { - const VecT = Vector2(T); - const vec = VecT{ .x = 1, .y = 3 }; - const cvec = vec._toCSFML(); - - try tst.expectEqual(vec.x, cvec.x); - try tst.expectEqual(vec.y, cvec.y); - - const vec2 = VecT._fromCSFML(cvec); - - try tst.expectEqual(vec, vec2); - } - - { - const vec = Vector3(f32){ .x = 1, .y = 3.5, .z = -12 }; - const cvec = vec._toCSFML(); - - try tst.expectEqual(vec.x, cvec.x); - try tst.expectEqual(vec.y, cvec.y); - try tst.expectEqual(vec.z, cvec.z); - - const vec2 = Vector3(f32)._fromCSFML(cvec); - - try tst.expectEqual(vec, vec2); - } -} diff --git a/src/sfml/window/Style.zig b/src/sfml/window/Style.zig deleted file mode 100644 index e9b401d..0000000 --- a/src/sfml/window/Style.zig +++ /dev/null @@ -1,5 +0,0 @@ -pub const none: u32 = 0; -pub const titlebar: u32 = 1; -pub const resize: u32 = 2; -pub const close: u32 = 4; -pub const defaultStyle = titlebar | resize | close; diff --git a/src/sfml/window/context_settings.zig b/src/sfml/window/context_settings.zig deleted file mode 100644 index 19b8f03..0000000 --- a/src/sfml/window/context_settings.zig +++ /dev/null @@ -1,28 +0,0 @@ -const sf = @import("../sfml.zig"); - -pub const ContextSettings = packed struct { - const PaddingType = @import("std").meta.Int(.unsigned, @bitSizeOf(c_int) - @bitSizeOf(bool)); - - depth_bits: c_uint = 0, - stencil_bits: c_uint = 0, - antialiasing_level: c_uint = 0, - major_version: c_uint = 1, - minor_version: c_uint = 1, - attribute_flags: u32 = 0, - srgb_capable: bool = false, - _padding: PaddingType = 0, - - pub const Attribute = struct { - pub const default: u32 = 0; - pub const core: u32 = 1; - pub const debug: u32 = 4; - }; - - pub fn _toCSFML(self: ContextSettings) sf.c.sfContextSettings { - return @bitCast(sf.c.sfContextSettings, self); - } - - pub fn _fromCSFML(context_settings: sf.c.sfContextSettings) ContextSettings { - return @bitCast(ContextSettings, context_settings); - } -}; \ No newline at end of file diff --git a/src/sfml/window/event.zig b/src/sfml/window/event.zig deleted file mode 100644 index a73c192..0000000 --- a/src/sfml/window/event.zig +++ /dev/null @@ -1,162 +0,0 @@ -//! Defines a system event and its parameters. - -const sf = struct { - pub usingnamespace @import("../sfml.zig"); - pub usingnamespace sf.system; -}; - -pub const Event = union(Event.Type) { - const Self = @This(); - - pub const Type = enum(c_int) { - closed, - resized, - lostFocus, - gainedFocus, - textEntered, - keyPressed, - keyReleased, - mouseWheelScrolled, - mouseButtonPressed, - mouseButtonReleased, - mouseMoved, - mouseEntered, - mouseLeft, - joystickButtonPressed, - joystickButtonReleased, - joystickMoved, - joystickConnected, - joystickDisconnected, - touchBegan, - touchMoved, - touchEnded, - sensorChanged, - }; - - // Big oof - /// Creates this event from a csfml one - pub fn _fromCSFML(event: sf.c.sfEvent) Self { - return switch (event.type) { - sf.c.sfEvtClosed => .{ .closed = {} }, - sf.c.sfEvtResized => .{ .resized = .{ .size = .{ .x = event.size.width, .y = event.size.height } } }, - sf.c.sfEvtLostFocus => .{ .lostFocus = {} }, - sf.c.sfEvtGainedFocus => .{ .gainedFocus = {} }, - sf.c.sfEvtTextEntered => .{ .textEntered = .{ .unicode = event.text.unicode } }, - sf.c.sfEvtKeyPressed => .{ .keyPressed = .{ .code = @intToEnum(sf.window.keyboard.KeyCode, event.key.code), .alt = (event.key.alt != 0), .control = (event.key.control != 0), .shift = (event.key.shift != 0), .system = (event.key.system != 0) } }, - sf.c.sfEvtKeyReleased => .{ .keyReleased = .{ .code = @intToEnum(sf.window.keyboard.KeyCode, event.key.code), .alt = (event.key.alt != 0), .control = (event.key.control != 0), .shift = (event.key.shift != 0), .system = (event.key.system != 0) } }, - sf.c.sfEvtMouseWheelScrolled => .{ .mouseWheelScrolled = .{ .wheel = @intToEnum(sf.window.mouse.Wheel, event.mouseWheelScroll.wheel), .delta = event.mouseWheelScroll.delta, .pos = .{ .x = event.mouseWheelScroll.x, .y = event.mouseWheelScroll.y } } }, - sf.c.sfEvtMouseButtonPressed => .{ .mouseButtonPressed = .{ .button = @intToEnum(sf.window.mouse.Button, event.mouseButton.button), .pos = .{ .x = event.mouseButton.x, .y = event.mouseButton.y } } }, - sf.c.sfEvtMouseButtonReleased => .{ .mouseButtonReleased = .{ .button = @intToEnum(sf.window.mouse.Button, event.mouseButton.button), .pos = .{ .x = event.mouseButton.x, .y = event.mouseButton.y } } }, - sf.c.sfEvtMouseMoved => .{ .mouseMoved = .{ .pos = .{ .x = event.mouseMove.x, .y = event.mouseMove.y } } }, - sf.c.sfEvtMouseEntered => .{ .mouseEntered = {} }, - sf.c.sfEvtMouseLeft => .{ .mouseLeft = {} }, - sf.c.sfEvtJoystickButtonPressed => .{ .joystickButtonPressed = .{ .joystickId = event.joystickButton.joystickId, .button = event.joystickButton.button } }, - sf.c.sfEvtJoystickButtonReleased => .{ .joystickButtonReleased = .{ .joystickId = event.joystickButton.joystickId, .button = event.joystickButton.button } }, - sf.c.sfEvtJoystickMoved => .{ .joystickMoved = .{ .joystickId = event.joystickMove.joystickId, .axis = event.joystickMove.axis, .position = event.joystickMove.position } }, - sf.c.sfEvtJoystickConnected => .{ .joystickConnected = .{ .joystickId = event.joystickConnect.joystickId } }, - sf.c.sfEvtJoystickDisconnected => .{ .joystickDisconnected = .{ .joystickId = event.joystickConnect.joystickId } }, - sf.c.sfEvtTouchBegan => .{ .touchBegan = .{ .finger = event.touch.finger, .pos = .{ .x = event.touch.x, .y = event.touch.y } } }, - sf.c.sfEvtTouchMoved => .{ .touchMoved = .{ .finger = event.touch.finger, .pos = .{ .x = event.touch.x, .y = event.touch.y } } }, - sf.c.sfEvtTouchEnded => .{ .touchEnded = .{ .finger = event.touch.finger, .pos = .{ .x = event.touch.x, .y = event.touch.y } } }, - sf.c.sfEvtSensorChanged => .{ .sensorChanged = .{ .sensorType = event.sensor.sensorType, .vector = .{ .x = event.sensor.x, .y = event.sensor.y, .z = event.sensor.z } } }, - sf.c.sfEvtCount => @panic("sfEvtCount should't exist as an event!"), - else => @panic("Unknown event!"), - }; - } - - /// Gets how many types of event exist - pub fn getEventCount() c_uint { - return @enumToInt(sf.c.sfEventType.sfEvtCount); - } - - /// Size events parameters - pub const SizeEvent = struct { - size: sf.Vector2u, - }; - - /// Keyboard event parameters - pub const KeyEvent = struct { - code: sf.window.keyboard.KeyCode, - alt: bool, - control: bool, - shift: bool, - system: bool, - }; - - /// Text event parameters - pub const TextEvent = struct { - unicode: u32, - }; - - /// Mouse move event parameters - pub const MouseMoveEvent = struct { - pos: sf.Vector2i, - }; - - /// Mouse buttons events parameters - pub const MouseButtonEvent = struct { - button: sf.window.mouse.Button, - pos: sf.Vector2i, - }; - - /// Mouse wheel events parameters - pub const MouseWheelScrollEvent = struct { - wheel: sf.window.mouse.Wheel, - delta: f32, - pos: sf.Vector2i, - }; - - /// Joystick axis move event parameters - pub const JoystickMoveEvent = struct { - joystickId: c_uint, - axis: sf.c.sfJoystickAxis, - position: f32, - }; - - /// Joystick buttons events parameters - pub const JoystickButtonEvent = struct { - joystickId: c_uint, - button: c_uint, - }; - - /// Joystick connection/disconnection event parameters - pub const JoystickConnectEvent = struct { - joystickId: c_uint, - }; - - /// Touch events parameters - pub const TouchEvent = struct { - finger: c_uint, - pos: sf.Vector2i, - }; - - /// Sensor event parameters - pub const SensorEvent = struct { - sensorType: sf.c.sfSensorType, - vector: sf.Vector3f, - }; - - // An event is one of those - closed: void, - resized: SizeEvent, - lostFocus: void, - gainedFocus: void, - textEntered: TextEvent, - keyPressed: KeyEvent, - keyReleased: KeyEvent, - mouseWheelScrolled: MouseWheelScrollEvent, - mouseButtonPressed: MouseButtonEvent, - mouseButtonReleased: MouseButtonEvent, - mouseMoved: MouseMoveEvent, - mouseEntered: void, - mouseLeft: void, - joystickButtonPressed: JoystickButtonEvent, - joystickButtonReleased: JoystickButtonEvent, - joystickMoved: JoystickMoveEvent, - joystickConnected: JoystickConnectEvent, - joystickDisconnected: JoystickConnectEvent, - touchBegan: TouchEvent, - touchMoved: TouchEvent, - touchEnded: TouchEvent, - sensorChanged: SensorEvent, -}; diff --git a/src/sfml/window/keyboard.zig b/src/sfml/window/keyboard.zig deleted file mode 100644 index 8e4e970..0000000 --- a/src/sfml/window/keyboard.zig +++ /dev/null @@ -1,11 +0,0 @@ -//! Give access to the real-time state of the keyboard. - -const sf = @import("../sfml_import.zig"); - -/// Keycodes -pub const KeyCode = enum(c_int) { Unknown = -1, A = 0, B, C, D, E, F, G, H, I, J, K, L, M, N, O, P, Q, R, S, T, U, V, W, X, Y, Z, Num0, Num1, Num2, Num3, Num4, Num5, Num6, Num7, Num8, Num9, Escape, LControl, LShift, LAlt, LSystem, RControl, RShift, RAlt, RSystem, Menu, LBracket, RBracket, Semicolon, Comma, Period, Quote, Slash, Backslash, Tilde, Equal, Hyphen, Space, Enter, Backspace, Tab, PageUp, PageDown, End, Home, Insert, Delete, Add, Subtract, Multiply, Divide, Left, Right, Up, Down, Numpad0, Numpad1, Numpad2, Numpad3, Numpad4, Numpad5, Numpad6, Numpad7, Numpad8, Numpad9, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, F13, F14, F15, Pause, KeyCount }; - -/// Returns true if the specified key is pressed -pub fn isKeyPressed(key: KeyCode) bool { - return sf.c.sfKeyboard_isKeyPressed(@enumToInt(key)) == 1; -} diff --git a/src/sfml/window/mouse.zig b/src/sfml/window/mouse.zig deleted file mode 100644 index b60ff00..0000000 --- a/src/sfml/window/mouse.zig +++ /dev/null @@ -1,26 +0,0 @@ -//! Give access to the real-time state of the mouse. - -const sf = @import("../sfml.zig"); - -/// Mouse buttons -pub const Button = enum(c_uint) { Left, Right, Middle, XButton1, XButton2 }; -/// Mouse wheels -pub const Wheel = enum(c_uint) { Vertical, Horizontal }; - -/// Returns true if the specified mouse button is pressed -pub fn isButtonPressed(button: Button) bool { - return sf.c.sfMouse_isButtonPressed(@intToEnum(sf.c.sfMouseButton, @enumToInt(button))) == 1; -} - -/// Gets the position of the mouse cursor relative to the window passed or desktop -pub fn getPosition(window: ?sf.graphics.RenderWindow) sf.system.Vector2i { - if (window) |w| { - return sf.system.Vector2i._fromCSFML(sf.c.sfMouse_getPosition(@ptrCast(*sf.c.sfWindow, w._ptr))); - } else return sf.system.Vector2i._fromCSFML(sf.c.sfMouse_getPosition(null)); -} -/// Set the position of the mouse cursor relative to the window passed or desktop -pub fn setPosition(position: sf.system.Vector2i, window: ?sf.graphics.RenderWindow) void { - if (window) |w| { - sf.c.sfMouse_setPosition(position._toCSFML(), @ptrCast(*sf.c.sfWindow, w._ptr)); - } else sf.c.sfMouse_setPosition(position._toCSFML(), null); -} diff --git a/src/zig-sfml-wrapper b/src/zig-sfml-wrapper new file mode 160000 index 0000000..2fea6d9 --- /dev/null +++ b/src/zig-sfml-wrapper @@ -0,0 +1 @@ +Subproject commit 2fea6d90b925d9401d7f7e80b7de92c7e4cb4bb7 -- cgit v1.3.1