Why is the sprite not rendering in OpenGL?
You have to initialize the model matrix variable glm::mat4 model
.
The glm API documentation refers to The OpenGL Shading Language specification 4.20.
5.4.2 Vector and Matrix Constructors
If there is a single scalar parameter to a vector constructor, it is used to initialize all components of the constructed vector to that scalar’s value. If there is a single scalar parameter to a matrix constructor, it is used to initialize all the components on the matrix’s diagonal, with the remaining components initialized to 0.0.
This means, that an identity matrix can be initialized by the single parameter 1.0:
glm::mat4 model(1.0f);
Further your sprite is very small and it is out of the viewport (clip space) at the left side:
Change your code like this:
glm::vec2 position = glm::vec2(10.0f, 10.0f); // 10.0f instead of -10.0f
OpenGL sprite mapping doesn't work
I'm not sure why are you mixing id within your equation. Furthermore, your structure just needs the start point and dimensions of the Sprite:
struct Sprite {
Vertex start,end;
int textureID;
}
// nx and ny are indexes of which sprite inside the atlas do you need (index starting at 0
// xsize and ysize are the standard size of an sprite in texture space, for example
// in your example both would be 0.5
Sprite generateSprite(int nx, int ny, int xsize int ysize){
Sprite s;
s.start.u = xsize*nx;
s.start.v = ysize*ny;
s.end.u = s.start.u+xsize;
s.end.v = s.start.v+ysize;
}
That's what I think you are trying to archive, hope that helps.
EDIT: you can calculate xsize and ysize easily, for example if your texture holds 4x4 sprites of the same size, xsize = ysize = 1.0/4
OpenGL point sprite uv coordinates not working correctly
From the additional comment:
I'm using GLFW to create a context with no specific profile selected.
If you do not explicitly request a core profile, you will get either a legacy context (something before the invention of profiles in GL), or a compatibility profile. Since support for compatibility profiles is optional,you can not rely on getting the a context supporting GL 3.3 that. way.
It creates a 4.6 profile on linux, should be the same on my Windows Laptop.
That's only luck. With the open source mesa driver on Linux, you will only get GL 3.0, and on MacOS, only 2.1.
I use glad as loader, which I configured to be in core profile.
That doesn't matter. It won't change which version and profile your context supports. It will just limit the loaded functions to the subset GL 3.3 core provides.
However, my main point about asking for the the GL profile is that point sprite rendering differs significantly between core and compatibility profiles:
- In core profile OpenGL, point rendering will automatically be point sprite rendering
- In compatibility profiles, you have to explicitly enable this via
glEnable(GL_POINT_SPRITE)
, otherwise,gl_PointCoord
will not be calculated.
I've read on a few sites that you can access the uv coordinates of a point sprite in the fragment shader with
gl_PointCoord
, but for some reason it is always 0, unless I capture a frame with renderdoc to take a look at whats going on.
That doesn't surprise me then: renderdoc only works with core profile contexts, and most likely tweaks the context creation to a core profile in your case.
Since your code seems to target core profile anyway (and seems to work on that, too, judging by the experience you get with renderdoc), you should explicitly request a core profile. This will have the additional benefit of greatly increasing the number of implementations which can run your code.
The other solution would be to detect if you're running in core or compat profiles, and conditionally call glEnable(GL_POINT_SPRITE)
(or, the quick&dirty variant: always call that and ignore the GL error which will be generated by this on core profile contexts). However, your glad loader's GL header probably will not even contain the #define GL_POINT_SPRITE 0x8861
definition...
Architecture for Sprite Rendering in OpenGL
From my experience with large numbers of particles, I would use option (2.). Maybe you can pack the index of the offset/direction into your data (e.g. as w-component of your postion vector, if you don't use it so far)? 0 = (-1,-1); 1 = (-1,1); 2 = (1,1); 3 = (1,-1).
(As suggested by Ian, I just copied my comment to an answer!)
@Ian: If I understand you corretly, you said that you have a global opacity/alpha, so you should be able to use an uniform
for that and use the w-component of your vec4 color
for the flag
. However, I doubt that this will make any difference...
By the way, the geometry shader solution you already mentioned should not only be more elegant, but also a bit faster.
OpenTK: Sprites not Rendering?
Solved it: My problem was on line 114, I had the following code:
public int Attribute(string name)
{
return _attributes.ContainsKey(name) ? _attributes[name].Address : -1;
}
public int Uniform(string name)
{
return _uniforms.ContainsKey("name") ? _uniforms[name].Address : -1;
}
public uint Buffer(string name)
{
return _buffers.ContainsKey(name) ? _buffers[name] : 0;
}
As follows:
_uniforms.ContainsKey("name") should be _uniforms.ContainsKey(name)
Related Topics
Vector of Const Objects Giving Compile Error
Mixing C++11 Atomics and Openmp
C++ Array Assignment of Multiple Values
Which Headers in the C++ Standard Library Are Guaranteed to Include Another Header
How to Sort an Stl Map by Value
How to Get Memory Usage Under Windows in C++
Serial Comm Using Writefile/Readfile
Why Is It Allowed to Pass R-Values by Const Reference But Not by Normal Reference
Gcc C++ "Hello World" Program -> .Exe Is 500Kb Big When Compiled on Windows. How to Reduce Its Size
Variable Assignment in an "If" Condition
Why Is My Helloworld Function Not Declared in This Scope
C++ Compare Char Array with String
C and C++ Programming on Ubuntu 11.10