/// <summary> /// Reset the allocated GPU buffer for this BufferObject. /// </summary> /// <param name="size"> /// A <see cref="UInt32"/> that determine the size of the buffer object GPU buffer, in bytes. /// </param> protected void AllocateGpuBuffer(uint size, object data) { // Define buffer object (type, size and hints) Gl.BufferData((int)BufferType, size, data, (int)Hint); // Store GPU buffer size _GpuBufferSize = size; }
/// <summary> /// Creates a standard VBO of type T where the length of the VBO is less than or equal to the length of the data. /// </summary> /// <typeparam name="T">The type of the data being stored in the VBO (make sure it's byte aligned).</typeparam> /// <param name="target">The VBO BufferTarget (usually ArrayBuffer or ElementArrayBuffer).</param> /// <param name="data">The data to store in the VBO.</param> /// <param name="hint">The buffer usage hint (usually StaticDraw).</param> /// <param name="length">The length of the VBO (will take the first 'length' elements from data).</param> /// <returns>The buffer ID of the VBO on success, 0 on failure.</returns> public static uint CreateVBO <T>(BufferTarget target, [InAttribute, OutAttribute] T[] data, BufferUsageHint hint, int position, int length) where T : struct { uint vboHandle = Gl.GenBuffer(); if (vboHandle == 0) { return(0); } Gl.BindBuffer(target, vboHandle); Gl.BufferData <T>(target, position * Marshal.SizeOf(typeof(T)), length * Marshal.SizeOf(typeof(T)), data, hint); Gl.BindBuffer(target, 0); return(vboHandle); }
/// <summary> /// Creates a standard VBO of type T where the length of the VBO is less than or equal to the length of the data. /// </summary> /// <typeparam name="T">The type of the data being stored in the VBO (make sure it's byte aligned).</typeparam> /// <param name="target">The VBO BufferTarget (usually ArrayBuffer or ElementArrayBuffer).</param> /// <param name="data">The data to store in the VBO.</param> /// <param name="hint">The buffer usage hint (usually StaticDraw).</param> /// <param name="length">The length of the VBO (will take the first 'length' elements from data).</param> /// <returns>The buffer ID of the VBO on success, 0 on failure.</returns> public static uint CreateVBO<T>(BufferTarget target, [In, Out] T[] data, BufferUsageHint hint, int length) where T : struct { uint vboHandle = Gl.GenBuffer(); if (vboHandle == 0) return 0; int size = length * Marshal.SizeOf(typeof(T)); #if MEMORY_LOGGER MemoryLogger.AllocateVBO(vboHandle, size); #endif Gl.BindBuffer(target, vboHandle); Gl.BufferData<T>(target, size, data, hint); Gl.BindBuffer(target, 0); return vboHandle; }
/// <summary> /// Creates a standard VBO of type T where the length of the VBO is less than or equal to the length of the data. /// </summary> /// <typeparam name="T">The type of the data being stored in the VBO (make sure it's byte aligned).</typeparam> /// <param name="target">The VBO BufferTarget (usually ArrayBuffer or ElementArrayBuffer).</param> /// <param name="data">The data to store in the VBO.</param> /// <param name="hint">The buffer usage hint (usually StaticDraw).</param> /// <param name="length">The length of the VBO (will take the first 'length' elements from data).</param> /// <returns>The buffer ID of the VBO on success, 0 on failure.</returns> public static uint CreateVBO <T>(BufferTarget target, [InAttribute, OutAttribute] T[] data, BufferUsageHint hint, int position, int length) where T : struct { uint vboHandle = Gl.GenBuffer(); if (vboHandle == 0) { return(0); } int offset = position * Marshal.SizeOf(typeof(T)); int size = length * Marshal.SizeOf(typeof(T)); #if MEMORY_LOGGER MemoryLogger.AllocateVBO(vboHandle, size - offset); #endif Gl.BindBuffer(target, vboHandle); Gl.BufferData <T>(target, offset, size, data, hint); Gl.BindBuffer(target, 0); return(vboHandle); }
/// <summary> /// Actually create this BufferObject resources. /// </summary> /// <param name="ctx"> /// A <see cref="GraphicsContext"/> used for allocating resources. /// </param> /// <exception cref="ArgumentNullException"> /// Exception thrown if <paramref name="ctx"/> is null. /// </exception> /// <exception cref="ArgumentException"> /// Exception thrown if <paramref name="ctx"/> is not current on the calling thread. /// </exception> /// <exception cref="InvalidOperationException"> /// Exception thrown if this BufferObject has not client memory allocated and the hint is different from /// <see cref="BufferObjectHint.StaticCpuDraw"/> or <see cref="BufferObjectHint.DynamicCpuDraw"/>. /// </exception> /// <exception cref="InvalidOperationException"> /// Exception thrown if this BufferObject is currently mapped. /// </exception> protected override void CreateObject(GraphicsContext ctx) { CheckCurrentContext(ctx); if ((ClientBufferAddress == IntPtr.Zero) && ((Hint != BufferObjectHint.StaticCpuDraw) && (Hint != BufferObjectHint.DynamicCpuDraw))) { throw new InvalidOperationException("no client buffer"); } // Determine the client buffer size uint clientBufferSize = _ClientBufferSize; if (ClientBufferAddress != IntPtr.Zero) { clientBufferSize = ClientBufferSize; } Debug.Assert(clientBufferSize > 0); // Buffer must be bound Bind(ctx); if (ctx.Caps.GlExtensions.VertexBufferObject_ARB) { if (IsMapped) { throw new InvalidOperationException("mapped"); } // Define buffer object (type, size and hints) Gl.BufferData((int)BufferType, clientBufferSize, null, (int)Hint); // Store GPU buffer size _GpuBufferSize = clientBufferSize; // Define buffer object contents if (ClientBufferAddress != IntPtr.Zero) { // Provide buffer contents Gl.BufferSubData(BufferType, IntPtr.Zero, _GpuBufferSize, ClientBufferAddress); // Release memory, if it is not required anymore if (_MemoryBufferAutoDispose) { ReleaseClientBuffer(); } } } else { // Discard previous GPU buffer, if any if (_GpuBuffer != null) { _GpuBuffer.Dispose(); } if (ClientBufferAddress == IntPtr.Zero) { // Note: GPU buffer size specified by _ClientBufferSize Debug.Assert(_ClientBufferSize > 0); // Allocate simulated GPU buffer _GpuBuffer = new AlignedMemoryBuffer(_ClientBufferSize, MinimumBufferAlignment); } else { // Let a virtual implementation decide how pass information from the client buffer and the "GPU" buffer UploadClientBuffer(); } // Store GPU buffer size _GpuBufferSize = _GpuBuffer.Size; } // Reset requested client buffer size _ClientBufferSize = 0; }