hlsl sharpen, blur post-proceesing effect code issue - directx-11

im trying to implement sharpen,blur hlsl shader code into my application
i referenced learnopengl tutorial and excuted glsl code and that was fine
https://learnopengl.com/Advanced-OpenGL/Framebuffers
when i implement those glsl code to hlsl code and run it
it doesnt apply effect here is my hlsl code
exture2D screenTex;
SamplerState splr :register(s0);
const float offsetX =1.0f/1600.0f;
const float offsetY = 1.0f / 900.0f;
float4 main(float2 tc : Texcoord) : SV_TARGET
{
float4 color;
//Kernels
float2 offsets[9] =
{
float2(-offsetX, offsetY), //top - left
float2(0.0f, offsetY), //top - center
float2(offsetX, offsetY), //top - right
float2(-offsetX, 0.0f), //center-left
float2(0.0f, 0.0f), //center-center
float2(offsetX, 0.0f), //center-right
float2(-offsetX, -offsetY), //bottom - left
float2(0.0f, -offsetY), //bottom - center
float2(offsetX, -offsetY) //bottom-right
};
//for sharpen effect
/*float kernel[9] = {
-1, -1, -1,
-1, 9, -1,
-1, -1, -1
};*/
float kernel[9]=
{
1.0f / 16.0f , 2.0f / 16.0f, 1.0f / 16.0f,
2.0f / 16.0f , 4.0f / 16.0f, 2.0f / 16.0f,
1.0f / 16.0f , 2.0f / 16.0f, 1.0f / 16.0f
};
float3 col = float3(0.0f, 0.0f, 0.0f);
[unroll]
for (int i = 0; i < 9; ++i)
{
col += screenTex.Sample(splr, tc + offsets[i]).rgb * kernel[i];
}
color = float4(col, 1.0f);
return color;
}
if i run these code there is no change on my scene
i think there is issue in texture sampling with texture coordinate
ps i checked offscreen rendering works fine, and simple effect code like inversion and grayscale
it does work correctly
what is problem i need help

i found what is problem in hlsl when sampling texture coordinates operation doesnt work
col += screenTex.Sample(splr, tc + offsets[i]).rgb * kernel[i];
you should use index like
screen.Sample(splr,tc,int2(x,y)
im not sure there is other way to modifying texturecoordinates

Related

OpenGL Orthographic Projection and Translate

The code below draws a rectangle in 2D screen space using OpenGL ES2. How do move the drawing of the rectangle by 1 pixel to the right without modifying its vertices?
Specifically, what I am trying to do is move the coordinates 0.5 pixels to the right. I had to do this previously with GLES1.x and the reason for this is that I had problems drawing lines in the correct place unless I did a glTranslate() with 0.5f.
I'm confused about the use of glm::translate() in the code below.
If I attempt a translate of 0.5f, the whole rectangle moves from the left of the screen to the middle - a jump of about 200 pixels.
I get the same result whether I do a glm::translate on the Model or the View matrix.
Is the order of the matrix multiplication wrong and what should it be?
short g_RectFromTriIndices[] =
{
0, 1, 2,
0, 2, 3
}; // The order of vertex rendering.
GLfloat g_AspectRatio = 1.0f;
//--------------------------------------------------------------------------------------------
// LoadTwoTriangleVerticesForRect()
//--------------------------------------------------------------------------------------------
void LoadTwoTriangleVerticesForRect( GLfloat *pfRectVerts, float fLeft, float fTop, float fWidth, float fHeight )
{
pfRectVerts[ 0 ] = fLeft;
pfRectVerts[ 1 ] = fTop;
pfRectVerts[ 2 ] = 0.0;
pfRectVerts[ 3 ] = fLeft + fWidth;
pfRectVerts[ 4 ] = fTop;
pfRectVerts[ 5 ] = 0.0;
pfRectVerts[ 6 ] = fLeft + fWidth;
pfRectVerts[ 7 ] = fTop + fHeight;
pfRectVerts[ 8 ] = 0.0;
pfRectVerts[ 9 ] = fLeft;
pfRectVerts[ 10 ] = fTop + fHeight;
pfRectVerts[ 11 ] = 0.0;
}
//--------------------------------------------------------------------------------------------
// Draw()
//--------------------------------------------------------------------------------------------
void Draw( void )
{
GLfloat afRectVerts[ 12 ];
//LoadTwoTriangleVerticesForRect( afRectVerts, 0, 0, g_ScreenWidth, g_ScreenHeight );
LoadTwoTriangleVerticesForRect( afRectVerts, 50, 50, 100, 100 );
// Correct for aspect ratio so squares ARE squares and not rectangular stretchings..
g_AspectRatio = (GLfloat) g_ScreenWidth / (GLfloat) g_ScreenHeight;
glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );
GLuint hPosition = glGetAttribLocation( g_SolidProgram, "vPosition" );
// PROJECTION
glm::mat4 Projection = glm::mat4(1.0);
// Projection = glm::perspective( 45.0f, g_AspectRatio, 0.1f, 100.0f );
// VIEW
glm::mat4 View = glm::mat4(1.0);
static GLfloat transValY = 0.5f;
static GLfloat transValX = 0.5f;
//View = glm::translate( View, glm::vec3( transValX, transValY, 0.0f ) );
// MODEL
glm::mat4 Model = glm::mat4(1.0);
// static GLfloat rot = 0.0f;
// rot += 0.001f;
// Model = glm::rotate( Model, rot, glm::vec3( 0.0f, 0.0f, 1.0f ) ); // where x, y, z is axis of rotation (e.g. 0 1 0)
glm::mat4 Ortho = glm::ortho( 0.0f, (GLfloat) g_ScreenWidth, (GLfloat) g_ScreenHeight, 0.0f, 0.0f, 1000.0f );
glm::mat4 MVP;
MVP = Projection * View * Model * Ortho;
GLuint hMVP;
hMVP = glGetUniformLocation( g_SolidProgram, "MVP" );
glUniformMatrix4fv( hMVP, 1, GL_FALSE, glm::value_ptr( MVP ) );
glEnableVertexAttribArray( hPosition );
// Prepare the triangle coordinate data
glVertexAttribPointer( hPosition, 3, GL_FLOAT, FALSE, 0, afRectVerts );
// Draw the rectangle using triangles
glDrawElements( GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, g_RectFromTriIndices );
glDisableVertexAttribArray( hPosition );
}
Here is the vertex shader source:
attribute vec4 vPosition;
uniform mat4 MVP;
void main()
{
gl_Position = MVP * vPosition;
}
UPDATE: I'm finding the below matrix multiplication is giving me better results. I don't know if this is "correct" or not though:
MVP = Ortho * Model * View * Projection;
That MVP seems really weird to me, you shouldn't need 4 things in there to get your MVP.. your Projection matrix should just be the Orthogonal one, so in this case
MVP = Projection * View * Ortho;
But I can also see that your Projection matrix has been commented from perspective so I don't think it's doing much right now.
By the sounds of it since you want the model co-ordinates to stay the same while moving, you want to move your camera right? So (By the looks of it your vertices are using a 1 unit per pixel co-ordinate range) doing a translate of 0.5f to your View is shifting whatever half your projection space is. Instead, you want to have something like a Camera class that you get your Viewfrom using the camera's X and Y positions.
Then you can get your View matrix using the cameras position which can share the world units system you're using, which is 1 unit per pixel.
glm::mat4 view;
view = glm::lookAt(glm::vec3(camX, camY, 0.0), glm::vec3(0.0, 0.0, 0.0),glm::vec3(0.0, 1.0, 0.0));
I ripped that line straight (minus changing camZ for camY) from a really good 3d tutorial on camera here but the exact same concept can be applied to a orthogonal camera instead
I know it's a bit more overhead but having a cmaera class that you can control this way is nicer practice than manually using glm::translate,rotate&scale to control your viewport (and it lets you ensure that you'r working with a more obivous co-ordinate system between your camera and models co-ordinate points.

OpenGL ES 2.0 renders coloured screen without the images

I'm trying to render sprites using OpenGL ES 2.0. However I only get a coloured screen without the sprites. Everything is setup correctly as far as I see. What could be wrong? Here is how I setup the projection and view matrices:
this.position = new Vector2(frustumWidth/2, frustumHeight/2);
for(int i=0;i<16;i++)
{
mtrxProjection[i] = 0.0f;
mtrxView[i] = 0.0f;
mtrxProjectionAndView[i] = 0.0f;
}
Matrix.orthoM(mtrxProjection, 0, position.x - frustumWidth * zoom / 2,
position.x + frustumWidth * zoom / 2,
position.y - frustumHeight * zoom / 2,
position.y + frustumHeight * zoom / 2,
10 , -10 );
Matrix.setLookAtM(mtrxView, 0, position.x, position.y, 0.0f, position.x, position.y, -1.0f, 0f, 1.0f, 0.0f);
Matrix.multiplyMM(mtrxProjectionAndView, 0, mtrxProjection, 0, mtrxView, 0);

Upgrading code from OpenGL ES 1.0 to 2.0

I'm just working through the twee jump project which is written in cocos2d 1.0 found here
I'm having trouble converting this section of the code to OpenGL ES 2.0. I need at least 10 reputations to post a picture but a picture of the errors I get when I try to build and run can be found here:
- (void)draw {
[super draw];
if(currentScorePosition < 0) return;
glColor4f(0.0f, 0.0f, 0.0f, 0.2f);
float w = 320.0f;
float h = 27.0f;
float x = (320.0f - w) / 2.0f;
float y = 359.0f - currentScorePosition * h;
GLfloat vertices[4][2];
GLubyte indices[4] = { 0, 1, 3, 2 };
vertices[0][0] = x; vertices[0][1] = y;
vertices[1][0] = x+w; vertices[1][1] = y;
vertices[2][0] = x+w; vertices[2][1] = y+h;
vertices[3][0] = x; vertices[3][1] = y+h;
glDisable(GL_TEXTURE_2D);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
glDisableClientState(GL_COLOR_ARRAY);
glVertexPointer(2, GL_FLOAT, 0, vertices);
glDrawElements(GL_TRIANGLE_STRIP, 4, GL_UNSIGNED_BYTE, indices);
glEnableClientState(GL_COLOR_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glEnable(GL_TEXTURE_2D);
glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
}

How to convert world coordinates to screen coordinates in OpenGL ES 2.0

I am using following OpenGL ES 1.x code to set my projection coordinates.
glMatrixMode(GL_PROJECTION);
float width = 320;
float height = 480;
glOrthof(0.0, // Left
1.0, // Right
height / width, // Bottom
0.0, // Top
-1.0, // Near
1.0); // Far
glMatrixMode(GL_MODELVIEW);
What is the equivalent method to setup this in OpenGL ES 2.0 ?
What projection matrix should I pass to the vertex shader ?
I have tried following function to create the matrix but its not working:
void SetOrtho (Matrix4x4& m, float left, float right, float bottom, float top, float near,
float far)
{
const float tx = - (right + left)/(right - left);
const float ty = - (top + bottom)/(top - bottom);
const float tz = - (far + near)/(far - near);
m.m[0] = 2.0f/(right-left);
m.m[1] = 0;
m.m[2] = 0;
m.m[3] = tx;
m.m[4] = 0;
m.m[5] = 2.0f/(top-bottom);
m.m[6] = 0;
m.m[7] = ty;
m.m[8] = 0;
m.m[9] = 0;
m.m[10] = -2.0/(far-near);
m.m[11] = tz;
m.m[12] = 0;
m.m[13] = 0;
m.m[14] = 0;
m.m[15] = 1;
}
Vertex Shader :
uniform mat4 u_mvpMatrix;
attribute vec4 a_position;
attribute vec4 a_color;
varying vec4 v_color;
void main()
{
gl_Position = u_mvpMatrix * a_position;
v_color = a_color;
}
Client Code (parameters to the vertex shader):
float min = 0.0f;
float max = 1.0f;
const GLfloat squareVertices[] = {
min, min,
min, max,
max, min,
max, max
};
const GLfloat squareColors[] = {
1, 1, 0, 1,
0, 1, 1, 1,
0, 0, 0, 1,
1, 0, 1, 1,
};
Matrix4x4 proj;
SetOrtho(proj, 0.0f, 1.0f, 480.0/320.0, 0.0f, -1.0f, 1.0f );
The output i am getting in the iPhone simulator:
Your transcription of the glOrtho formula looks correct.
Your Matrix4x4 class is custom, but is it possible that m.m ends up being loaded directly as a glUniformMatrix4fv? If so check that you're setting the transpose flag as GL_TRUE, since you're loading data in row major format and OpenGL expects column major (ie, standard rules are that index [0] is the top of the first column, [3] is at the bottom of the first column, [4] is at the top of the second column, etc).
It's possibly also worth checking that —— assuming you've directly replicated the old world matrix stacks — you're applying modelview and projection in the correct order in your vertex shader or else compositing them correctly on the CPU, whichever way around you're doing it.

OpenGL ES glRotatef performing shear instead of rotate?

I am able to draw a sprite on the screen of an iPhone, but when I try to rotate it I am getting some weird results. It seems to be stretching the sprite in the y direction more the closer the sprite gets to pointing down the y-axis (90 and 270 degrees). It displays correctly when pointing down the x and -x axes (0 and 180 degrees). It is basically like it is shearing instead of rotating. Here are the essentials of the code (projection matrix is ortho):
glPushMatrix();
glLoadIdentity();
glTranslatef( position.x, position.y, -1.0f );
glRotatef( rotation, 0.0f, 0.0f, 1.0f );
glScalef( halfSize.x, halfSize.y, 1.0f );
vertices[0] = 1.0f;
vertices[1] = 1.0f;
vertices[2] = 0.0f;
vertices[3] = 1.0f;
vertices[4] = -1.0f;
vertices[5] = 0.0f;
vertices[6] = -1.0f;
vertices[7] = 1.0f;
vertices[8] = 0.0f;
vertices[9] = -1.0f;
vertices[10] = -1.0f;
vertices[11] = 0.0f;
glVertexPointer( 3, GL_FLOAT, 0, vertices );
glDrawArrays( GL_TRIANGLE_STRIP, 0, 4 );
glPopMatrix();
Can anybody explain to me how to fix this please?
halfsize is just half the x and y extent of the sprite; removing the glScalef call does not make any difference.
Here is my matrix setup:
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrthof(0, 320, 480, 0, 0.01, 5);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
OK, hopefully this screenshot will demonstrate what's happening:
If you are scaling by the same amount in the x and y directions, then your projection is causing the distortion.
Just a hunch, but maybe try swapping the 320 and 480 in your Ortho projection. (In case the X and Y on the iPhone is swapped)

Resources