///<param name="filename">Note that filename is required even if passing a byte[], because filename is used as the key to identify duplicate textures</param> ///<param name="source">Whether to load the texture from file path, from an embedded resource in the entry assembly, or from 'textureBytes'</param> ///<param name="textureBytes">Used only if source == TextureLoadSource.FromByteArray</param> public static Surface Create(GLWindow window, string texture_filename, TextureMinFilter minFilter, TextureMagFilter magFilter, TextureLoadSource source, byte[] textureBytes, string frag_shader, bool has_depth, params int[] vertex_attrib_counts) { Surface s = new Surface(); s.window = window; int dims = has_depth? 3 : 2; s.UseDepthBuffer = has_depth; VertexAttributes attribs = VertexAttributes.Create(vertex_attrib_counts); s.vbo = VBO.Create(dims, attribs); s.texture = Texture.Create(texture_filename, null, minFilter, magFilter, source, textureBytes); s.shader = Shader.Create(frag_shader); if (window != null) { window.Surfaces.Add(s); } return(s); }
protected void LoadTexture(string filename, string filenameOfTextureToReplace = null, TextureMinFilter minFilter = TextureMinFilter.Nearest, TextureMagFilter magFilter = TextureMagFilter.Nearest, TextureLoadSource source = TextureLoadSource.FromFilePath, byte[] textureBytes = null) { if (String.IsNullOrEmpty(filename)) { throw new ArgumentException(filename); } if (texture_info.ContainsKey(filename)) { Texture t = texture_info[filename]; TextureIndex = t.TextureIndex; TextureHeightPx = t.TextureHeightPx; TextureWidthPx = t.TextureWidthPx; } else { int num; if (filenameOfTextureToReplace != null && texture_info.ContainsKey(filenameOfTextureToReplace)) { num = texture_info[filenameOfTextureToReplace].TextureIndex; texture_info.Remove(filenameOfTextureToReplace); } else { if (max_textures == -1) { GL.GetInteger(GetPName.MaxTextureImageUnits, out max_textures); } num = next_texture++; if (num == max_textures) //todo: eventually fix this { throw new NotSupportedException("This machine only supports " + num + " texture units, and this GL code isn't smart enough to switch them out yet, sorry."); } } GL.ActiveTexture(TextureUnit.Texture0 + num); int id = GL.GenTexture(); //todo: eventually i'll want to support more than 16 or 32 textures. At that time I'll need to store this ID somewhere. GL.BindTexture(TextureTarget.Texture2D, id); //maybe a list of Scenes which are lists of textures needed, and then i'll bind all those and make sure to track their texture units. Bitmap bmp; if (source == TextureLoadSource.FromEmbedded) { bmp = new Bitmap(Assembly.GetEntryAssembly().GetManifestResourceStream(filename)); } else if (source == TextureLoadSource.FromByteArray) { if (textureBytes == null) { throw new ArgumentNullException(nameof(textureBytes)); } using (System.IO.MemoryStream ms = new System.IO.MemoryStream(textureBytes)){ bmp = new Bitmap(ms); } } else { bmp = new Bitmap(filename); } BitmapData bmp_data = bmp.LockBits(new Rectangle(0, 0, bmp.Width, bmp.Height), ImageLockMode.ReadOnly, System.Drawing.Imaging.PixelFormat.Format32bppArgb); GL.TexImage2D(TextureTarget.Texture2D, 0, PixelInternalFormat.Rgba, bmp_data.Width, bmp_data.Height, 0, OpenTK.Graphics.OpenGL.PixelFormat.Bgra, PixelType.UnsignedByte, bmp_data.Scan0); bmp.UnlockBits(bmp_data); GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMinFilter, (int)minFilter); GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMagFilter, (int)magFilter); TextureIndex = num; TextureHeightPx = bmp.Height; TextureWidthPx = bmp.Width; Texture t = new Texture(); //this one goes into the dictionary as an easy way to store the index/height/width of this filename. t.TextureIndex = num; t.TextureHeightPx = bmp.Height; t.TextureWidthPx = bmp.Width; texture_info.Add(filename, t); } }
protected static Dictionary <string, Texture> texture_info = new Dictionary <string, Texture>(); //the Textures contained herein are used only to store index/height/width ///<param name="filename">Note that filename is required even if passing a byte[], because filename is used as the key to identify duplicate textures</param> ///<param name="textureBytes">Used only if source == TextureLoadSource.FromByteArray</param> public static Texture Create(string filename, string filenameOfTextureToReplace = null, TextureMinFilter minFilter = TextureMinFilter.Nearest, TextureMagFilter magFilter = TextureMagFilter.Nearest, TextureLoadSource source = TextureLoadSource.FromFilePath, byte[] textureBytes = null) { Texture t = new Texture(); t.Sprite = new List <SpriteType>(); t.LoadTexture(filename, filenameOfTextureToReplace, minFilter, magFilter, source, textureBytes); return(t); }