Brak opisu
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

RenderGraphBuilder.cs 16KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355
  1. using System;
  2. using System.Diagnostics;
  3. using UnityEngine.Scripting.APIUpdating;
  4. namespace UnityEngine.Rendering.RenderGraphModule
  5. {
  6. /// <summary>
  7. /// Use this struct to set up a new Render Pass.
  8. /// </summary>
  9. [MovedFrom(true, "UnityEngine.Experimental.Rendering.RenderGraphModule", "UnityEngine.Rendering.RenderGraphModule")]
  10. public struct RenderGraphBuilder : IDisposable
  11. {
  12. RenderGraphPass m_RenderPass;
  13. RenderGraphResourceRegistry m_Resources;
  14. RenderGraph m_RenderGraph;
  15. bool m_Disposed;
  16. #region Public Interface
  17. /// <summary>
  18. /// Specify that the pass will use a Texture resource as a color render target.
  19. /// This has the same effect as WriteTexture and also automatically sets the Texture to use as a render target.
  20. /// </summary>
  21. /// <param name="input">The Texture resource to use as a color render target.</param>
  22. /// <param name="index">Index for multiple render target usage.</param>
  23. /// <returns>An updated resource handle to the input resource.</returns>
  24. public TextureHandle UseColorBuffer(in TextureHandle input, int index)
  25. {
  26. CheckResource(input.handle, false);
  27. m_Resources.IncrementWriteCount(input.handle);
  28. m_RenderPass.SetColorBuffer(input, index);
  29. return input;
  30. }
  31. /// <summary>
  32. /// Specify that the pass will use a Texture resource as a depth buffer.
  33. /// </summary>
  34. /// <param name="input">The Texture resource to use as a depth buffer during the pass.</param>
  35. /// <param name="flags">Specify the access level for the depth buffer. This allows you to say whether you will read from or write to the depth buffer, or do both.</param>
  36. /// <returns>An updated resource handle to the input resource.</returns>
  37. public TextureHandle UseDepthBuffer(in TextureHandle input, DepthAccess flags)
  38. {
  39. CheckResource(input.handle, false);
  40. if ((flags & DepthAccess.Write) != 0)
  41. m_Resources.IncrementWriteCount(input.handle);
  42. if ((flags & DepthAccess.Read) != 0)
  43. {
  44. if (!m_Resources.IsRenderGraphResourceImported(input.handle) && m_Resources.TextureNeedsFallback(input))
  45. WriteTexture(input);
  46. }
  47. m_RenderPass.SetDepthBuffer(input, flags);
  48. return input;
  49. }
  50. /// <summary>
  51. /// Specify a Texture resource to read from during the pass.
  52. /// </summary>
  53. /// <param name="input">The Texture resource to read from during the pass.</param>
  54. /// <returns>An updated resource handle to the input resource.</returns>
  55. public TextureHandle ReadTexture(in TextureHandle input)
  56. {
  57. CheckResource(input.handle);
  58. if (!m_Resources.IsRenderGraphResourceImported(input.handle) && m_Resources.TextureNeedsFallback(input))
  59. {
  60. var textureResource = m_Resources.GetTextureResource(input.handle);
  61. // Ensure we get a fallback to black
  62. textureResource.desc.clearBuffer = true;
  63. textureResource.desc.clearColor = Color.black;
  64. // If texture is read from but never written to, return a fallback black texture to have valid reads
  65. // Return one from the preallocated default textures if possible
  66. if (m_RenderGraph.GetImportedFallback(textureResource.desc, out var fallback))
  67. return fallback;
  68. // If not, simulate a write to the texture so that it gets allocated
  69. WriteTexture(input);
  70. }
  71. m_RenderPass.AddResourceRead(input.handle);
  72. return input;
  73. }
  74. /// <summary>
  75. /// Specify a Texture resource to write to during the pass.
  76. /// </summary>
  77. /// <param name="input">The Texture resource to write to during the pass.</param>
  78. /// <returns>An updated resource handle to the input resource.</returns>
  79. public TextureHandle WriteTexture(in TextureHandle input)
  80. {
  81. CheckResource(input.handle);
  82. m_Resources.IncrementWriteCount(input.handle);
  83. m_RenderPass.AddResourceWrite(input.handle);
  84. return input;
  85. }
  86. /// <summary>
  87. /// Specify a Texture resource to read and write to during the pass.
  88. /// </summary>
  89. /// <param name="input">The Texture resource to read and write to during the pass.</param>
  90. /// <returns>An updated resource handle to the input resource.</returns>
  91. public TextureHandle ReadWriteTexture(in TextureHandle input)
  92. {
  93. CheckResource(input.handle);
  94. m_Resources.IncrementWriteCount(input.handle);
  95. m_RenderPass.AddResourceWrite(input.handle);
  96. m_RenderPass.AddResourceRead(input.handle);
  97. return input;
  98. }
  99. /// <summary>
  100. /// Create a new Render Graph Texture resource.
  101. /// This texture will only be available for the current pass and will be assumed to be both written and read so users don't need to add explicit read/write declarations.
  102. /// </summary>
  103. /// <param name="desc">Texture descriptor.</param>
  104. /// <returns>A new transient TextureHandle.</returns>
  105. public TextureHandle CreateTransientTexture(in TextureDesc desc)
  106. {
  107. var result = m_Resources.CreateTexture(desc, m_RenderPass.index);
  108. m_RenderPass.AddTransientResource(result.handle);
  109. return result;
  110. }
  111. /// <summary>
  112. /// Create a new Render Graph Texture resource using the descriptor from another texture.
  113. /// This texture will only be available for the current pass and will be assumed to be both written and read so users don't need to add explicit read/write declarations.
  114. /// </summary>
  115. /// <param name="texture">Texture from which the descriptor should be used.</param>
  116. /// <returns>A new transient TextureHandle.</returns>
  117. public TextureHandle CreateTransientTexture(in TextureHandle texture)
  118. {
  119. var desc = m_Resources.GetTextureResourceDesc(texture.handle);
  120. var result = m_Resources.CreateTexture(desc, m_RenderPass.index);
  121. m_RenderPass.AddTransientResource(result.handle);
  122. return result;
  123. }
  124. /// <summary>
  125. /// Specify a RayTracingAccelerationStructure resource to build during the pass.
  126. /// </summary>
  127. /// <param name="input">The RayTracingAccelerationStructure resource to build during the pass.</param>
  128. /// <returns>An updated resource handle to the input resource.</returns>
  129. public RayTracingAccelerationStructureHandle WriteRayTracingAccelerationStructure(in RayTracingAccelerationStructureHandle input)
  130. {
  131. CheckResource(input.handle);
  132. m_Resources.IncrementWriteCount(input.handle);
  133. m_RenderPass.AddResourceWrite(input.handle);
  134. return input;
  135. }
  136. /// <summary>
  137. /// Specify a RayTracingAccelerationStructure resource to use during the pass.
  138. /// </summary>
  139. /// <param name="input">The RayTracingAccelerationStructure resource to use during the pass.</param>
  140. /// <returns>An updated resource handle to the input resource.</returns>
  141. public RayTracingAccelerationStructureHandle ReadRayTracingAccelerationStructure(in RayTracingAccelerationStructureHandle input)
  142. {
  143. CheckResource(input.handle);
  144. m_RenderPass.AddResourceRead(input.handle);
  145. return input;
  146. }
  147. /// <summary>
  148. /// Specify a Renderer List resource to use during the pass.
  149. /// </summary>
  150. /// <param name="input">The Renderer List resource to use during the pass.</param>
  151. /// <returns>An updated resource handle to the input resource.</returns>
  152. public RendererListHandle UseRendererList(in RendererListHandle input)
  153. {
  154. if(input.IsValid())
  155. m_RenderPass.UseRendererList(input);
  156. return input;
  157. }
  158. /// <summary>
  159. /// Specify a Graphics Buffer resource to read from during the pass.
  160. /// </summary>
  161. /// <param name="input">The Graphics Buffer resource to read from during the pass.</param>
  162. /// <returns>An updated resource handle to the input resource.</returns>
  163. public BufferHandle ReadBuffer(in BufferHandle input)
  164. {
  165. CheckResource(input.handle);
  166. m_RenderPass.AddResourceRead(input.handle);
  167. return input;
  168. }
  169. /// <summary>
  170. /// Specify a Graphics Buffer resource to write to during the pass.
  171. /// </summary>
  172. /// <param name="input">The Graphics Buffer resource to write to during the pass.</param>
  173. /// <returns>An updated resource handle to the input resource.</returns>
  174. public BufferHandle WriteBuffer(in BufferHandle input)
  175. {
  176. CheckResource(input.handle);
  177. m_RenderPass.AddResourceWrite(input.handle);
  178. m_Resources.IncrementWriteCount(input.handle);
  179. return input;
  180. }
  181. /// <summary>
  182. /// Create a new Render Graph Graphics Buffer resource.
  183. /// This Graphics Buffer will only be available for the current pass and will be assumed to be both written and read so users don't need to add explicit read/write declarations.
  184. /// </summary>
  185. /// <param name="desc">Graphics Buffer descriptor.</param>
  186. /// <returns>A new transient GraphicsBufferHandle.</returns>
  187. public BufferHandle CreateTransientBuffer(in BufferDesc desc)
  188. {
  189. var result = m_Resources.CreateBuffer(desc, m_RenderPass.index);
  190. m_RenderPass.AddTransientResource(result.handle);
  191. return result;
  192. }
  193. /// <summary>
  194. /// Create a new Render Graph Graphics Buffer resource using the descriptor from another Graphics Buffer.
  195. /// This Graphics Buffer will only be available for the current pass and will be assumed to be both written and read so users don't need to add explicit read/write declarations.
  196. /// </summary>
  197. /// <param name="graphicsbuffer">Graphics Buffer from which the descriptor should be used.</param>
  198. /// <returns>A new transient GraphicsBufferHandle.</returns>
  199. public BufferHandle CreateTransientBuffer(in BufferHandle graphicsbuffer)
  200. {
  201. var desc = m_Resources.GetBufferResourceDesc(graphicsbuffer.handle);
  202. var result = m_Resources.CreateBuffer(desc, m_RenderPass.index);
  203. m_RenderPass.AddTransientResource(result.handle);
  204. return result;
  205. }
  206. /// <summary>
  207. /// Specify the render function to use for this pass.
  208. /// A call to this is mandatory for the pass to be valid.
  209. /// </summary>
  210. /// <typeparam name="PassData">The Type of the class that provides data to the Render Pass.</typeparam>
  211. /// <param name="renderFunc">Render function for the pass.</param>
  212. public void SetRenderFunc<PassData>(BaseRenderFunc<PassData, RenderGraphContext> renderFunc)
  213. where PassData : class, new()
  214. {
  215. ((RenderGraphPass<PassData>)m_RenderPass).renderFunc = renderFunc;
  216. }
  217. /// <summary>
  218. /// Enable asynchronous compute for this pass.
  219. /// </summary>
  220. /// <param name="value">Set to true to enable asynchronous compute.</param>
  221. public void EnableAsyncCompute(bool value)
  222. {
  223. m_RenderPass.EnableAsyncCompute(value);
  224. }
  225. /// <summary>
  226. /// Allow or not pass culling
  227. /// By default all passes can be culled out if the render graph detects it's not actually used.
  228. /// In some cases, a pass may not write or read any texture but rather do something with side effects (like setting a global texture parameter for example).
  229. /// This function can be used to tell the system that it should not cull this pass.
  230. /// </summary>
  231. /// <param name="value">True to allow pass culling.</param>
  232. public void AllowPassCulling(bool value)
  233. {
  234. m_RenderPass.AllowPassCulling(value);
  235. }
  236. /// <summary>
  237. /// Enable foveated rendering for this pass.
  238. /// </summary>
  239. /// <param name="value">True to enable foveated rendering.</param>
  240. public void EnableFoveatedRasterization(bool value)
  241. {
  242. m_RenderPass.EnableFoveatedRasterization(value);
  243. }
  244. /// <summary>
  245. /// Dispose the RenderGraphBuilder instance.
  246. /// </summary>
  247. public void Dispose()
  248. {
  249. Dispose(true);
  250. }
  251. /// <summary>
  252. /// Allow or not pass culling based on renderer list results
  253. /// By default all passes can be culled out if the render graph detects they are using a renderer list that is empty (does not draw any geometry)
  254. /// In some cases, a pass may not write or read any texture but rather do something with side effects (like setting a global texture parameter for example).
  255. /// This function can be used to tell the system that it should not cull this pass.
  256. /// </summary>
  257. /// <param name="value">True to allow pass culling.</param>
  258. public void AllowRendererListCulling(bool value)
  259. {
  260. m_RenderPass.AllowRendererListCulling(value);
  261. }
  262. /// <summary>
  263. /// Used to indicate that a pass depends on an external renderer list (that is not directly used in this pass).
  264. /// </summary>
  265. /// <param name="input">The renderer list handle this pass depends on.</param>
  266. /// <returns>A <see cref="RendererListHandle"/></returns>
  267. public RendererListHandle DependsOn(in RendererListHandle input)
  268. {
  269. m_RenderPass.UseRendererList(input);
  270. return input;
  271. }
  272. #endregion
  273. #region Internal Interface
  274. internal RenderGraphBuilder(RenderGraphPass renderPass, RenderGraphResourceRegistry resources, RenderGraph renderGraph)
  275. {
  276. m_RenderPass = renderPass;
  277. m_Resources = resources;
  278. m_RenderGraph = renderGraph;
  279. m_Disposed = false;
  280. }
  281. void Dispose(bool disposing)
  282. {
  283. if (m_Disposed)
  284. return;
  285. m_RenderGraph.OnPassAdded(m_RenderPass);
  286. m_Disposed = true;
  287. }
  288. [Conditional("DEVELOPMENT_BUILD"), Conditional("UNITY_EDITOR")]
  289. void CheckResource(in ResourceHandle res, bool checkTransientReadWrite = true)
  290. {
  291. if(RenderGraph.enableValidityChecks)
  292. {
  293. if (res.IsValid())
  294. {
  295. int transientIndex = m_Resources.GetRenderGraphResourceTransientIndex(res);
  296. // We have dontCheckTransientReadWrite here because users may want to use UseColorBuffer/UseDepthBuffer API to benefit from render target auto binding. In this case we don't want to raise the error.
  297. if (transientIndex == m_RenderPass.index && checkTransientReadWrite)
  298. {
  299. Debug.LogError($"Trying to read or write a transient resource at pass {m_RenderPass.name}.Transient resource are always assumed to be both read and written.");
  300. }
  301. if (transientIndex != -1 && transientIndex != m_RenderPass.index)
  302. {
  303. throw new ArgumentException($"Trying to use a transient texture (pass index {transientIndex}) in a different pass (pass index {m_RenderPass.index}).");
  304. }
  305. }
  306. else
  307. {
  308. throw new ArgumentException($"Trying to use an invalid resource (pass {m_RenderPass.name}).");
  309. }
  310. }
  311. }
  312. internal void GenerateDebugData(bool value)
  313. {
  314. m_RenderPass.GenerateDebugData(value);
  315. }
  316. #endregion
  317. }
  318. }