Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion src/libprojectM/Renderer/Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ libRenderer_la_SOURCES = \
Waveform.cpp \
Filters.cpp \
PerlinNoise.cpp \
PerlinNoiseWithAlpha.cpp \
PipelineContext.cpp \
Renderable.cpp \
BeatDetect.cpp \
Expand All @@ -28,7 +29,7 @@ libRenderer_la_SOURCES = \
Filters.hpp RenderItemMatcher.hpp Transformation.hpp\
MilkdropWaveform.hpp RenderItemMergeFunction.hpp Texture.hpp\
PerPixelMesh.hpp Renderable.hpp VideoEcho.hpp\
PerlinNoise.hpp Renderer.hpp Waveform.hpp\
PerlinNoise.hpp PerlinNoiseWithAlpha.hpp Renderer.hpp Waveform.hpp\
Pipeline.hpp Shader.hpp\
SOIL2/SOIL2.h SOIL2/stbi_DDS.h\
SOIL2/etc1_utils.h SOIL2/stbi_DDS_c.h\
Expand Down
81 changes: 81 additions & 0 deletions src/libprojectM/Renderer/PerlinNoiseWithAlpha.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
/*
* PerlinNoiseWithAlpha.cpp
*
* Created and based on PerlinNoise.hpp
* Created on: Sep 14, 2019
* Author: hibengler
*/

#include "PerlinNoiseWithAlpha.hpp"
#include <iostream>
#include <stdlib.h>

/* The reason for this cousin class is that in Open GLES 2.0 environments,
the glTexImage2d cannot convert from GL_RGB into GL_RGBA
so the TextureManager has to use something that is pre-RGBA
*/
PerlinNoiseWithAlpha::PerlinNoiseWithAlpha()
{
for (int x = 0; x < 256;x++) {
for (int y = 0; y < 256;y++) {
noise_lq[x][y][0] = noise(x , y);
noise_lq[x][y][1] = noise_lq[x][y][0];
noise_lq[x][y][2] = noise_lq[x][y][0];
noise_lq[x][y][3] = 1.f;
}
}

for (int x = 0; x < 32;x++) {
for (int y = 0; y < 32;y++) {
noise_lq_lite[x][y][0] = noise(4*x,16*y);
noise_lq_lite[x][y][1] = noise_lq_lite[x][y][0];
noise_lq_lite[x][y][2] = noise_lq_lite[x][y][0];
noise_lq_lite[x][y][3] = 1.f;
}
}

for (int x = 0; x < 256;x++) {
for (int y = 0; y < 256;y++) {
noise_mq[x][y][0] = InterpolatedNoise((float)x/(float)2.0,(float)y/(float)2.0);
noise_mq[x][y][1] = noise_mq[x][y][0];
noise_mq[x][y][2] = noise_mq[x][y][0];
noise_mq[x][y][3] = 1.f;
}
}

for (int x = 0; x < 256;x++) {
for (int y = 0; y < 256;y++) {
noise_hq[x][y][0] = InterpolatedNoise((float)x/(float)3.0,(float)y/(float)3.0);
noise_hq[x][y][1] = noise_hq[x][y][0];
noise_hq[x][y][2] = noise_hq[x][y][0];
noise_hq[x][y][3] = 1.f;
}
}

for (int x = 0; x < 32;x++) {
for (int y = 0; y < 32;y++) {
for (int z = 0; z < 32;z++) {
noise_lq_vol[x][y][z][0] = noise(x,y,z);
noise_lq_vol[x][y][z][1] = noise_lq_vol[x][y][z][0];
noise_lq_vol[x][y][z][2] = noise_lq_vol[x][y][z][0];
noise_lq_vol[x][y][z][3] = 1.f;
}
}
}

for (int x = 0; x < 32;x++) {
for (int y = 0; y < 32;y++) {
for (int z = 0; z < 32;z++) {
noise_hq_vol[x][y][z][0] = noise(x,y,z);
noise_hq_vol[x][y][z][1] = noise_hq_vol[x][y][z][0];
noise_hq_vol[x][y][z][2] = noise_hq_vol[x][y][z][0];
noise_hq_vol[x][y][z][3] = 1.f;
}
}
}
}

PerlinNoiseWithAlpha::~PerlinNoiseWithAlpha()
{
// TODO Auto-generated destructor stub
}
176 changes: 176 additions & 0 deletions src/libprojectM/Renderer/PerlinNoiseWithAlpha.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,176 @@
/*
* PerlinNoise.hpp
*
* Created and based on PerlinNoise.hpp
* Created on: Sep 14, 2019
* Author: hibengler
*/


/* The reason for this cousin class is that in Open GLES 2.0 environments,
the glTexImage2d cannot convert from GL_RGB into GL_RGBA
so the TextureManager has to use something that is pre-RGBA
*/
#ifndef PERLINNOISEWITHALPHA_HPP_
#define PERLINNOISEWITHALPHA_HPP_

#include <math.h>

class PerlinNoiseWithAlpha
{
public:

float noise_lq[256][256][4];
float noise_lq_lite[32][32][4];
float noise_mq[256][256][4];
float noise_hq[256][256][4];
float noise_lq_vol[32][32][32][4];
float noise_hq_vol[32][32][32][4];


PerlinNoiseWithAlpha();
virtual ~PerlinNoiseWithAlpha();

private:

static inline float noise( int x)
{
x = (x<<13)^x;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i truly actually have no idea what is going on here. comment? make some constants?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, it is generating random noise data used by some of the visualizers.

The noise functions convert the standard random numbers to follow different
ranges, styles, etc.

inline float noise looks to be generating a psuedo random number that is seeded with X.

This file is basically a copy of PerlInNoise.hpp, and does the same thing as PerlInNoise class, except that it generates the noise in an RGBA buffer instead of an RGB buffer.

OpenGL ES 2.0 cannot transform RGB into RGBA in hardware, but it can do RGBA to RGBA. This is why I me the step-sibling class.

return (((x * (x * x * 15731 + 789221) + 1376312589) & 0x7fffffff) / 2147483648.0);
}

static inline float noise(int x, int y)
{
int n = x + y * 57;
return noise(n);
}

static inline float noise(int x, int y, int z)
{
int n = x + y * 57 + z * 141;
return noise(n);
}

static inline float cubic_interp(float v0, float v1, float v2, float v3, float x)
{
float P = (v3 - v2) - (v0 - v1);
float Q = (v0 - v1) - P;
float R = v2 - v0;

return P*pow(x,3) + Q * pow(x,2) + R*x + v1;
}

static inline float InterpolatedNoise(float x, float y)
{
int integer_X = int(x);
float fractional_X = x - integer_X;

int integer_Y = int(y);
float fractional_Y = y - integer_Y;

float a0 = noise(integer_X - 1, integer_Y - 1);
float a1 = noise(integer_X, integer_Y - 1);
float a2 = noise(integer_X + 1, integer_Y - 1);
float a3 = noise(integer_X + 2, integer_Y - 1);

float x0 = noise(integer_X - 1, integer_Y);
float x1 = noise(integer_X, integer_Y);
float x2 = noise(integer_X + 1, integer_Y);
float x3 = noise(integer_X + 2, integer_Y);

float y0 = noise(integer_X + 0, integer_Y + 1);
float y1 = noise(integer_X, integer_Y + 1);
float y2 = noise(integer_X + 1, integer_Y + 1);
float y3 = noise(integer_X + 2, integer_Y + 1);

float b0 = noise(integer_X - 1, integer_Y + 2);
float b1 = noise(integer_X, integer_Y + 2);
float b2 = noise(integer_X + 1, integer_Y + 2);
float b3 = noise(integer_X + 2, integer_Y + 2);

float i0 = cubic_interp(a0 , a1, a2, a3, fractional_X);
float i1 = cubic_interp(x0 , x1, x2, x3, fractional_X);
float i2 = cubic_interp(y0 , y1, y2, y3, fractional_X);
float i3 = cubic_interp(b0 , b1, b2, b3, fractional_X);

return cubic_interp(i0, i1 , i2 , i3, fractional_Y);

}

static inline float perlin_octave_3d(float x,float y, float z,int width, int seed, float period)
{
float freq=1/(float)(period);

int num=(int)(width*freq);
int step_x=(int)(x*freq);
int step_y=(int)(y*freq);
int step_z=(int)(z*freq);
float zone_x=x*freq-step_x;
float zone_y=y*freq-step_y;
float zone_z=z*freq-step_z;

int boxB=step_x+step_y+step_z*num;
int boxC=step_x+step_y+step_z*(num+1);
int boxD=step_x+step_y+step_z*(num+2);
int boxA=step_x+step_y+step_z*(num-1);

float u,a,b,v,noisedata,box;

box = boxA;
noisedata=(box+seed);
u=cubic_interp(noise(noisedata-num-1),noise(noisedata-num),noise(noisedata-num+1),noise(noisedata-num+2),zone_x);
a=cubic_interp(noise(noisedata-1),noise(noisedata),noise(noisedata+1),noise(noisedata+2),zone_x);
b=cubic_interp(noise(noisedata+num -1),noise(noisedata+num),noise(noisedata+1+num),noise(noisedata+2+num),zone_x);
v=cubic_interp(noise(noisedata+2*num -1),noise(noisedata+2*num),noise(noisedata+1+2*num),noise(noisedata+2+2*num),zone_x);
float A=cubic_interp(u,a,b,v,zone_y);

box = boxB;
noisedata=(box+seed);
u=cubic_interp(noise(noisedata-num-1),noise(noisedata-num),noise(noisedata-num+1),noise(noisedata-num+2),zone_x);
a=cubic_interp(noise(noisedata-1),noise(noisedata),noise(noisedata+1),noise(noisedata+2),zone_x);
b=cubic_interp(noise(noisedata+num -1),noise(noisedata+num),noise(noisedata+1+num),noise(noisedata+2+num),zone_x);
v=cubic_interp(noise(noisedata+2*num -1),noise(noisedata+2*num),noise(noisedata+1+2*num),noise(noisedata+2+2*num),zone_x);
float B=cubic_interp(u,a,b,v,zone_y);

box = boxC;
noisedata=(box+seed);
u=cubic_interp(noise(noisedata-num-1),noise(noisedata-num),noise(noisedata-num+1),noise(noisedata-num+2),zone_x);
a=cubic_interp(noise(noisedata-1),noise(noisedata),noise(noisedata+1),noise(noisedata+2),zone_x);
b=cubic_interp(noise(noisedata+num -1),noise(noisedata+num),noise(noisedata+1+num),noise(noisedata+2+num),zone_x);
v=cubic_interp(noise(noisedata+2*num -1),noise(noisedata+2*num),noise(noisedata+1+2*num),noise(noisedata+2+2*num),zone_x);
float C=cubic_interp(u,a,b,v,zone_y);

box = boxD;
noisedata=(box+seed);
u=cubic_interp(noise(noisedata-num-1),noise(noisedata-num),noise(noisedata-num+1),noise(noisedata-num+2),zone_x);
a=cubic_interp(noise(noisedata-1),noise(noisedata),noise(noisedata+1),noise(noisedata+2),zone_x);
b=cubic_interp(noise(noisedata+num -1),noise(noisedata+num),noise(noisedata+1+num),noise(noisedata+2+num),zone_x);
v=cubic_interp(noise(noisedata+2*num -1),noise(noisedata+2*num),noise(noisedata+1+2*num),noise(noisedata+2+2*num),zone_x);
float D=cubic_interp(u,a,b,v,zone_y);

float value =cubic_interp(A,B,C,D,zone_z);

return value;
}


static inline float perlin_noise_3d(int x, int y, int z, int width, int octaves, int seed, float persistance, float basePeriod)
{
float p = persistance;
float val = 0.0;

for (int i = 0; i<octaves;i++)
{
val += perlin_octave_3d(x,y,z,width,seed,basePeriod) * p;

basePeriod *= 0.5;
p *= persistance;
}
return val;
}



};

#endif /* PERLINNOISEWITHALPHA_HPP_ */
3 changes: 0 additions & 3 deletions src/libprojectM/Renderer/Renderer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@

Pipeline* Renderer::currentPipe;


class Preset;

Renderer::Renderer(int width, int height, int gx, int gy, BeatDetect *_beatDetect, std::string _presetURL,
Expand All @@ -33,7 +32,6 @@ Renderer::Renderer(int width, int height, int gx, int gy, BeatDetect *_beatDetec
this->showstats = false;
this->studio = false;
this->realfps = 0;

/* Set up the v xoffset and vy offset to 0 which is normal Only used for VR */
this->vstartx = 0;
this->vstarty = 0;
Expand Down Expand Up @@ -169,7 +167,6 @@ Renderer::Renderer(int width, int height, int gx, int gy, BeatDetect *_beatDetec
glBindBuffer(GL_ARRAY_BUFFER, 0);



// CompositeShaderOutput VAO/VBO's
glGenBuffers(1, &m_vbo_CompositeShaderOutput);
glGenVertexArrays(1, &m_vao_CompositeShaderOutput);
Expand Down
33 changes: 26 additions & 7 deletions src/libprojectM/Renderer/TextureManager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,22 @@
#include "Common.hpp"
#include "IdleTextures.hpp"
#include "Texture.hpp"
#include "PerlinNoise.hpp"
/* OpenGL ES 2.0 cant handle converting textures fro GL_RGB to GL_RGBA via glTexImage2D
http://docs.gl/es2/glTexImage2D

This causes a GLError INVALID_OPERATION(0x502) whenever making a new Renderer or resizing it.

So because of this, we switch to a PerlinNoiseWithAlpha class to generate the noise textures.
*/
#ifdef GL_ES_VERSION_2_0
#include "PerlinNoiseWithAlpha.hpp"
#define NOISE_INTERNAL_DATA_FORMAT GL_RGBA
#else
#include "PerlinNoise.hpp"
#define NOISE_INTERNAL_DATA_FORMAT GL_RGB
#endif


#define NUM_BLUR_TEX 6


Expand Down Expand Up @@ -94,55 +107,61 @@ TextureManager::TextureManager(const std::string _presetsURL, const int texsizeX
blurTextures.push_back(textureBlur);
}

#ifdef GL_ES_VERSION_2_0
std::unique_ptr<PerlinNoiseWithAlpha> noise(new PerlinNoiseWithAlpha());
#else
std::unique_ptr<PerlinNoise> noise(new PerlinNoise());
#endif

GLuint noise_texture_lq_lite;
glGenTextures(1, &noise_texture_lq_lite);
glBindTexture(GL_TEXTURE_2D, noise_texture_lq_lite);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 32, 32, 0, GL_RGB, GL_FLOAT, noise->noise_lq_lite);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 32, 32, 0, NOISE_INTERNAL_DATA_FORMAT, GL_FLOAT, noise->noise_lq_lite);
Texture * textureNoise_lq_lite = new Texture("noise_lq_lite", noise_texture_lq_lite, GL_TEXTURE_2D, 32, 32, false);
textureNoise_lq_lite->getSampler(GL_REPEAT, GL_LINEAR);
textures["noise_lq_lite"] = textureNoise_lq_lite;

GLuint noise_texture_lq;
glGenTextures(1, &noise_texture_lq);
glBindTexture(GL_TEXTURE_2D, noise_texture_lq);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, GL_RGB, GL_FLOAT, noise->noise_lq);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, NOISE_INTERNAL_DATA_FORMAT, GL_FLOAT, noise->noise_lq);
Texture * textureNoise_lq = new Texture("noise_lq", noise_texture_lq, GL_TEXTURE_2D, 256, 256, false);
textureNoise_lq->getSampler(GL_REPEAT, GL_LINEAR);
textures["noise_lq"] = textureNoise_lq;

GLuint noise_texture_mq;
glGenTextures(1, &noise_texture_mq);
glBindTexture(GL_TEXTURE_2D, noise_texture_mq);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, GL_RGB, GL_FLOAT, noise->noise_mq);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, NOISE_INTERNAL_DATA_FORMAT, GL_FLOAT, noise->noise_mq);
Texture * textureNoise_mq = new Texture("noise_mq", noise_texture_mq, GL_TEXTURE_2D, 256, 256, false);
textureNoise_mq->getSampler(GL_REPEAT, GL_LINEAR);
textures["noise_mq"] = textureNoise_mq;

GLuint noise_texture_hq;
glGenTextures(1, &noise_texture_hq);
glBindTexture(GL_TEXTURE_2D, noise_texture_hq);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, GL_RGB, GL_FLOAT, noise->noise_hq);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 256, 256, 0, NOISE_INTERNAL_DATA_FORMAT, GL_FLOAT, noise->noise_hq);
Texture * textureNoise_hq = new Texture("noise_hq", noise_texture_hq, GL_TEXTURE_2D, 256, 256, false);
textureNoise_hq->getSampler(GL_REPEAT, GL_LINEAR);
textures["noise_hq"] = textureNoise_hq;

GLuint noise_texture_lq_vol;
glGenTextures( 1, &noise_texture_lq_vol );
glBindTexture( GL_TEXTURE_3D, noise_texture_lq_vol );
glTexImage3D(GL_TEXTURE_3D, 0, GL_RGBA, 32 ,32 ,32 ,0 ,GL_RGB ,GL_FLOAT ,noise->noise_lq_vol);
glTexImage3D(GL_TEXTURE_3D, 0, GL_RGBA, 32 ,32 ,32 ,0 ,NOISE_INTERNAL_DATA_FORMAT, GL_FLOAT ,noise->noise_lq_vol);
Texture * textureNoise_lq_vol = new Texture("noisevol_lq", noise_texture_lq_vol, GL_TEXTURE_3D, 32, 32, false);
textureNoise_lq_vol->getSampler(GL_REPEAT, GL_LINEAR);
textures["noisevol_lq"] = textureNoise_lq_vol;

GLuint noise_texture_hq_vol;
glGenTextures( 1, &noise_texture_hq_vol );
glBindTexture( GL_TEXTURE_3D, noise_texture_hq_vol );
glTexImage3D(GL_TEXTURE_3D, 0, GL_RGBA, 32, 32, 32, 0, GL_RGB, GL_FLOAT, noise->noise_hq_vol);
glTexImage3D(GL_TEXTURE_3D, 0, GL_RGBA, 32, 32, 32, 0, NOISE_INTERNAL_DATA_FORMAT, GL_FLOAT, noise->noise_hq_vol);

Texture * textureNoise_hq_vol = new Texture("noisevol_hq", noise_texture_hq_vol, GL_TEXTURE_3D, 32, 32, false);
textureNoise_hq_vol->getSampler(GL_REPEAT, GL_LINEAR);
textures["noisevol_hq"] = textureNoise_hq_vol;

}

TextureManager::~TextureManager()
Expand Down
1 change: 1 addition & 0 deletions src/projectM-sdl/projectM_SDL_main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,7 @@ HRESULT get_default_device(IMMDevice **ppMMDevice) {
#endif /** WASAPI_LOOPBACK */

int main(int argc, char *argv[]) {
srand((int)(time(NULL)));

#ifdef WASAPI_LOOPBACK
HRESULT hr;
Expand Down