Cromon

GlobalBufferManager.cs

Oct 15th, 2012
113
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 2.99 KB | None | 0 0
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Text;
  5. using System.Threading.Tasks;
  6. using DX11 = SlimDX.Direct3D11;
  7. using System.Runtime.InteropServices;
  8.  
  9. namespace Rendering.HLSL
  10. {
  11.     public class GlobalBufferManager
  12.     {
  13.         public GlobalBufferManager(GXDevice dstDevice)
  14.         {
  15.             mDevice = dstDevice as D3D11.GXDevice11;
  16.         }
  17.  
  18.         public T GetGlobalBuffer<T>() where T : struct
  19.         {
  20.             if (mGlobalBuffers.ContainsKey(typeof(T)))
  21.                 return (T)mGlobalBuffers[typeof(T)].BufferObject;
  22.  
  23.             return CreateNewBuffer<T>();
  24.         }
  25.  
  26.         public void UpdateGlobalBuffer<T>(T newValue) where T : struct
  27.         {
  28.             if (mGlobalBuffers.ContainsKey(newValue.GetType()) == false)
  29.                 throw new ArgumentException("Attempted to update a buffer that does not exist. Type: " + newValue.GetType());
  30.  
  31.             mGlobalBuffers[newValue.GetType()].BufferObject = newValue;
  32.             SlimDX.DataStream stream = new SlimDX.DataStream(Marshal.SizeOf(newValue), true, true);
  33.             stream.Write(newValue);
  34.             SlimDX.DataBox box = new SlimDX.DataBox(0, 0, stream);
  35.             mDevice.ImmediateContext.UpdateSubresource(box, mGlobalBuffers[newValue.GetType()].ConstBuffer, 0);
  36.             if (BufferChanged != null)
  37.                 BufferChanged(typeof(T), mGlobalBuffers[newValue.GetType()]);
  38.         }
  39.  
  40.         private T CreateNewBuffer<T>() where T : struct
  41.         {
  42.             var layoutAttribs = (StructLayoutAttribute[])typeof(T).GetCustomAttributes(typeof(StructLayoutAttribute), false);
  43.             if (layoutAttribs.Length == 0 || layoutAttribs[0].Value != LayoutKind.Sequential)
  44.                 throw new ArgumentException("Attempted to create a global buffer on a struct that has not the StructLayout attribute with LayoutKind.Sequential.");
  45.  
  46.             GlobalBufferEntry entry = new GlobalBufferEntry()
  47.             {
  48.                 BufferObject = new T(),
  49.                 ConstBuffer = new DX11.Buffer(mDevice.Device, new DX11.BufferDescription()
  50.                 {
  51.                     BindFlags = DX11.BindFlags.ConstantBuffer,
  52.                     CpuAccessFlags = DX11.CpuAccessFlags.None,
  53.                     OptionFlags = DX11.ResourceOptionFlags.None,
  54.                     SizeInBytes = Marshal.SizeOf(typeof(T)),
  55.                     StructureByteStride = 0,
  56.                     Usage = DX11.ResourceUsage.Default
  57.                 })
  58.             };
  59.  
  60.             mGlobalBuffers.Add(typeof(T), entry);
  61.             return (T)entry.BufferObject;
  62.         }
  63.  
  64.         internal event Action<Type, GlobalBufferEntry> BufferChanged;
  65.  
  66.         private class GlobalBufferEntry
  67.         {
  68.             public object BufferObject { get; set; }
  69.             public DX11.Buffer ConstBuffer { get; set; }
  70.         }
  71.  
  72.         private Dictionary<Type, GlobalBufferEntry> mGlobalBuffers = new Dictionary<Type, GlobalBufferEntry>();
  73.         private D3D11.GXDevice11 mDevice;
  74.     }
  75. }
Advertisement
Add Comment
Please, Sign In to add comment