diff --git a/shaders/StylishShaders/FlashFrag.glsl b/shaders/StylishShaders/FlashFrag.glsl new file mode 100644 index 0000000..e9e4a03 --- /dev/null +++ b/shaders/StylishShaders/FlashFrag.glsl @@ -0,0 +1,26 @@ +#version 410 + +out vec4 FragColor; + +in vec4 color; +in vec2 fragCoord; +in vec2 texCoord; + +uniform sampler2D texture1; +uniform float time; + +void main(){ + + vec4 flash; + + flash = sin(flash + time * 15); + flash = mix(flash, color, 0.5f); + + vec4 tex = texture(texture1, texCoord); + if (tex.a == 0.0){ + FragColor = tex; + } else{ + FragColor = mix(tex, flash, 0.5f); + FragColor.a = 1.0f; + } +} diff --git a/shaders/StylishShaders/PerlinNoise.glsl b/shaders/StylishShaders/PerlinNoise.glsl deleted file mode 100644 index 7ff344f..0000000 --- a/shaders/StylishShaders/PerlinNoise.glsl +++ /dev/null @@ -1,31 +0,0 @@ -#version 410 - -// Source = https://www.shadertoy.com/view/MlsXDr - -out vec4 FragColor; - -in vec4 color; -in vec2 fragCoord; -in vec2 texCoord; - -uniform sampler2D texture1; -uniform float time; - -void main() -{ // Pas fini c'est moche - - vec4 perlinNoise; - vec2 fragCoordTemp = fragCoord; - fragCoordTemp = 8. * fragCoordTemp / fragCoordTemp.y-vec2(7,4); - - perlinNoise = sin(perlinNoise + time*15); - perlinNoise = mix(perlinNoise,color,0.5f); - - vec4 tex = texture(texture1, texCoord); - if (tex.a == 0.0){ - FragColor = tex; - } else{ - FragColor = mix(tex, perlinNoise, 0.5f); - FragColor.a = 1.0f; - } -} diff --git a/src/engine/Engine.java b/src/engine/Engine.java index 534319f..342552d 100644 --- a/src/engine/Engine.java +++ b/src/engine/Engine.java @@ -3,13 +3,10 @@ package engine; import engine.math.*; import engine.object.*; -import org.lwjgl.glfw.GLFW; import org.lwjgl.glfw.GLFWFramebufferSizeCallback; import org.lwjgl.glfw.GLFWVidMode; import org.lwjgl.opengl.GL; -import java.nio.ByteBuffer; -import java.nio.FloatBuffer; import java.util.ArrayList; import java.util.List; @@ -177,7 +174,7 @@ public class Engine { zangief.translate(new Vector3f(-5000.0f, 500.0f, 10.0f)); zangief.setColor(new Vector3f(1.0f, 1.0f, 1.0f)); zangief.useTime = true; - zangief.setShader("shaders/StylishShaders/BasicVert.glsl", "shaders/StylishShaders/PerlinNoise.glsl"); + zangief.setShader("shaders/StylishShaders/BasicVert.glsl", "shaders/StylishShaders/FlashFrag.glsl"); ObjectGl smiley2 = new ObjectGl(0.0f, 500.0f, 500.0f, 1f, path2, null); engine.add_objectGl(smiley2); diff --git a/src/engine/graphics/Shader.java b/src/engine/graphics/Shader.java index 19ae290..ea8a247 100644 --- a/src/engine/graphics/Shader.java +++ b/src/engine/graphics/Shader.java @@ -15,7 +15,7 @@ public class Shader { //Identifiant du programme resultat de la compilation des shaders private final int ID; - private Map locationCache = new HashMap(); + private final Map locationCache = new HashMap(); /* Crée le fragment et le vertex shader les lie dans un programme dont il renvoie l'identifiant. diff --git a/src/engine/sound/SoundBuffer.java b/src/engine/sound/SoundBuffer.java new file mode 100644 index 0000000..01cfa03 --- /dev/null +++ b/src/engine/sound/SoundBuffer.java @@ -0,0 +1,87 @@ +/** + * Vorbis : https://fr.wikipedia.org/wiki/Vorbis + */ + + +package engine.sound; + +import org.lwjgl.stb.STBVorbisInfo; +import org.lwjgl.system.MemoryStack; +import org.lwjgl.system.MemoryUtil; + +import java.nio.ByteBuffer; +import java.nio.IntBuffer; +import java.nio.ShortBuffer; + +import static engine.utils.BufferUtils.StringToByteBuffer; +import static org.lwjgl.openal.AL10.*; +import static org.lwjgl.stb.STBVorbis.*; +import static org.lwjgl.system.MemoryUtil.NULL; + +/** + * Prends un fichier .ogg, crée un buffer associé utilisable par openAl + * Vorbis : https://fr.wikipedia.org/wiki/Vorbis + */ +public class SoundBuffer { + + private final int bufferId; + + private ShortBuffer pcm = null; + + private ByteBuffer vorbis = null; + + /** + * + * @param path path to the file (.ogg) + * @throws Exception if the path is incorrect... + */ + public SoundBuffer(String path) throws Exception { + this.bufferId = alGenBuffers(); + try (STBVorbisInfo info = STBVorbisInfo.malloc()) { + ShortBuffer pcm = readVorbis(path, info); + + // Equivalent de glBufferData pour openAl + alBufferData(this.bufferId, info.channels() == 1 ? AL_FORMAT_MONO16 : AL_FORMAT_STEREO16, pcm, info.sample_rate()); + } + } + + public int getBufferId() { + return this.bufferId; + } + + public void cleanup() { + alDeleteBuffers(this.bufferId); + } + + /** + * Source : https://github.com/lwjglgamedev/lwjglbook/blob/master/chapter28/src/main/java/org/lwjglb/engine/sound/SoundBuffer.java + * lis un fichier .ogg et le convertis en .pcm seul format lisible par openAl + * @param resource le fichier .ogg + * @param info STBVorbisInfo + * @return pcm + * @throws Exception MemoryStack.stackPush() + */ + private ShortBuffer readVorbis(String resource, STBVorbisInfo info) throws Exception { + try (MemoryStack stack = MemoryStack.stackPush()) { + vorbis = StringToByteBuffer(resource); + IntBuffer error = stack.mallocInt(1); + long decoder = stb_vorbis_open_memory(vorbis, error, null); + if (decoder == NULL) { + throw new RuntimeException("Failed to open Ogg Vorbis file. Error: " + error.get(0)); + } + + stb_vorbis_get_info(decoder, info); + + int channels = info.channels(); + + int lengthSamples = stb_vorbis_stream_length_in_samples(decoder); + + pcm = MemoryUtil.memAllocShort(lengthSamples); + + pcm.limit(stb_vorbis_get_samples_short_interleaved(decoder, channels, pcm) * channels); + stb_vorbis_close(decoder); + + return pcm; + } + } +} \ No newline at end of file diff --git a/src/engine/sound/SoundListener.java b/src/engine/sound/SoundListener.java new file mode 100644 index 0000000..0776076 --- /dev/null +++ b/src/engine/sound/SoundListener.java @@ -0,0 +1,37 @@ +package engine.sound; + +import engine.math.Vector3f; + +import static org.lwjgl.openal.AL10.*; + +public class SoundListener { + + public SoundListener() { + this(new Vector3f(0, 0, 0)); + } + + public SoundListener(Vector3f position) { + alListener3f(AL_POSITION, position.x, position.y, position.z); + alListener3f(AL_VELOCITY, 0, 0, 0); + + } + + public void setSpeed(Vector3f speed) { + alListener3f(AL_VELOCITY, speed.x, speed.y, speed.z); + } + + public void setPosition(Vector3f position) { + alListener3f(AL_POSITION, position.x, position.y, position.z); + } + + public void setOrientation(Vector3f at, Vector3f up) { + float[] data = new float[6]; + data[0] = at.x; + data[1] = at.y; + data[2] = at.z; + data[3] = up.x; + data[4] = up.y; + data[5] = up.z; + alListenerfv(AL_ORIENTATION, data); + } +} diff --git a/src/engine/sound/SoundManager.java b/src/engine/sound/SoundManager.java new file mode 100644 index 0000000..9116961 --- /dev/null +++ b/src/engine/sound/SoundManager.java @@ -0,0 +1,52 @@ +package engine.sound; + +import engine.math.Matrix4f; +import org.lwjgl.openal.*; +import org.lwjgl.openal.AL; +import org.lwjgl.openal.ALC; +import org.lwjgl.openal.ALCCapabilities; +import java.nio.ByteBuffer; +import java.nio.IntBuffer; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import static org.lwjgl.openal.ALC10.*; +import static org.lwjgl.system.MemoryUtil.NULL; + + +public class SoundManager { + + private long device; + + private long context; + + private SoundListener listener; + + private final List soundBufferList; + + private final Map soundSourceMap; + + private final Matrix4f cameraMatrix; + + public SoundManager() { + soundBufferList = new ArrayList<>(); + soundSourceMap = new HashMap<>(); + cameraMatrix = new Matrix4f(); + } + + public void init() throws Exception { + this.device = alcOpenDevice((ByteBuffer) null); + if (device == NULL) { + throw new IllegalStateException("Failed to open the default OpenAL device."); + } + ALCCapabilities deviceCaps = ALC.createCapabilities(device); + this.context = alcCreateContext(device, (IntBuffer) null); + if (context == NULL) { + throw new IllegalStateException("Failed to create OpenAL context."); + } + alcMakeContextCurrent(context); + AL.createCapabilities(deviceCaps); + } +} diff --git a/src/engine/sound/SoundSource.java b/src/engine/sound/SoundSource.java new file mode 100644 index 0000000..e7b2389 --- /dev/null +++ b/src/engine/sound/SoundSource.java @@ -0,0 +1,62 @@ +package engine.sound; + +import engine.math.Vector3f; + +import static org.lwjgl.openal.AL10.*; + +public class SoundSource { + + private final int sourceId; + + public SoundSource(boolean loop, boolean relative) { + this.sourceId = alGenSources(); + if (loop) { + alSourcei(sourceId, AL_LOOPING, AL_TRUE); + } + if (relative) { + alSourcei(sourceId, AL_SOURCE_RELATIVE, AL_TRUE); + } + } + + public void setBuffer(int bufferId) { + stop(); + alSourcei(sourceId, AL_BUFFER, bufferId); + } + + public void setPosition(Vector3f position) { + alSource3f(sourceId, AL_POSITION, position.x, position.y, position.z); + } + + public void setSpeed(Vector3f speed) { + alSource3f(sourceId, AL_VELOCITY, speed.x, speed.y, speed.z); + } + + public void setGain(float gain) { + alSourcef(sourceId, AL_GAIN, gain); + } + + public void setProperty(int param, float value) { + alSourcef(sourceId, param, value); + } + + public void play() { + alSourcePlay(sourceId); + } + + public boolean isPlaying() { + return alGetSourcei(sourceId, AL_SOURCE_STATE) == AL_PLAYING; + } + + public void pause() { + alSourcePause(sourceId); + } + + public void stop() { + alSourceStop(sourceId); + } + + public void cleanup() { + stop(); + alDeleteSources(sourceId); + } +} diff --git a/src/engine/utils/BufferUtils.java b/src/engine/utils/BufferUtils.java index d420b8e..50a2ddb 100644 --- a/src/engine/utils/BufferUtils.java +++ b/src/engine/utils/BufferUtils.java @@ -29,4 +29,8 @@ public class BufferUtils { return result; } + public static ByteBuffer StringToByteBuffer(String msg){ + return ByteBuffer.wrap(msg.getBytes()); + } + }