コード例 #1
0
ファイル: Pass.cs プロジェクト: RonOHara-GG/WebGLRenderer
 public Pass(Scene scene, string name, string src)
     : base(scene, name, src)
 {
     renderObjects = new List<RenderObject>();
     lights = new List<Light>();
     cameras = new List<Camera>();
 }
コード例 #2
0
        public FrameBuffer(Scene scene, string name, string src)
            : base(scene, name, src)
        {
            try
            {
                XmlDocument fbXML = new XmlDocument();
                fbXML.Load(src);

                width = Convert.ToInt32(fbXML.DocumentElement.Attributes.GetNamedItem("width").Value);
                height = Convert.ToInt32(fbXML.DocumentElement.Attributes.GetNamedItem("height").Value);
                colorFormat = fbXML.DocumentElement.Attributes.GetNamedItem("colorFormat").Value;

                colorTexture = scene.GetTexture(name + "_color", null);
                colorTexture.width = width;
                colorTexture.height = height;
                colorTexture.Create(PixelFormat.Rgba, PixelType.UnsignedByte, IntPtr.Zero);

                depthTexture = scene.GetTexture(name + "_depth", null);
                depthTexture.width = width;
                depthTexture.height = height;
                depthTexture.format = PixelInternalFormat.DepthComponent;
                depthTexture.Create(PixelFormat.DepthComponent, PixelType.UnsignedShort, IntPtr.Zero);

                GL.GenFramebuffers(1, out frameBuffer);
                GL.BindFramebuffer(FramebufferTarget.Framebuffer, frameBuffer);
                GL.FramebufferTexture2D(FramebufferTarget.Framebuffer, FramebufferAttachment.ColorAttachment0, TextureTarget.Texture2D, colorTexture.glTexture, 0);
                GL.FramebufferTexture2D(FramebufferTarget.Framebuffer, FramebufferAttachment.DepthAttachment, TextureTarget.Texture2D, depthTexture.glTexture, 0);

                GL.BindFramebuffer(FramebufferTarget.Framebuffer, 0);
            }
            catch(Exception )
            {
                System.Windows.Forms.MessageBox.Show("Failed to load framebuffer: " + src);
            }
        }
コード例 #3
0
ファイル: Texture.cs プロジェクト: RonOHara-GG/WebGLRenderer
 public Texture(Scene scene, string name, string src)
     : base(scene, name, src)
 {
     if( src != null && src.Length > 0 )
     {
         // TODO: figure out how to load a texture!
     }
 }
コード例 #4
0
ファイル: Viewport.cs プロジェクト: RonOHara-GG/WebGLRenderer
        public Viewport(Scene scene, string name, string src)
            : base(scene, name, src)
        {
            // load the xml
            try
            {
                XmlDocument viewportXML = new XmlDocument();
                viewportXML.Load(src);

                this.left = Convert.ToSingle(viewportXML.DocumentElement.Attributes.GetNamedItem("left").Value);
                this.top = Convert.ToSingle(viewportXML.DocumentElement.Attributes.GetNamedItem("top").Value);
                this.width = Convert.ToSingle(viewportXML.DocumentElement.Attributes.GetNamedItem("width").Value);
                this.height = Convert.ToSingle(viewportXML.DocumentElement.Attributes.GetNamedItem("height").Value);
                this.percentageMode = viewportXML.DocumentElement.Attributes.GetNamedItem("percentageMode").Value == "true";
            }
            catch (Exception)
            {
                System.Windows.Forms.MessageBox.Show("Failed to load viewport: " + src);
            }
        }
コード例 #5
0
ファイル: Light.cs プロジェクト: RonOHara-GG/WebGLRenderer
        public Light(Scene scene, string name, string src)
            : base(scene, name, src)
        {
            color = new Vector3(1.0f, 1.0f, 1.0f);
            dir = new Vector3();
            shadowMatrix = Matrix4.Identity;

            try
            {
                XmlDocument xml = new XmlDocument();
                xml.Load(src);
                foreach( XmlAttribute attrib in xml.DocumentElement.Attributes )
                {
                    string[] values;
                    switch (attrib.Name)
                    {
                        case "type":
                            type = attrib.Value;
                            break;
                        case "color":
                            values = attrib.Value.Split(',');
                            color = new Vector3(Convert.ToSingle(values[0]) / 255.0f, Convert.ToSingle(values[1]) / 255.0f, Convert.ToSingle(values[2]) / 255.0f);
                            break;
                        case "dir":
                            values = attrib.Value.Split(',');
                            dir = new Vector3(Convert.ToSingle(values[0]), Convert.ToSingle(values[1]), Convert.ToSingle(values[2]));
                            dir.Normalize();
                            break;
                        default:
                            break;
                    }
                }
            }
            catch (Exception)
            {
                System.Windows.Forms.MessageBox.Show("Failed to load light: " + src);
            }
        }
コード例 #6
0
ファイル: Asset.cs プロジェクト: RonOHara-GG/WebGLRenderer
 public Asset(Scene s, string n, string sr)
 {
     scene = s;
     name = n;
     src = sr;
 }
コード例 #7
0
 public UpdatePass(Scene scene, string name, string src)
     : base(scene, name, src)
 {
 }
コード例 #8
0
ファイル: Mesh.cs プロジェクト: RonOHara-GG/WebGLRenderer
        public Mesh(Scene scene, string name, string src)
            : base(scene, name, src)
        {
            try
            {
                List<Vector3> posArray = new List<Vector3>();
                List<Vector3> nrmArray = new List<Vector3>();
                List<Vector2> uvArray = new List<Vector2>();

                XmlDocument meshXML = new XmlDocument();
                meshXML.Load(src);
                triangleCount = Convert.ToInt32(meshXML.DocumentElement.Attributes.GetNamedItem("triangleCount").Value);

                foreach( XmlNode child in meshXML.DocumentElement.ChildNodes )
                {
                    if (child.NodeType == XmlNodeType.Element)
                    {
                        if (child.Name == "verts")
                        {
                            vertCount = Convert.ToInt32(child.Attributes.GetNamedItem("count").Value);
                            vertFormat = child.Attributes.GetNamedItem("format").Value;

                            foreach( XmlNode vertPiece in child.ChildNodes )
                            {
                                if (vertPiece.NodeType == XmlNodeType.Element)
                                {
                                    if (vertPiece.Name == "positions")
                                    {
                                        foreach( XmlNode position in vertPiece.ChildNodes )
                                        {
                                            if (position.NodeType == XmlNodeType.Element)
                                            {
                                                if (position.Name == "v3")
                                                {
                                                    string[] posVals = position.InnerText.Split(',');
                                                    Vector3 pos = new Vector3(Convert.ToSingle(posVals[0]), Convert.ToSingle(posVals[1]), Convert.ToSingle(posVals[2]));
                                                    posArray.Add(pos);
                                                }
                                            }
                                        }
                                    }
                                    else if (vertPiece.Name == "normals")
                                    {
                                        foreach( XmlNode normal in vertPiece.ChildNodes )
                                        {
                                            if (normal.NodeType == XmlNodeType.Element)
                                            {
                                                if (normal.Name == "v3")
                                                {
                                                    string[] vals = normal.InnerText.Split(',');
                                                    Vector3 nrm = new Vector3(Convert.ToSingle(vals[0]), Convert.ToSingle(vals[1]), Convert.ToSingle(vals[2]));
                                                    nrmArray.Add(nrm);
                                                }
                                            }
                                        }
                                    }
                                    else if (vertPiece.Name == "texcoords")
                                    {
                                        foreach( XmlNode uvs in vertPiece.ChildNodes )
                                        {
                                            if (uvs.NodeType == XmlNodeType.Element)
                                            {
                                                if (uvs.Name == "v2")
                                                {
                                                    string[] vals = uvs.InnerText.Split(',');
                                                    Vector2 uv = new Vector2(Convert.ToSingle(vals[0]), Convert.ToSingle(vals[1]));
                                                    uvArray.Add(uv);
                                                }
                                            }
                                        }
                                    }
                                }
                            }

                            List<float> interleaved = new List<float>();
                            int vertexSize = 0;
                            switch (this.vertFormat)
                            {
                                case "P3":
                                    for (var j = 0; j < this.vertCount; j++)
                                    {
                                        interleaved.Add(posArray[j].X);
                                        interleaved.Add(posArray[j].Y);
                                        interleaved.Add(posArray[j].Z);
                                    }
                                    vertexSize = 12;
                                    break;
                                case "P3N3":
                                    for (var j = 0; j < this.vertCount; j++)
                                    {
                                        interleaved.Add(posArray[j].X);
                                        interleaved.Add(posArray[j].Y);
                                        interleaved.Add(posArray[j].Z);
                                        interleaved.Add(nrmArray[j].X);
                                        interleaved.Add(nrmArray[j].Y);
                                        interleaved.Add(nrmArray[j].Z);
                                    }
                                    vertexSize = 24;
                                    break;
                                case "P3T2":
                                    for (var j = 0; j < this.vertCount; j++)
                                    {
                                        interleaved.Add(posArray[j].X);
                                        interleaved.Add(posArray[j].Y);
                                        interleaved.Add(posArray[j].Z);
                                        interleaved.Add(uvArray[j].X);
                                        interleaved.Add(uvArray[j].Y);
                                    }
                                    vertexSize = 20;
                                    break;
                                default:
                                    System.Windows.Forms.MessageBox.Show("unsupported vertex format: " + this.vertFormat);
                                    break;
                            }

                            GL.GenBuffers(1, out vb);
                            GL.BindBuffer(BufferTarget.ArrayBuffer, vb);
                            GL.BufferData(BufferTarget.ArrayBuffer, (IntPtr)(interleaved.Count * vertexSize), interleaved.ToArray(), BufferUsageHint.StaticDraw);
                        }
                        else if (child.Name == "indices")
                        {
                            string[] vals = child.InnerText.Split(',');
                            List<UInt16> indices = new List<UInt16>();
                            foreach( string val in vals )
                            {
                                indices.Add(Convert.ToUInt16(val));
                            }

                            GL.GenBuffers(1, out ib);
                            GL.BindBuffer(BufferTarget.ElementArrayBuffer, ib);
                            GL.BufferData(BufferTarget.ElementArrayBuffer, (IntPtr)(indices.Count * 2), indices.ToArray(), BufferUsageHint.StaticDraw);
                        }
                    }
                }

                /*
                if (posArray.Count > 0)
                {
                    GL.GenBuffers(1, out posBuffer);
                    GL.BindBuffer(BufferTarget.ArrayBuffer, posBuffer);
                    GL.BufferData<Vector3>(BufferTarget.ArrayBuffer, new IntPtr(posArray.Count * Vector3.SizeInBytes), posArray.ToArray(), BufferUsageHint.StaticDraw);
                }
                if (nrmArray.Count > 0)
                {
                    GL.GenBuffers(1, out nrmBuffer);
                    GL.BindBuffer(BufferTarget.ArrayBuffer, nrmBuffer);
                    GL.BufferData<Vector3>(BufferTarget.ArrayBuffer, new IntPtr(nrmArray.Count * Vector3.SizeInBytes), nrmArray.ToArray(), BufferUsageHint.StaticDraw);
                }
                if (uvArray.Count > 0)
                {
                    GL.GenBuffers(1, out uvBuffer);
                    GL.BindBuffer(BufferTarget.ArrayBuffer, uvBuffer);
                    GL.BufferData<Vector2>(BufferTarget.ArrayBuffer, new IntPtr(uvArray.Count * Vector2.SizeInBytes), uvArray.ToArray(), BufferUsageHint.StaticDraw);
                }

                GL.GenVertexArrays(1, out vb);
                GL.BindVertexArray(vb);

                GL.EnableVertexAttribArray(0);
                GL.BindBuffer(BufferTarget.ArrayBuffer, posBuffer);
                GL.VertexAttribPointer(0, 3, VertexAttribPointerType.Float, false, Vector3.SizeInBytes, 0);

                int stream = 1;
                if (nrmBuffer > 0)
                {
                    GL.EnableVertexAttribArray(stream);
                    GL.BindBuffer(BufferTarget.ArrayBuffer, nrmBuffer);
                    GL.VertexAttribPointer(0, 3, VertexAttribPointerType.Float, true, Vector3.SizeInBytes, 0);
                    stream++;
                }
                if (uvBuffer > 0)
                {
                    GL.EnableVertexAttribArray(stream);
                    GL.BindBuffer(BufferTarget.ArrayBuffer, uvBuffer);
                    GL.VertexAttribPointer(0, 2, VertexAttribPointerType.Float, false, Vector2.SizeInBytes, 0);
                    stream++;
                }

                GL.BindBuffer(BufferTarget.ElementArrayBuffer, ib);
                GL.BindVertexArray(0);
                 * */

            }
            catch(Exception)
            {
                System.Windows.Forms.MessageBox.Show("Failed to load mesh: " + src);
            }
        }
コード例 #9
0
        public RenderObject(Scene scene, string name, string src)
            : base(scene, name, src)
        {
            textures = new List<Texture>();

            pos = new Vector3(0, 0, 0);
            rot = new Quaternion(0, 0, 0, 1.0f);
            scale = new Vector3(1.0f, 1.0f, 1.0f);
            worldMatrix = new Matrix4();

            try
            {
                XmlDocument roXML = new XmlDocument();
                roXML.Load(src);

                foreach( XmlAttribute attrib in roXML.DocumentElement.Attributes )
                {
                    if( attrib.Name == "pos")
                    {
                        string[] values = attrib.Value.Split(',');
                        pos = new Vector3(Convert.ToSingle(values[0]), Convert.ToSingle(values[1]), Convert.ToSingle(values[2]));
                    }
                    else if( attrib.Name == "rot")
                    {
                        string[] values = attrib.Value.Split(',');
                        rot = new Quaternion(Convert.ToSingle(values[0]), Convert.ToSingle(values[1]), Convert.ToSingle(values[2]), Convert.ToSingle(values[3]));
                    }
                    else if( attrib.Name == "scale" )
                    {
                        string[] values = attrib.Value.Split(',');
                        scale = new Vector3(Convert.ToSingle(values[0]), Convert.ToSingle(values[1]), Convert.ToSingle(values[2]));
                    }
                    else if( attrib.Name == "update" )
                    {
                        updateCallback = Program.TheForm.FindUpdateFunction(attrib.Value);
                    }
                }

                foreach( XmlNode child in roXML.DocumentElement.ChildNodes )
                {
                    if( child.NodeType == XmlNodeType.Element )
                    {
                        string nodeName = child.Attributes.GetNamedItem("name").Value;
                        string nodeSrc = child.Attributes.GetNamedItem("src").Value;
                        if (child.Name == "mesh")
                        {
                            mesh = scene.GetMesh(nodeName, nodeSrc);
                        }
                        else if (child.Name == "shader")
                        {
                            shader = scene.GetShader(nodeName, nodeSrc);
                        }
                        else if (child.Name == "texture")
                        {
                            Texture tex = null;
                            if( nodeSrc == "frameBuffer" )
                            {
                                var depthTexture = false;
                                XmlAttribute dtAttr = (XmlAttribute)child.Attributes.GetNamedItem("depthTexture");
                                if( dtAttr != null )
                                    depthTexture = (dtAttr.Value == "true");

                                FrameBuffer fb = scene.GetFrameBuffer(nodeName, null);
                                if( fb != null )
                                {
                                    if( depthTexture )
                                        tex = fb.depthTexture;
                                    else
                                        tex = fb.colorTexture;
                                }
                            }
                            else
                            {
                                // Normal texture
                                tex = scene.GetTexture(nodeName, nodeSrc);
                            }

                            if( tex != null )
                            {
                                var texIndex = 0;
                                XmlAttribute index = (XmlAttribute)child.Attributes.GetNamedItem("texIndex");
                                if( index != null)
                                    texIndex = Convert.ToInt32(index.Value);

                                while (textures.Count <= texIndex)
                                    textures.Add(null);
                                textures[texIndex] = tex;
                            }
                        }
                        else if (child.Name == "shadowCamera")
                        {
                            shadowCamera = scene.GetCamera(nodeName, nodeSrc);
                        }
                    }
                }
            }
            catch(Exception e)
            {
                System.Windows.Forms.MessageBox.Show("Failed to load render object: " + src + "\r\n" + e.Message);
            }

            UpdateWorldMatrix();
        }
コード例 #10
0
ファイル: Camera.cs プロジェクト: RonOHara-GG/WebGLRenderer
        public Camera(Scene scene, string name, string src)
            : base(scene, name, src)
        {
            pos = new Vector3();
            target = new Vector3();
            up = new Vector3(0.0f, 1.0f, 0.0f);
            proj = new Matrix4();
            view = Matrix4.Identity;

            try
            {
                XmlDocument cameraXML = new XmlDocument();
                cameraXML.Load(src);

                foreach( XmlAttribute attrib in cameraXML.DocumentElement.Attributes )
                {
                    if( attrib.Name == "ortho")
                        ortho = (attrib.Value == "true");
                    else if( attrib.Name == "fov")
                        fov = Convert.ToSingle(attrib.Value);
                    else if( attrib.Name == "near")
                        near = Convert.ToSingle(attrib.Value);
                    else if( attrib.Name == "far")
                        far = Convert.ToSingle(attrib.Value);
                    else if( attrib.Name == "left")
                        left = Convert.ToSingle(attrib.Value);
                    else if( attrib.Name == "right")
                        right = Convert.ToSingle(attrib.Value);
                    else if( attrib.Name == "top")
                        top = Convert.ToSingle(attrib.Value);
                    else if( attrib.Name == "bottom")
                        bottom = Convert.ToSingle(attrib.Value);
                    else if( attrib.Name == "static")
                        isStatic = (attrib.Value == "true");
                    else if( attrib.Name == "shadowDistance")
                        shadowDistance = Convert.ToSingle(attrib.Value);
                    else if( attrib.Name == "identityView")
                        identityView = (attrib.Value == "true");
                }

                foreach( XmlNode child in cameraXML.DocumentElement.ChildNodes )
                {
                    if (child.NodeType == XmlNodeType.Element)
                    {
                        if (child.Name == "position")
                        {
                            var posX = Convert.ToSingle(child.Attributes.GetNamedItem("x").Value);
                            var posY = Convert.ToSingle(child.Attributes.GetNamedItem("y").Value);
                            var posZ = Convert.ToSingle(child.Attributes.GetNamedItem("z").Value);
                            pos = new Vector3(posX, posY, posZ);
                        }
                        else if (child.Name == "lookAt")
                        {
                            var lookAtX = Convert.ToSingle(child.Attributes.GetNamedItem("x").Value);
                            var lookAtY = Convert.ToSingle(child.Attributes.GetNamedItem("y").Value);
                            var lookAtZ = Convert.ToSingle(child.Attributes.GetNamedItem("z").Value);
                            target = new Vector3(lookAtX, lookAtY, lookAtZ);
                        }
                        else if (child.Name == "up")
                        {
                            var upX = Convert.ToSingle(child.Attributes.GetNamedItem("x").Value);
                            var upY = Convert.ToSingle(child.Attributes.GetNamedItem("y").Value);
                            var upZ = Convert.ToSingle(child.Attributes.GetNamedItem("z").Value);
                            up = new Vector3(upX, upY, upZ);
                        }
                        else if (child.Name == "shadowLight")
                        {
                            shadowLight = scene.GetLight(child.Attributes.GetNamedItem("name").Value, child.Attributes.GetNamedItem("src").Value);
                        }
                    }
                }
            }
            catch(Exception )
            {
                System.Windows.Forms.MessageBox.Show("Failed to load camera: " + src);
            }

            if( shadowLight != null )
            {
                shadowCamera = true;
                switch( shadowLight.type )
                {
                    case "dir":
                        Vector3 tempVec = Vector3.Multiply(shadowLight.dir, -shadowDistance);
                        pos = target;
                        pos = Vector3.Add(target, tempVec);
                        break;
                    default:
                        break;
                }
            }

            if( isStatic )
                BuildProj(1);
        }
コード例 #11
0
        public RenderPass(Scene scene, string name, string src)
            : base(scene, name, src)
        {
            // Load the source
            try
            {
                XmlDocument rpXML = new XmlDocument();
                rpXML.Load(src);

                // Get the attribute properties
                foreach( XmlAttribute attrib in rpXML.DocumentElement.Attributes )
                {
                    switch( attrib.Name )
                    {
                        case "sortMode":
                            sortMode = attrib.Value;
                            break;
                        case "clearMode":
                            string clearMode = attrib.Value;
                            clearColor = (clearMode.IndexOf("color") >= 0);
                            clearDepth = (clearMode.IndexOf("depth") >= 0);
                            clearStencil = (clearMode.IndexOf("stencil") >= 0);
                            break;
                        case "clearDepth":
                            clearDepthValue = Convert.ToSingle(attrib.Value);
                            break;
                        case "clearStencil":
                            clearStencilValue = Convert.ToSingle(attrib.Value);
                            break;
                        case "clearColor":
                            string[] clearColors = attrib.Value.Split(',');
                            clearColorRed = Convert.ToSingle(clearColors[0]) / 255.0f;
                            clearColorGreen = Convert.ToSingle(clearColors[1]) / 255.0f;
                            clearColorBlue = Convert.ToSingle(clearColors[2]) / 255.0f;
                            break;
                        default:
                            break;
                    }
                }

                foreach( XmlNode child in rpXML.DocumentElement.ChildNodes )
                {
                    if (child.NodeType == XmlNodeType.Element)
                    {
                        string objName = child.Attributes.GetNamedItem("name").Value;
                        string objSrc = child.Attributes.GetNamedItem("src").Value;
                        if (child.Name == "viewport")
                        {
                            viewport = scene.GetViewport(objName, objSrc);
                        }
                        else if (child.Name == "camera")
                        {
                            camera = scene.GetCamera(objName, objSrc);
                        }
                        else if (child.Name == "frameBuffer")
                        {
                            frameBuffer = scene.GetFrameBuffer(objName, objSrc);
                        }
                        else if (child.Name == "overrideShader")
                        {
                            overrideShader = scene.GetShader(objName, objSrc);
                        }
                    }
                }
            }
            catch(Exception e)
            {
                System.Windows.Forms.MessageBox.Show("Failed to load render pass: "******"\r\n" + e.Message);
            }
        }
コード例 #12
0
ファイル: Shader.cs プロジェクト: RonOHara-GG/WebGLRenderer
        public Shader(Scene scene, string name, string src)
            : base(scene, name, src)
        {
            lightDirs = new List<int>();
            lightCols = new List<int>();

            try
            {
                XmlDocument shaderXML = new XmlDocument();
                shaderXML.Load(src);
                foreach( XmlAttribute attrib in shaderXML.DocumentElement.Attributes )
                {
                    switch (attrib.Name)
                    {
                        case "maxLights":
                            maxLights = Convert.ToInt32(attrib.Value);
                            break;
                        case "textureCount":
                            textureCount = Convert.ToInt32(attrib.Value);
                            break;
                        default:
                            break;
                    }
                }

                string vertShaderSrc = null;
                string fragShaderSrc = null;

                foreach( XmlNode child in shaderXML.DocumentElement.ChildNodes)
                {
                    if (child.NodeType == XmlNodeType.Element)
                    {
                        string childName = child.Attributes.GetNamedItem("name").Value;
                        string childSrc = child.Attributes.GetNamedItem("src").Value;
                        switch (child.Name)
                        {
                            case "vertshader":
                                vertShaderSrc = Program.LoadTextFile(childSrc);
                                break;
                            case "fragshader":
                                fragShaderSrc = Program.LoadTextFile(childSrc);
                                break;
                        }
                    }
                }

                int vs = CreateShader(ShaderType.VertexShader, vertShaderSrc);
                int fs = CreateShader(ShaderType.FragmentShader, fragShaderSrc);

                if (vs > 0 && fs > 0)
                {
                    shaderProgram = CreateShaderProgram(vs, fs);
                }
            }
            catch(Exception)
            {
                System.Windows.Forms.MessageBox.Show("Failed to load shader: " + src);
            }

            if (shaderProgram > 0)
            {
                mvpUniform = GL.GetUniformLocation(shaderProgram, "uMVPMatrix");
                worldUniform = GL.GetUniformLocation(shaderProgram, "uWorldMatrix");
                viewUniform = GL.GetUniformLocation(shaderProgram, "uViewMatrix");
                projUniform = GL.GetUniformLocation(shaderProgram, "uProjMatrix");
                normalUniform = GL.GetUniformLocation(shaderProgram, "uNormalMatrix");
                shadowMtxUniform = GL.GetUniformLocation(shaderProgram, "uShadowMatrix");
                positionAttribute = GL.GetAttribLocation(shaderProgram, "aVertexPosition");
                normalAttribute = GL.GetAttribLocation(shaderProgram, "aVertexNormal");
                uvAttribute = GL.GetAttribLocation(shaderProgram, "aVertexUV");

                for (var i = 0; i < textureCount; i++ )
                {
                    int texSampler = GL.GetUniformLocation(shaderProgram, "texture" + i);
                    GL.Uniform1(texSampler, i);
                }

                for (var i = 0; i < maxLights; i++)
                {
                    int lightDir = GL.GetUniformLocation(shaderProgram, "uLightDir" + i);
                    int lightCol = GL.GetUniformLocation(shaderProgram, "uLightColor" + i);

                    lightDirs.Add(lightDir);
                    lightCols.Add(lightCol);
                }
            }
        }