/// <summary> /// Sets the attributes. /// </summary> /// <param name="gl">The OpenGL instance.</param> public override void SetAttributes(OpenGL gl) { if (enableCullFace.HasValue) { gl.EnableIf(OpenGL.GL_CULL_FACE, enableCullFace.Value); } if (cullFaceMode.HasValue) { gl.CullFace((uint)cullFaceMode.Value); } if (enableSmooth.HasValue) { gl.EnableIf(OpenGL.GL_POLYGON_SMOOTH, enableSmooth.Value); } if (frontFaceMode.HasValue) { gl.FrontFace((uint)frontFaceMode.Value); } if (polygonMode.HasValue) { gl.PolygonMode(OpenGL.GL_FRONT_AND_BACK, (uint)polygonMode.Value); } if (offsetFactor.HasValue && offsetBias.HasValue) { gl.PolygonOffset(offsetFactor.Value, offsetBias.Value); } if (enableOffsetPoint.HasValue) { gl.EnableIf(OpenGL.GL_POLYGON_OFFSET_POINT, enableOffsetPoint.Value); } if (enableOffsetLine.HasValue) { gl.EnableIf(OpenGL.GL_POLYGON_OFFSET_LINE, enableOffsetLine.Value); } if (enableOffsetFill.HasValue) { gl.EnableIf(OpenGL.GL_POLYGON_OFFSET_FILL, enableOffsetFill.Value); } }
public override void Draw(ref OpenGL gl) { if (!TexturesInitialised) { InitializeTexture(ref gl); } // Clear the color and depth buffer. gl.Clear(OpenGL.GL_COLOR_BUFFER_BIT | OpenGL.GL_DEPTH_BUFFER_BIT); // Load the identity matrix. gl.LoadIdentity(); gl.Enable(OpenGL.GL_TEXTURE_2D); gl.Enable(OpenGL.GL_LIGHTING); gl.Enable(OpenGL.GL_LIGHT0); gl.Enable(OpenGL.GL_DEPTH_TEST); gl.Enable(OpenGL.GL_NORMALIZE); gl.BindTexture(OpenGL.GL_TEXTURE_2D, gtexture[0]); gl.Color(1.0f, 1.0f, 1.0f, 0.1f); gl.Begin(OpenGL.GL_QUADS); gl.FrontFace(OpenGL.GL_FRONT_FACE); gl.TexCoord(1.0f, 1.0f); gl.Vertex(gImage1.Width, gImage1.Height, 1.0f); gl.TexCoord(0.0f, 1.0f); gl.Vertex(0.0f, gImage1.Height, 1.0f); gl.TexCoord(0.0f, 0.0f); gl.Vertex(0.0f, 0.0f, 1.0f); gl.TexCoord(1.0f, 0.0f); gl.Vertex(gImage1.Width, 0.0f, 1.0f); gl.End(); gl.Disable(OpenGL.GL_TEXTURE_2D); gl.MatrixMode(OpenGL.GL_PROJECTION); gl.LoadIdentity(); gl.Ortho(0.0, (double)gImage1.Width, (double)gImage1.Height, 0.0, -1.0, 1.0); gl.MatrixMode(OpenGL.GL_MODELVIEW); gl.Disable(OpenGL.GL_DEPTH_TEST); }
public void draw(OpenGL gl) { if (net) gl.CullFace(OpenGL.GL_FRONT); else gl.CullFace(OpenGL.GL_BACK); if (vertices != null) { gl.EnableClientState(OpenGL.GL_VERTEX_ARRAY); gl.VertexPointer(3, OpenGL.GL_FLOAT, 0, vertices); } if (normals != null) { gl.EnableClientState(OpenGL.GL_NORMAL_ARRAY); gl.NormalPointer(OpenGL.GL_FLOAT, 0, normals); } if (colors != null) { gl.EnableClientState(OpenGL.GL_COLOR_ARRAY); gl.ColorPointer(3, OpenGL.GL_UNSIGNED_BYTE, 0, colors); } if (textCoords != null) { gl.EnableClientState(OpenGL.GL_TEXTURE_COORD_ARRAY); gl.TexCoordPointer(2, OpenGL.GL_FLOAT, 0, textCoords); } gl.FrontFace(OpenGL.GL_CCW); if (lengths != null && strips != null) for (int i = 0; i < strips.Count; i++) { gl.DrawElements(OpenGL.GL_TRIANGLE_STRIP, lengths[i], OpenGL.GL_UNSIGNED_INT, strips[i]); } if (doubleSurface) { if (doubleNormals != null) { gl.NormalPointer(OpenGL.GL_FLOAT, 0, doubleNormals); } gl.FrontFace(OpenGL.GL_CW); for (int i = 0; i < strips.Count; i++) { gl.DrawElements(OpenGL.GL_TRIANGLE_STRIP, lengths[i], OpenGL.GL_UNSIGNED_INT, strips[i]); } } gl.DisableClientState(OpenGL.GL_VERTEX_ARRAY); gl.DisableClientState(OpenGL.GL_COLOR_ARRAY); gl.DisableClientState(OpenGL.GL_NORMAL_ARRAY); gl.DisableClientState(OpenGL.GL_TEXTURE_COORD_ARRAY); }
/// <summary> /// Casts a real time 3D shadow. /// </summary> /// <param name="gl">The OpenGL object.</param> /// <param name="lights">The lights.</param> private void CastShadow(OpenGL gl) { // Set the connectivity, (calculate the neighbours of each face). SetConnectivity(); // Get the lights in the scene. var lights = TraverseToRootElement().Traverse <Light>(l => l.IsEnabled && l.On && l.CastShadow); // Get some useful references. var faces = ParentPolygon.Faces; // Go through every light in the scene. foreach (var light in lights) { // Every face will have a visibility setting. bool[] facesVisible = new bool[faces.Count]; // Get the light position relative to the polygon. Vertex lightPos = light.Position; lightPos = lightPos - ParentPolygon.Transformation.TranslationVertex; // Go through every face, finding out whether it's visible to the light. for (int nFace = 0; nFace < faces.Count; nFace++) { // Get a reference to the face. Face face = faces[nFace]; // Is this face facing the light? float[] planeEquation = face.GetPlaneEquation(ParentPolygon); float side = planeEquation[0] * lightPos.X + planeEquation[1] * lightPos.Y + planeEquation[2] * lightPos.Z + planeEquation[3]; facesVisible[nFace] = (side > 0) ? true : false; } // Save all the attributes. gl.PushAttrib(OpenGL.GL_ALL_ATTRIB_BITS); // Turn off lighting. gl.Disable(OpenGL.GL_LIGHTING); // Turn off writing to the depth mask. gl.DepthMask(0); gl.DepthFunc(OpenGL.GL_LEQUAL); // Turn on stencil buffer testing. gl.Enable(OpenGL.GL_STENCIL_TEST); // Translate our shadow volumes. ParentPolygon.PushObjectSpace(gl); // Don't draw to the color buffer. gl.ColorMask(0, 0, 0, 0); gl.StencilFunc(OpenGL.GL_ALWAYS, 1, 0xFFFFFFFF); gl.Enable(OpenGL.GL_CULL_FACE); // First Pass. Increase Stencil Value In The Shadow gl.FrontFace(OpenGL.GL_CCW); gl.StencilOp(OpenGL.GL_KEEP, OpenGL.GL_KEEP, OpenGL.GL_INCR); DoShadowPass(gl, lightPos, facesVisible); // Second Pass. Decrease Stencil Value In The Shadow gl.FrontFace(OpenGL.GL_CW); gl.StencilOp(OpenGL.GL_KEEP, OpenGL.GL_KEEP, OpenGL.GL_DECR); DoShadowPass(gl, lightPos, facesVisible); gl.FrontFace(OpenGL.GL_CCW); ParentPolygon.PopObjectSpace(gl); // Enable writing to the color buffer. gl.ColorMask(1, 1, 1, 1); // Draw A Shadowing Rectangle Covering The Entire Screen gl.Color(light.ShadowColor); gl.Enable(OpenGL.GL_BLEND); gl.BlendFunc(OpenGL.GL_SRC_ALPHA, OpenGL.GL_ONE_MINUS_SRC_ALPHA); gl.StencilFunc(OpenGL.GL_NOTEQUAL, 0, 0xFFFFFFF); gl.StencilOp(OpenGL.GL_KEEP, OpenGL.GL_KEEP, OpenGL.GL_KEEP); Sphere shadow = new Sphere(); shadow.Transformation.ScaleX = shadowSize; shadow.Transformation.ScaleY = shadowSize; shadow.Transformation.ScaleZ = shadowSize; shadow.Render(gl, RenderMode.Design); gl.PopAttrib(); } }