SharpGL madness - c#

I've ported 1-1 this code from C++/OpenGL to C# SharpGL:
float[] cameraAngle = { 0, 0, 0 };
float[] cameraPosition = { 0, 0, 10 };
float[] modelPosition = { 0, 0, 0 };
float[] modelAngle = { 0, 0, 0 };
float[] matrixView = new float[16];
float[] matrixModel = new float[16];
float[] matrixModelView = new float[16];
// clear buffer
gl.ClearColor(0.1f, 0.1f, 0.1f, 1);
gl.Clear(OpenGL.COLOR_BUFFER_BIT | OpenGL.DEPTH_BUFFER_BIT | OpenGL.STENCIL_BUFFER_BIT);
// initialze ModelView matrix
gl.PushMatrix();
gl.LoadIdentity();
// ModelView matrix is product of viewing matrix and modeling matrix
// ModelView_M = View_M * Model_M
// First, transform the camera (viewing matrix) from world space to eye space
// Notice all values are negated, because we move the whole scene with the
// inverse of camera transform
gl.Rotate(-cameraAngle[0], 1, 0, 0); // pitch
gl.Rotate(-cameraAngle[1], 0, 1, 0); // heading
gl.Rotate(-cameraAngle[2], 0, 0, 1); // roll
gl.Translate(-cameraPosition[0], -cameraPosition[1], -cameraPosition[2]);
// we have set viewing matrix upto this point. (Matrix from world space to eye space)
// save the view matrix only
gl.GetFloat(OpenGL.MODELVIEW_MATRIX, matrixView); // save viewing matrix
//=========================================================================
// always Draw the grid at the origin (before any modeling transform)
//DrawGrid(10, 1);
// In order to get the modeling matrix only, reset OpenGL.MODELVIEW matrix
gl.LoadIdentity();
// transform the object
// From now, all transform will be for modeling matrix only. (transform from object space to world space)
gl.Translate(modelPosition[0], modelPosition[1], modelPosition[2]);
gl.Rotate(modelAngle[0], 1, 0, 0);
gl.Rotate(modelAngle[1], 0, 1, 0);
gl.Rotate(modelAngle[2], 0, 0, 1);
// save modeling matrix
gl.GetFloat(OpenGL.MODELVIEW_MATRIX, matrixModel);
//=========================================================================
// re-strore OpenGL.MODELVIEW matrix by multiplying matrixView and matrixModel before drawing the object
// ModelView_M = View_M * Model_M
gl.LoadMatrixf(matrixView); // Mmv = Mv
gl.MultMatrixf(matrixModel); // Mmv *= Mm
// save ModelView matrix
gl.GetFloat(OpenGL.MODELVIEW_MATRIX, matrixModelView);
//=========================================================================
// Draw a teapot after ModelView transform
// v' = Mmv * v
//DrawAxis(4);
//DrawTeapot();
gl.PopMatrix();
It doesn't look like the ModelView matrix gets multiplied, the result is the Identity Matrix!
What could be wrong??
Thanks

wrong glMatrixMode?

Related

Unable to draw Primitives on Texture in SharpDX

I have a little problem with rendering in my SharpDX Direct11 App.
I had being tested rendering scene on a texture, and then draw this texture on backBuffer... but unfortunately renderTexture do not contains primitives which should be drawn. Texture is only filled by color.
Whole project on github: https://github.com/Kordi3112/SharpDXTest11
Main code part with rendering methods:
public override void Render()
{
//Camera
var proj = Matrix.OrthoLH(3 * Form.Bounds.Width / Form.Bounds.Height, 3, 0.01f, 100f);
var view = Matrix.LookAtLH(new Vector3(0, 0, -10), new Vector3(0, 0, 20), Vector3.UnitY);
var viewProj = Matrix.Multiply(view, proj);
var world = Matrix.Identity;
var worldViewProj = world * viewProj;
worldViewProj.Transpose();
//Update wvp matrix
Context.UpdateSubresource(ref worldViewProj, ContantBuffer);
DrawOnTexture();
//Set BackBuffer as render target
Context.OutputMerger.SetTargets(depthView, renderView);
// Clear views
Context.ClearDepthStencilView(depthView, DepthStencilClearFlags.Depth, 1.0f, 0);
Context.ClearRenderTargetView(renderView, Color.Pink);
//Set TextureColor Shader
Effect2.ApplyShader(Context);
//Set Buffers
Context.InputAssembler.SetVertexBuffers(0, new VertexBufferBinding(VertexBuffer2, Utilities.SizeOf<VertexPositionColorTexture>(), 0));
Context.InputAssembler.SetIndexBuffer(IndexBuffer, Format.R32_UInt, 0);
//Set Texture to Shader
Context.PixelShader.SetShaderResource(0, RenderTexture.ShaderResourceView);
//Draw
Context.DrawIndexed(6, 0, 0);
// Present!
SwapChain.Present(0, PresentFlags.None);
}
private void DrawOnTexture()
{
//Set Color Shader
Effect1.ApplyShader(Context);
//Set Buffers
Context.InputAssembler.SetVertexBuffers(0, new VertexBufferBinding(VertexBuffer, Utilities.SizeOf<VertexPositionColor>(), 0));
Context.InputAssembler.SetIndexBuffer(IndexBuffer, Format.R32_UInt, 0);
//Set Target
RenderTexture.SetRenderTarget(Context, depthView);
//Clear Targets - Green Bgound
RenderTexture.ClearRenderTarget(Context, depthView, 0, 1, 0, 1);
//Draw on RenderTarget
Context.DrawIndexed(6, 0, 0);
}
After call: Context.DrawIndexed(6, 0, 0); in private void DrawOnTexture() primitive should be drawn.
What this code above do
What i wanted to get
What's wrong with my code?
I'm sure the problem is not matrix or camera. When i will modify code to render primitive directly on backBuffer then its drawing normaly.
public override void Render()
{
//Camera
var proj = Matrix.OrthoLH(3 * Form.Bounds.Width / Form.Bounds.Height, 3, 0.01f, 100f);
var view = Matrix.LookAtLH(new Vector3(0, 0, -10), new Vector3(0, 0, 20), Vector3.UnitY);
var viewProj = Matrix.Multiply(view, proj);
var world = Matrix.Identity;
var worldViewProj = world * viewProj;
worldViewProj.Transpose();
//Update wvp matrix
Context.UpdateSubresource(ref worldViewProj, ContantBuffer);
//DrawOnTexture();
//Set BackBuffer as render target
Context.OutputMerger.SetTargets(depthView, renderView);
// Clear views
Context.ClearDepthStencilView(depthView, DepthStencilClearFlags.Depth, 1.0f, 0);
Context.ClearRenderTargetView(renderView, Color.Pink);
//Set Color Shader
Effect1.ApplyShader(Context);
//Set Buffers
Context.InputAssembler.SetVertexBuffers(0, new VertexBufferBinding(VertexBuffer, Utilities.SizeOf<VertexPositionColor>(), 0));
Context.InputAssembler.SetIndexBuffer(IndexBuffer, Format.R32_UInt, 0);
//Set Texture to Shader
//Context.PixelShader.SetShaderResource(0, RenderTexture.ShaderResourceView);
//Draw
Context.DrawIndexed(6, 0, 0);
// Present!
SwapChain.Present(0, PresentFlags.None);
}
output
Vertex Buffers declaration:
//Position Color
VertexBuffer = Buffer.Create(Device, BindFlags.VertexBuffer, new[] {
new VertexPositionColor(new Vector4(-1, -1, 0, 1), Color.Red.ToVector4()),
new VertexPositionColor(new Vector4(-1, 1, 0, 1), Color.Green.ToVector4()),
new VertexPositionColor(new Vector4(1, 1, 0, 1), Color.Blue.ToVector4()),
new VertexPositionColor(new Vector4(1, -1, 0, 1), Color.Yellow.ToVector4())
});
//Position Color Texture
VertexBuffer2 = Buffer.Create(Device, BindFlags.VertexBuffer, new[] {
new VertexPositionColorTexture(new Vector4(-1, -1, 0, 1), Color.White.ToVector4(), new Vector2(0,1)),
new VertexPositionColorTexture(new Vector4(-1, 1, 0, 1), Color.White.ToVector4(),new Vector2(0,0)),
new VertexPositionColorTexture(new Vector4(1, 1, 0, 1), Color.White.ToVector4(),new Vector2(1,0)),
new VertexPositionColorTexture(new Vector4(1, -1, 0, 1), Color.White.ToVector4(),new Vector2(1,1))
});
IndexBuffer = Buffer.Create(Device, BindFlags.IndexBuffer, new[] {
0,1,2,
0,2,3
});

How to change position of imported STL file by coordinates

What is the way to set and get position of imported STL file. I'm looking for a solution to set position x,y,z to imported STL file like is possible for example to Joint.
Normally things are moved in eyeshot by a transformation matrix. This matrix consists of a rotation matrix 3 x 3, a location 1 x 3, and skew/stretch 4 x 1. All together this makes a 4 x 4 transformation matrix.
an imported stl actually contains lots of locations. But all you need to do is grab one of these. below I have just grabbed the min point of the bounding box.
Then to get to a place create an identity transformation matrix to ensure the rotation and skew are Zero. Now insert your location into the location part of the matrix. The transformBy function will now move every point of the stl to a new location.
to move between points you need the vector difference between the points.
Mesh myMesh = Mesh.CreateBox(10, 10, 10);
//Mesh myMesh = new Mesh();
Point3D getLocation = myMesh.BoxMin;
Point3D setLocation = new Point3D(20, -10, 0);
Point3D moveVector = setLocation - getLocation;
Transformation goPlaces = new Transformation(1);
goPlaces[0, 3] = moveVector.X;
goPlaces[1, 3] = moveVector.Y;
goPlaces[2, 3] = moveVector.Z;
//Transformation goPlaces = new Transformation(
// new double[,]
// {
// { 1, 0, 0, 20 },
// { 0, 1, 0,-10 },
// { 0, 0, 1, 0 },
// { 0, 0, 0, 1 }
// }
//);
Transformation goBack = (Transformation)goPlaces.Clone();
goBack.Invert();
myMesh.TransformBy(goPlaces);
myMesh.TransformBy(goBack);
Cheers!

MonoGame VertexPositionColor draws in incorrect place

I'm trying to make a rendering library for monogame and I'm currently working on drawing 2D polygons. However, The positions don't make any sense. Somehow, drawing them at (0, 0, 0), (100. 0, 0), (0, 100, 0), and (100, 100, 0) doesn't reach the top-left coordinate (0, 0). How do I fix this?
My Code:
BasicEffect basicEffect = new BasicEffect(GraphicsDevice);
VertexPositionColor[] vert = new VertexPositionColor[4];
vert[0].Position = new Vector3(0, 0, 0);
vert[1].Position = new Vector3(100, 0, 0);
vert[2].Position = new Vector3(0, 100, 0);
vert[3].Position = new Vector3(100, 100, 0);
short[] ind = new short[6];
ind[0] = 0;
ind[1] = 2;
ind[2] = 1;
ind[3] = 1;
ind[4] = 2;
ind[5] = 3;
foreach (EffectPass effectPass in basicEffect.CurrentTechnique.Passes)
{
effectPass.Apply();
GraphicsDevice.DrawUserIndexedPrimitives<VertexPositionColor>(
PrimitiveType.TriangleList, vert, 0, vert.Length, ind, 0, ind.Length / 3);
}
RESULT: https://imgur.com/GkyqmlY
MonoGame uses a different origin for 2D and 3D coordinate systems. In 2D, (0, 0) is top-left corner, and Y increases toward the bottom of the screen. In 3D, (0,0,0) is the center of the screen, and the coordinate grid works very much like it does in mathematics - think 4 quadrants in math, if you "flatten" the z-axis.
You're drawing in Quadrant I. If you want the drawing to be based on top-left corner, you need to translate your vertices by -1/2 your viewport width and +1/2 your viewport height.

How to prevent triangles in OpenGL from rendering on top of triangles in front of themselves

I've been working with OpenGL using the OpenTK library for .NET, writing my own engine. I placed 3 different objects, one spinning cube and 2 adjacent cubes. Everything seemed to work fine until I changed the color of the quad on top of the objects.
I'm rendering cubes with a green top, on the left the block on the back is being rendered over the block in the front. I can't seem to find out where I'm going wrong with this, when the camera is set to look from the other side it renders correctly.
The following is the related code in classes with irrelevant or unrelated methods, properties and attributes omitted:
GameState.cs
class GameState : State
{
// TEMP: Test Block
SimpleBlock block;
int i = 0;
public override void Render()
{
base.Render();
// Set OpenGL Settings
GL.Viewport(0, 0, 1024, 768);
GL.Enable(EnableCap.CullFace);
// Reset the Matrices
Matrices.ClearMatrices();
// Set Camera Settings (Field of view in radians)
Matrices.ProjectionMatrix = Matrix4.CreatePerspectiveFieldOfView((float)Math.PI / 2, (1024.0f / 768.0f), 1, 1000);
// Create the Camera
// this has to be in reverse
Matrix4 viewMatrix = Matrix4.CreateRotationX((float)Math.PI/8);
viewMatrix = viewMatrix.Translate(0, -2, -4);
// Multiply it with the ModelView (Which at this point is set to a value that we can just use = and it has the same result)
Matrices.ModelViewMatrix = viewMatrix;
// Render the Block
Matrices.Push();
Matrices.ModelViewMatrix = Matrices.ModelViewMatrix.Translate(2, 0, 0);
Matrices.ModelViewMatrix = Matrices.ModelViewMatrix.Translate(0.5f, 0, 0.5f);
Matrices.ModelViewMatrix = Matrices.ModelViewMatrix.Rotate(0, i / 40.0f, 0);
block.Render();
Matrices.Pop();
// Render the Block Again Twice
Matrices.Push();
Matrices.ModelViewMatrix = Matrices.ModelViewMatrix.Translate(-2, 0, 0);
Matrices.ModelViewMatrix = Matrices.ModelViewMatrix.Translate(0.5f, 0, 0.5f);
block.Render();
Matrices.ModelViewMatrix = Matrices.ModelViewMatrix.Translate(0, 0, -1);
block.Render();
Matrices.Pop();
// Increment Rotation Test Variable
i++;
}
}
SimpleBlock.cs
class SimpleBlock : IBlock
{
public void Render()
{
// Send the Shader Parameters to the GPU
Shader.Bind();
Shader.SendMatrices();
// Begin Rendering the Polys
GL.Begin(BeginMode.Triangles);
// Front Quad
Shader.SetColor(Color4.SaddleBrown);
GL.Normal3(0, 0, 1);
GLUtils.QuadVertices(
new Vector3(-0.5f, 1, 0.5f),
new Vector3(-0.5f, 0, 0.5f),
new Vector3( 0.5f, 1, 0.5f),
new Vector3( 0.5f, 0, 0.5f));
// Right Quad
GL.Normal3(1, 0, 0);
GLUtils.QuadVertices(
new Vector3(0.5f, 1, 0.5f),
new Vector3(0.5f, 0, 0.5f),
new Vector3(0.5f, 1, -0.5f),
new Vector3(0.5f, 0, -0.5f));
// Back Quad
GL.Normal3(0, 0, -1);
GLUtils.QuadVertices(
new Vector3( 0.5f, 1, -0.5f),
new Vector3( 0.5f, 0, -0.5f),
new Vector3(-0.5f, 1, -0.5f),
new Vector3(-0.5f, 0, -0.5f));
// Left Quad
GL.Normal3(-1, 0, 0);
GLUtils.QuadVertices(
new Vector3(-0.5f, 1, -0.5f),
new Vector3(-0.5f, 0, -0.5f),
new Vector3(-0.5f, 1, 0.5f),
new Vector3(-0.5f, 0, 0.5f));
// Bottom Quad
GL.Normal3(0, -1, 0);
GLUtils.QuadVertices(
new Vector3(-0.5f, 0, 0.5f),
new Vector3(-0.5f, 0, -0.5f),
new Vector3( 0.5f, 0, 0.5f),
new Vector3( 0.5f, 0, -0.5f));
// Top Quad
Shader.SetColor(Color4.Green);
GL.Normal3(0, 1, 0);
GLUtils.QuadVertices(
new Vector3(-0.5f, 1, -0.5f),
new Vector3(-0.5f, 1, 0.5f),
new Vector3(0.5f, 1, -0.5f),
new Vector3(0.5f, 1, 0.5f));
// Done!
GL.End();
}
}
BasicFragment.glfs
#version 130
// MultiColor Attribute
in vec4 multiColor;
// Output color
out vec4 gl_FragColor;
void main()
{
// Set fragment
gl_FragColor = multiColor;
}
BasicVertex.glvs
#version 130
// Transformation Matrices
uniform mat4 ProjectionMatrix;
uniform mat4 ModelViewMatrix;
// Vertex Position Attribute
in vec3 VertexPos;
// MultiColor Attributes
in vec4 MultiColor;
out vec4 multiColor;
void main()
{
// Process Colors
multiColor = MultiColor;
// Process Vertex
gl_Position = ProjectionMatrix * ModelViewMatrix * vec4(VertexPos.x, VertexPos.y, VertexPos.z, 1);
}
MainWindow.cs
// Extends OpenTK's GameWindow Class
class MainWindow : GameWindow
{
public MainWindow()
: base(1024, 768, new GraphicsMode(32, 0, 0, 4))
{
this.Title = "Trench Wars";
this.WindowBorder = WindowBorder.Fixed;
this.ClientSize = new Size(1024, 768);
// Set VSync On
this.VSync = VSyncMode.Adaptive;
}
protected override void OnRenderFrame(FrameEventArgs e)
{
base.OnRenderFrame(e);
// Clear Screen
GL.ClearColor(Color4.CornflowerBlue);
GL.Clear(ClearBufferMask.ColorBufferBit | ClearBufferMask.DepthBufferBit);
// Do State-Specific Rendering
StateEngine.Render();
// Pull a Wicked Bluffing move in Poker
GL.Flush();
// Swap Buffers
this.SwapBuffers();
}
}
It seems like you did forget to enable depth testing. glEnable(GL_DEPTH_TEST) before rendering the geometry is your friend (or given the language bindings you're using GL.Enable(EnableCap.DepthTest);).

Dynamic Vertexbuffer in SharpDX

I have massive Problems figuring out how to set up a dynamic VertexBuffer and IndexBuffer using SharpDX.
I have to generate Triangles where ever the User presses on the Screen.
I think i have to set up a transformation function that converts my screen coordinates to projection coordinates.
But i dont ever come this far...
I want to set up a Buffer with space for 10000 Vertices.
layout = new InputLayout(d3dDevice, vertexShaderByteCode, new[]
{
new SharpDX.Direct3D11.InputElement("POSITION", 0, Format.R32G32B32A32_Float, 0, 0),
new SharpDX.Direct3D11.InputElement("COLOR", 0, Format.R32G32B32A32_Float, 16, 0)
});
vb = Buffer.Create(d3dDevice, BindFlags.VertexBuffer, stream, 10000, ResourceUsage.Dynamic, CpuAccessFlags.Write);
vertexBufferBinding = new VertexBufferBinding(vb, Utilities.SizeOf<Vector4>() * 2, 0);
That Buffer i want to update every time i have to add new triangles using:
d3dDevice.ImmediateContext.UpdateSubresource(updateVB, vb);
updateVB are the new Triangles to be added.
Rendering works the following way:
// Prepare matrices
var view = Matrix.LookAtLH(new Vector3(0, 0, -5), new Vector3(0, 0, 0), Vector3.UnitY);
var proj = Matrix.PerspectiveFovLH((float)Math.PI / 4.0f, width / (float)height, 0.1f, 100.0f);
var viewProj = Matrix.Multiply(view, proj);
// Set targets (This is mandatory in the loop)
d3dContext.OutputMerger.SetTargets(render.DepthStencilView, render.RenderTargetView);
// Clear the views
d3dContext.ClearDepthStencilView(render.DepthStencilView, DepthStencilClearFlags.Depth, 1.0f, 0);
d3dContext.ClearRenderTargetView(render.RenderTargetView, Colors.Black);
// Calculate WorldViewProj
var worldViewProj = Matrix.Scaling(1f) * viewProj;
worldViewProj.Transpose();
// Setup the pipeline
d3dContext.InputAssembler.SetVertexBuffers(0, vertexBufferBinding);
d3dContext.InputAssembler.InputLayout = layout;
d3dContext.InputAssembler.PrimitiveTopology = PrimitiveTopology.TriangleList;
d3dContext.VertexShader.Set(vertexShader);
d3dContext.PixelShader.Set(pixelShader);
d3dContext.Draw(vertexCount, 0);
I am new to DirectX and the DirectX9 tutorials on the web don't help me very good with DirectX11.1.
Thanks
vb = Buffer.Create(d3dDevice, BindFlags.VertexBuffer, stream, 10000, ResourceUsage.Dynamic, CpuAccessFlags.Write);
Is wrong, since you want 10000 vertices, but allocate 10000 bytes, so should be:
10000 * sizeof(Vector4) * 2
According to your input layout.
Also to write into your buffer, you should look at context.MapSubresource instead.

Categories