• Advertisement
  • Popular Tags

  • Popular Now

  • Advertisement
  • Similar Content

    • By Fadey Duh
      Good evening everyone!

      I was wondering if there is something equivalent of  GL_NV_blend_equation_advanced for AMD?
      Basically I'm trying to find more compatible version of it.

      Thank you!
    • By Jens Eckervogt
      Hello guys, 
       
      Please tell me! 
      How do I know? Why does wavefront not show for me?
      I already checked I have non errors yet.
      using OpenTK; using System.Collections.Generic; using System.IO; using System.Text; namespace Tutorial_08.net.sourceskyboxer { public class WaveFrontLoader { private static List<Vector3> inPositions; private static List<Vector2> inTexcoords; private static List<Vector3> inNormals; private static List<float> positions; private static List<float> texcoords; private static List<int> indices; public static RawModel LoadObjModel(string filename, Loader loader) { inPositions = new List<Vector3>(); inTexcoords = new List<Vector2>(); inNormals = new List<Vector3>(); positions = new List<float>(); texcoords = new List<float>(); indices = new List<int>(); int nextIdx = 0; using (var reader = new StreamReader(File.Open("Contents/" + filename + ".obj", FileMode.Open), Encoding.UTF8)) { string line = reader.ReadLine(); int i = reader.Read(); while (true) { string[] currentLine = line.Split(); if (currentLine[0] == "v") { Vector3 pos = new Vector3(float.Parse(currentLine[1]), float.Parse(currentLine[2]), float.Parse(currentLine[3])); inPositions.Add(pos); if (currentLine[1] == "t") { Vector2 tex = new Vector2(float.Parse(currentLine[1]), float.Parse(currentLine[2])); inTexcoords.Add(tex); } if (currentLine[1] == "n") { Vector3 nom = new Vector3(float.Parse(currentLine[1]), float.Parse(currentLine[2]), float.Parse(currentLine[3])); inNormals.Add(nom); } } if (currentLine[0] == "f") { Vector3 pos = inPositions[0]; positions.Add(pos.X); positions.Add(pos.Y); positions.Add(pos.Z); Vector2 tc = inTexcoords[0]; texcoords.Add(tc.X); texcoords.Add(tc.Y); indices.Add(nextIdx); ++nextIdx; } reader.Close(); return loader.loadToVAO(positions.ToArray(), texcoords.ToArray(), indices.ToArray()); } } } } } And It have tried other method but it can't show for me.  I am mad now. Because any OpenTK developers won't help me.
      Please help me how do I fix.

      And my download (mega.nz) should it is original but I tried no success...
      - Add blend source and png file here I have tried tried,.....  
       
      PS: Why is our community not active? I wait very longer. Stop to lie me!
      Thanks !
    • By codelyoko373
      I wasn't sure if this would be the right place for a topic like this so sorry if it isn't.
      I'm currently working on a project for Uni using FreeGLUT to make a simple solar system simulation. I've got to the point where I've implemented all the planets and have used a Scene Graph to link them all together. The issue I'm having with now though is basically the planets and moons orbit correctly at their own orbit speeds.
      I'm not really experienced with using matrices for stuff like this so It's likely why I can't figure out how exactly to get it working. This is where I'm applying the transformation matrices, as well as pushing and popping them. This is within the Render function that every planet including the sun and moons will have and run.
      if (tag != "Sun") { glRotatef(orbitAngle, orbitRotation.X, orbitRotation.Y, orbitRotation.Z); } glPushMatrix(); glTranslatef(position.X, position.Y, position.Z); glRotatef(rotationAngle, rotation.X, rotation.Y, rotation.Z); glScalef(scale.X, scale.Y, scale.Z); glDrawElements(GL_TRIANGLES, mesh->indiceCount, GL_UNSIGNED_SHORT, mesh->indices); if (tag != "Sun") { glPopMatrix(); } The "If(tag != "Sun")" parts are my attempts are getting the planets to orbit correctly though it likely isn't the way I'm meant to be doing it. So I was wondering if someone would be able to help me? As I really don't have an idea on what I would do to get it working. Using the if statement is truthfully the closest I've got to it working but there are still weird effects like the planets orbiting faster then they should depending on the number of planets actually be updated/rendered.
    • By Jens Eckervogt
      Hello everyone, 
      I have problem with texture
      using System; using OpenTK; using OpenTK.Input; using OpenTK.Graphics; using OpenTK.Graphics.OpenGL4; using System.Drawing; using System.Reflection; namespace Tutorial_05 { class Game : GameWindow { private static int WIDTH = 1200; private static int HEIGHT = 720; private static KeyboardState keyState; private int vaoID; private int vboID; private int iboID; private Vector3[] vertices = { new Vector3(-0.5f, 0.5f, 0.0f), // V0 new Vector3(-0.5f, -0.5f, 0.0f), // V1 new Vector3(0.5f, -0.5f, 0.0f), // V2 new Vector3(0.5f, 0.5f, 0.0f) // V3 }; private Vector2[] texcoords = { new Vector2(0, 0), new Vector2(0, 1), new Vector2(1, 1), new Vector2(1, 0) }; private int[] indices = { 0, 1, 3, 3, 1, 2 }; private string vertsrc = @"#version 450 core in vec3 position; in vec2 textureCoords; out vec2 pass_textureCoords; void main(void) { gl_Position = vec4(position, 1.0); pass_textureCoords = textureCoords; }"; private string fragsrc = @"#version 450 core in vec2 pass_textureCoords; out vec4 out_color; uniform sampler2D textureSampler; void main(void) { out_color = texture(textureSampler, pass_textureCoords); }"; private int programID; private int vertexShaderID; private int fragmentShaderID; private int textureID; private Bitmap texsrc; public Game() : base(WIDTH, HEIGHT, GraphicsMode.Default, "Tutorial 05 - Texturing", GameWindowFlags.Default, DisplayDevice.Default, 4, 5, GraphicsContextFlags.Default) { } protected override void OnLoad(EventArgs e) { base.OnLoad(e); CursorVisible = true; GL.GenVertexArrays(1, out vaoID); GL.BindVertexArray(vaoID); GL.GenBuffers(1, out vboID); GL.BindBuffer(BufferTarget.ArrayBuffer, vboID); GL.BufferData(BufferTarget.ArrayBuffer, (IntPtr)(vertices.Length * Vector3.SizeInBytes), vertices, BufferUsageHint.StaticDraw); GL.GenBuffers(1, out iboID); GL.BindBuffer(BufferTarget.ElementArrayBuffer, iboID); GL.BufferData(BufferTarget.ElementArrayBuffer, (IntPtr)(indices.Length * sizeof(int)), indices, BufferUsageHint.StaticDraw); vertexShaderID = GL.CreateShader(ShaderType.VertexShader); GL.ShaderSource(vertexShaderID, vertsrc); GL.CompileShader(vertexShaderID); fragmentShaderID = GL.CreateShader(ShaderType.FragmentShader); GL.ShaderSource(fragmentShaderID, fragsrc); GL.CompileShader(fragmentShaderID); programID = GL.CreateProgram(); GL.AttachShader(programID, vertexShaderID); GL.AttachShader(programID, fragmentShaderID); GL.LinkProgram(programID); // Loading texture from embedded resource texsrc = new Bitmap(Assembly.GetEntryAssembly().GetManifestResourceStream("Tutorial_05.example.png")); textureID = GL.GenTexture(); GL.BindTexture(TextureTarget.Texture2D, textureID); GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMagFilter, (int)All.Linear); GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMinFilter, (int)All.Linear); GL.TexImage2D(TextureTarget.Texture2D, 0, PixelInternalFormat.Rgba, texsrc.Width, texsrc.Height, 0, PixelFormat.Bgra, PixelType.UnsignedByte, IntPtr.Zero); System.Drawing.Imaging.BitmapData bitmap_data = texsrc.LockBits(new Rectangle(0, 0, texsrc.Width, texsrc.Height), System.Drawing.Imaging.ImageLockMode.ReadOnly, System.Drawing.Imaging.PixelFormat.Format32bppRgb); GL.TexSubImage2D(TextureTarget.Texture2D, 0, 0, 0, texsrc.Width, texsrc.Height, PixelFormat.Bgra, PixelType.UnsignedByte, bitmap_data.Scan0); texsrc.UnlockBits(bitmap_data); GL.Enable(EnableCap.Texture2D); GL.BufferData(BufferTarget.TextureBuffer, (IntPtr)(texcoords.Length * Vector2.SizeInBytes), texcoords, BufferUsageHint.StaticDraw); GL.BindAttribLocation(programID, 0, "position"); GL.BindAttribLocation(programID, 1, "textureCoords"); } protected override void OnResize(EventArgs e) { base.OnResize(e); GL.Viewport(0, 0, ClientRectangle.Width, ClientRectangle.Height); } protected override void OnUpdateFrame(FrameEventArgs e) { base.OnUpdateFrame(e); keyState = Keyboard.GetState(); if (keyState.IsKeyDown(Key.Escape)) { Exit(); } } protected override void OnRenderFrame(FrameEventArgs e) { base.OnRenderFrame(e); // Prepare for background GL.Clear(ClearBufferMask.ColorBufferBit); GL.ClearColor(Color4.Red); // Draw traingles GL.EnableVertexAttribArray(0); GL.EnableVertexAttribArray(1); GL.BindVertexArray(vaoID); GL.UseProgram(programID); GL.BindBuffer(BufferTarget.ArrayBuffer, vboID); GL.VertexAttribPointer(0, 3, VertexAttribPointerType.Float, false, 0, IntPtr.Zero); GL.ActiveTexture(TextureUnit.Texture0); GL.BindTexture(TextureTarget.Texture3D, textureID); GL.BindBuffer(BufferTarget.ElementArrayBuffer, iboID); GL.DrawElements(BeginMode.Triangles, indices.Length, DrawElementsType.UnsignedInt, 0); GL.DisableVertexAttribArray(0); GL.DisableVertexAttribArray(1); SwapBuffers(); } protected override void OnClosed(EventArgs e) { base.OnClosed(e); GL.DeleteVertexArray(vaoID); GL.DeleteBuffer(vboID); } } } I can not remember where do I add GL.Uniform2();
    • By Jens Eckervogt
      Hello everyone
      For @80bserver8 nice job - I have found Google search. How did you port from Javascript WebGL to C# OpenTK.?
      I have been searched Google but it shows f***ing Unity 3D. I really want know how do I understand I want start with OpenTK But I want know where is porting of Javascript and C#?
       
      Thanks!
  • Advertisement
  • Advertisement
Sign in to follow this  

OpenGL Can Render Triangle And A Quad, But More Complex Shape Results In Segfault

This topic is 619 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hello there!

 

I am currently making my own little game engine with OpenGL, but I have been stuck with this problem for a while now.

I can render a triangle with no problems, but I get a segfault from glDrawElements with a more complex shape.

I'll try and post the relevant code snippets.

 

Here is how I send mesh data to the buffer:

void Mesh::sendToBuffer()
{
	GLuint vbo = 0;
	glGenBuffers(1, &vbo);
	glBindBuffer(GL_ARRAY_BUFFER, vbo);
	glBufferData(GL_ARRAY_BUFFER, verticesBufferSize(), vertices, GL_STATIC_DRAW);


	GLuint ibo;
	glGenBuffers(1, &ibo);
	glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ibo);
	glBufferData(GL_ELEMENT_ARRAY_BUFFER, indicesBufferSize(), indices, GL_STATIC_DRAW);

	vao = 0;
	glGenVertexArrays(1, &vao);
	glBindVertexArray(vao);
	glEnableVertexAttribArray(0);
	glBindBuffer(GL_ARRAY_BUFFER, vbo);
	glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ibo);

	// Position
	glVertexAttribPointer(0, numVertices, GL_FLOAT, GL_FALSE, sizeof(Vertex), nullptr);

	// Normals
	glVertexAttribPointer(1, numVertices, GL_FLOAT, GL_FALSE, sizeof(Vertex), (const void *)3);
}

Here is the code for creating a triangle, this works flawlessly:

Mesh Primitives::createTriangle()
{
	Mesh tri;
	tri.numVertices = 3;

	Vertex vertices[] =
	{
			glm::vec3(0.0f, 0.5f, 0.0f), // Position
			glm::vec3(0.0f, 0.0f, 1.0f), // Normal
			glm::vec3(1.0f, 1.0f, 1.0f), // Color

			glm::vec3(0.5f, -0.5f, 0.0f),
			glm::vec3(0.0f, 0.0f, 1.0f),
			glm::vec3(1.0f, 1.0f, 1.0f),

			glm::vec3(-0.5f, -0.5f, 0.0f),
			glm::vec3(0.0f, 0.0f, 1.0f),
			glm::vec3(1.0f, 1.0f, 1.0f)
	};

	tri.vertices = new Vertex[tri.numVertices];
	memcpy(tri.vertices, vertices, sizeof(vertices));

	tri.numIndices = 3;

	GLushort indices[] =
	{
		0, 1, 2
	};
	
	tri.indices = new GLushort[tri.numIndices];
	memcpy(tri.indices, indices, sizeof(indices));

	tri.sendToBuffer();

	return tri;
}

However rendering a cube, or part of a cube as shown here, fails:

Mesh Primitives::createCube()
{
	Mesh cube;
	cube.numVertices = 6;

	Vertex vertices[] =
	{
			glm::vec3(-0.5f, -0.5f, 0.5f),
			glm::vec3(0.0f, 0.0f, 1.0f),
			glm::vec3(5.0f, 5.0f, 5.0f),

			glm::vec3(-0.5f, 0.5f, 0.5f),
			glm::vec3(0.0f, 0.0f, 1.0f),
			glm::vec3(5.0f, 5.0f, 5.0f),

			glm::vec3(0.5f, 0.5f, 0.5f),
			glm::vec3(0.0f, 0.0f, 1.0f),
			glm::vec3(5.0f, 5.0f, 5.0f),

			glm::vec3(-2.5f, -0.5f, 0.5f),
			glm::vec3(0.0f, 0.0f, 1.0f),
			glm::vec3(5.0f, 5.0f, 5.0f),

			glm::vec3(-2.5f, 0.5f, 0.5f),
			glm::vec3(0.0f, 0.0f, 1.0f),
			glm::vec3(5.0f, 5.0f, 5.0f),

			glm::vec3(-1.0f, 0.5f, 0.5f),
			glm::vec3(0.0f, 0.0f, 1.0f),
			glm::vec3(5.0f, 5.0f, 5.0f),
	};

	cube.vertices = new Vertex[cube.numVertices];
	memcpy(cube.vertices, vertices, sizeof(vertices));

	cube.numIndices = 6;

	GLushort indices[] =
	{
		0, 1, 2,		0, 1, 2 // Front
		//4, 5, 6,		6, 7, 4, // Back
		//8, 9, 10,		10, 11, 8, // Bottom
		//12, 13, 14,		14, 15, 12, // Top
		//16, 17, 18,		18, 19, 16, // Left
		//20, 21, 22,		22, 23, 20 // Right
	};

	cube.indices = new GLushort[cube.numIndices];
	memcpy(cube.indices, indices, sizeof(indices));

	cube.sendToBuffer();

	return cube;
}

And to draw the mesh I simply call:

mesh.bind();
glDrawElements(GL_TRIANGLES, mesh.getNumIndices(), GL_UNSIGNED_SHORT, 0);

I think this is the relevant code, the full source is on GitHub: https://github.com/mathiassoeholm/OpenGLPlayground/tree/master/GameEngine

 

I'm sorry for posting so much code here, but I'm at a loss for what causes the Segmentation fault to happen.

 

Any help is much appreciated.

Share this post


Link to post
Share on other sites
Advertisement

You say numIndices = 6, but then you have an array of only three indices?

cube.numIndices = 6;

GLushort indices[] =
{
	0, 1, 2,		0, 1, 2 // Front
	//4, 5, 6,		6, 7, 4, // Back
	//8, 9, 10,		10, 11, 8, // Bottom
	//12, 13, 14,		14, 15, 12, // Top
	//16, 17, 18,		18, 19, 16, // Left
	//20, 21, 22,		22, 23, 20 // Right
};

You seem to be using alot of magic numbers - that can lead to bugs.

Also, you're manually allocating memory (new GLushort) - if done carelessly, that can also lead to bugs.

 

Basically, I have a pretty much zero tolerance for magic numbers and manual allocation of memory (outside of utility-classes) in my code. It just makes the code overall less error-prone.

Share this post


Link to post
Share on other sites

Thanks for the fast reply!

 

There's six indices, it's just the same triangle being repeated (0,1,2), which should still work right?

I tried changing it to: 0, 1, 2, 2, 3, which still doesn't work.

 

I have to agree with you on the magic numbers part. Things are being done very manually here though, because it's a utility method that creates a primitive.

The idea being that all the magic numbers are hidden inside a method call.

I don't think it would makes sense to introduce a constant called NUM_VERTICES_IN_A_TRIANGLE or something like that.

Share this post


Link to post
Share on other sites

Hey!

 

There might be other issues, but this is definitely one. The glVertexAttribPointer needs the offset in bytes (ie, the starting position inside your buffer for that attrib). So in your case, that's 3 * sizeof(float), rather than 3.

Edited by sirpalee

Share this post


Link to post
Share on other sites

Thanks, I've fixed that now :-)

 

Unfortunately my original problem persists.

Share this post


Link to post
Share on other sites

There's six indices

 
You're right; the spacing between them confused me.
 

Things are being done very manually here though, because it's a utility method that creates a primitive.
The idea being that all the magic numbers are hidden inside a method call.

All magic numbers ever, are "hidden inside" a function or class or source file. The point is to explain the magic numbers (and gain the benefit of strongly-typed variables), as well as centralizing the location to change, so that different pieces of code relying on the same value don't have to be manually updated if the value changes in the future.
 

I don't think it would makes sense to introduce a constant called NUM_VERTICES_IN_A_TRIANGLE or something like that.

 
Actual lines from my code:

static const size_t VerticesPerQuad = 4;
static const size_t IndicesPerQuad = 6; //Two triangles, sharing 4 vertices, have 6 indices.

 
The point is, when I see something like this:

glVertexAttribPointer(1, numVertices, GL_FLOAT, GL_FALSE, sizeof(Vertex), (const void *)3);

I go, "wait, what is '3' supposed to represent in this context?"

'1' is fine, though.

 

 

For example, isn't the final parameter of glVertexAttribPointer() supposed to be an offset in bytes? Why are you hardcoding a byte offset into your vertex structure?

[Edit:] Bah, I'm super distracted in multiple browser tabs. sirapalee already mentioned that.

 

Also, my OpenGL skills are very poor, but I don't think the second parameter is the number of vertices.  :ph34r:

Edited by Servant of the Lord

Share this post


Link to post
Share on other sites
Oh right, the second parameter is the number of components.

Also, op, you have to double check your classes. For example the mesh class does not cleanup the vbos and ibos when deleted. If those are managed by a different class, then it's a bad idea to store them on the mesh.

Share this post


Link to post
Share on other sites

Thank you so much!

 

Changing the number to 3 (pos + normal + color) gets rid of the Segfault, and the cube is now rendered :-)

 

I've removed some magic numbers, as suggested.

 

Good point about the buffers. I've added a reference count to the Mesh class, which is incremented and decremented by the MeshRenderer class.

When the ref count becomes 0, the Mesh deletes the ibo and vbo.

Share this post


Link to post
Share on other sites
You answer is a bit misleading, so was mine. Just to clarify this, to avoid issues in the future, the second parameter is the number of components for that element. Ie, for positions it's three because you have 3 components, xyz.

Share this post


Link to post
Share on other sites

I think you're still misunderstanding how glVertexAttribPointer is used; the answer is not "3". The absence of crashing doesn't mean the code is correct, unfortunately.  :( 
 
Imagine you have vertex structure like this:

struct Position
{
     float x, y, z;
};

struct Color
{
     uint8_t r, g, b, a;
};

struct Vertex
{
     Position position;
     Color coloration;
};

 
"Position" (in this example) is one entire attribute that has three float components. "Color" is a separate attribute with four uint8 components.
 
In this example, you'd set it up like this:

glVertexAttribPointer(TheIndexOfYourPositionAttribute,
 	3, GL_FLOAT, //Position has three floats. 
 	GL_FALSE, //We don't want it normalized.
 	sizeof(Vertex), //The entire stride, from one Position to the next Position (normally the size of the Vertex).
 	(GLvoid*)offsetof(Vertex, position)); //The offset of the 'Position' struct within the 'Vertex' struct.

glVertexAttribPointer(TheIndexOfYourColorAttribute,
 	4, GL_UNSIGNED_BYTE, //Color has four unsigned bytes. 
 	GL_TRUE, //We want 0-255 normalized to be 0.0 to 1.0.
 	sizeof(Vertex),
 	(GLvoid*)offsetof(Vertex, coloration)); //The offset of the 'Color' struct within the 'Vertex' struct.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement