Unity Compute Shader 入门
Compute Shader
- 创建Shader
- 设置参数
- Dispatch()
- 获取结果
参考
代码
- ComputeNoise.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69using System.Collections;
using System.Collections.Generic;
using UnityEditor;
using UnityEngine;
[ExecuteInEditMode]
[RequireComponent(typeof(MeshRenderer))]
public class ComputeNoise : MonoBehaviour
{
public int resolution = 512;
public Color color = Color.white;
[Range(0, 100)] public float seed;
private ComputeShader m_computeShader;
private Material m_material;
private RenderTexture m_texture;
void OnEnable()
{
m_material = new Material(Shader.Find("Unlit/Texture"));
GetComponent<MeshRenderer>().material = m_material;
CreateNoise();
}
private void CreateNoise()
{
if (!m_computeShader)
{
#if UNITY_EDITOR
const string computeShaderFile = "Assets/Dev/Shader/Compute/NoiseTexture.compute";
m_computeShader = AssetDatabase.LoadAssetAtPath<ComputeShader>(computeShaderFile);
#endif
}
if (!m_computeShader.HasKernel("CSMain")) return;
int id = m_computeShader.FindKernel("CSMain");
bool bCreateNewTexture = false;
if (m_texture == null)
{
bCreateNewTexture = true;
}
else if (m_texture.width != resolution || m_texture.enableRandomWrite == false)
{
bCreateNewTexture = true;
m_texture.Release();
}
if (bCreateNewTexture)
{
m_texture = new RenderTexture(resolution, resolution, 24);
m_texture.enableRandomWrite = true;
m_texture.Create();
}
m_computeShader.SetTexture(id, "Result", m_texture);
m_computeShader.SetVector("Color", color);
m_computeShader.SetFloat("Seed", seed);
m_computeShader.GetKernelThreadGroupSizes(id, out uint groupNumX, out uint groupNumY, out _);
int numX = Mathf.CeilToInt(resolution / (float) groupNumX);
int numY = Mathf.CeilToInt(resolution / (float) groupNumY);
m_computeShader.Dispatch(id, numX, numY, 1);
if (m_material) m_material.SetTexture("_MainTex", m_texture);
}
} - NoiseTexture.compute
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27#pragma kernel CSMain
float hash2d_value(float2 uv, float seed = 0)
{
uint x = (uint)uv.x << 4;
uint y = (uint)uv.y << 6;
return frac(sin(dot(uv, float2(12.9898 + seed + x * y, 78.233))) * 43758.5453);
}
RWTexture2D<float4> Result;
float3 Color;
float Seed;
[numthreads(8,8,1)]
void CSMain(uint3 id : SV_DispatchThreadID)
{
uint w, h;
Result.GetDimensions(w, h);
if (id.x < w && id.y < h)
{
float2 uv = id.xy / float2(w, h);
float randValue = hash2d_value(uv, Seed);
Result[id.xy] = float4(randValue * Color, 1);
}
}
Unity Compute Shader 入门
https://automask.github.io/wild/2022/06/28/lab/S_Unity_Shader_Compute/