浏览代码

compute buffer setup - shadow shader

/main
xingwei.zhu 5 年前
当前提交
62426391
共有 8 个文件被更改,包括 244 次插入6 次删除
  1. 2
      Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_computebuffer_utils.cs
  2. 2
      Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_impl.cs
  3. 12
      Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_shader.cs
  4. 2
      Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_shadow_utils.cs
  5. 91
      Runtime/Resources/shaders/computebuffer/UIWidgets_canvas_shadowBox_cb.shader
  6. 9
      Runtime/Resources/shaders/computebuffer/UIWidgets_canvas_shadowBox_cb.shader.meta
  7. 123
      Runtime/Resources/shaders/computebuffer/UIWidgets_canvas_shadowRBox_cb.shader
  8. 9
      Runtime/Resources/shaders/computebuffer/UIWidgets_canvas_shadowRBox_cb.shader.meta

2
Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_computebuffer_utils.cs


bool supportComputeBuffer;
void setupComputeBuffer() {
this.supportComputeBuffer = this._isMainCanvas && CanvasShader.supportComputeBuffer && false;
this.supportComputeBuffer = this._isMainCanvas && CanvasShader.supportComputeBuffer;
}
void initComputeBuffer() {

2
Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_impl.cs


}
D.assert(mesh.vertices.Count > 0);
if (this.supportComputeBuffer && CanvasShader.rshadowShader != cmd.material.shader && CanvasShader.rrshadowShader != cmd.material.shader) {
if (this.supportComputeBuffer) {
this.addMeshToComputeBuffer(mesh.vertices?.data, mesh.uv?.data, mesh.triangles?.data);
cmd.properties.SetBuffer(CmdDraw.vertexBufferId, this.computeBuffer);
cmd.properties.SetBuffer(CmdDraw.indexBufferId, this.indexBuffer);

12
Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_shader.cs


static readonly Material _stencilMat_cb;
static readonly Material _filterMat_cb;
static readonly MaterialByBlendModeStencilComp _strokeAlphaMat_cb;
static readonly Material _shadowBox_cb;
static readonly Material _shadowRBox_cb;
static Shader GetShader(string shaderName) {
var shader = Shader.Find(shaderName);

var texShaderCompute = GetShader("UIWidgets/canvas_tex_cb");
var stencilShaderCompute = GetShader("UIWidgets/canvas_stencil_cb");
var filterShaderCompute = GetShader("UIWidgets/canvas_filter_cb");
var shadowBoxShaderCompute = GetShader("UIWidgets/ShadowBox_cb");
var shadowRBoxShaderCompute = GetShader("UIWidgets/ShadowRBox_cb");
var strokeAlphaShaderCompute = GetShader("UIWidgets/canvas_strokeAlpha_cb");
rshadowShader = shadowBoxShader;

_texMat_cb = new MaterialByBlendModeStencilComp(texShaderCompute);
_stencilMat_cb = new Material(stencilShaderCompute) {hideFlags = HideFlags.HideAndDontSave};
_filterMat_cb = new Material(filterShaderCompute) {hideFlags = HideFlags.HideAndDontSave};
_shadowBox_cb = new Material(shadowBoxShaderCompute) {hideFlags = HideFlags.HideAndDontSave};
_shadowRBox_cb = new Material(shadowRBoxShaderCompute) {hideFlags = HideFlags.HideAndDontSave};
supportComputeBuffer = convexFillShaderCompute.isSupported;
}

}
public static PictureFlusher.CmdDraw fastShadow(PictureFlusher.RenderLayer layer, uiMeshMesh mesh, float sigma,
bool isRect, bool isCircle, float corner, Vector4 bound, uiColor color) {
bool isRect, bool isCircle, float corner, Vector4 bound, uiColor color, bool supportComputeBuffer) {
var mat = _shadowBox;
var mat = supportComputeBuffer ? _shadowBox_cb : _shadowBox;
mat = _shadowRBox;
mat = supportComputeBuffer ? _shadowRBox_cb : _shadowRBox;
}
var props = ObjectPool<MaterialPropertyBlockWrapper>.alloc();

2
Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_shadow_utils.cs


ObjectPool<uiMeshMesh>.release(meshBounds);
ObjectPool<uiMeshMesh>.release(blurMesh);
var mesh = uiMeshMesh.create(state.matrix, vertices, _triangles);
layer.draws.Add(CanvasShader.fastShadow(layer, mesh, sigma, path.isRect, path.isCircle, path.rRectCorner, new Vector4(bound.left, bound.top, bound.right, bound.bottom), paint.color));
layer.draws.Add(CanvasShader.fastShadow(layer, mesh, sigma, path.isRect, path.isCircle, path.rRectCorner, new Vector4(bound.left, bound.top, bound.right, bound.bottom), paint.color, this.supportComputeBuffer));
}
}

91
Runtime/Resources/shaders/computebuffer/UIWidgets_canvas_shadowBox_cb.shader


Shader "UIWidgets/ShadowBox_cb"
{
//originally from http://madebyevan.com/shaders/fast-rounded-rectangle-shadows/
Properties
{
_SrcBlend("_SrcBlend", Int) = 1 // One
_DstBlend("_DstBlend", Int) = 10 // OneMinusSrcAlpha
_StencilComp("_StencilComp", Float) = 8 // - Equal, 8 - Always
}
SubShader
{
ZTest Always
ZWrite Off
Blend [_SrcBlend] [_DstBlend]
Stencil {
Ref 128
Comp [_StencilComp]
}
Pass {
CGPROGRAM
float4 _sb_box;
float4 _viewport;
float _sb_sigma;
float4 _sb_color;
float _mat[9];
struct vdata
{
float2 vertex;
float2 uv;
};
StructuredBuffer<vdata> databuffer;
StructuredBuffer<int> indexbuffer;
int _startVertex;
struct v2f
{
float4 vertex : SV_POSITION;
float2 coord : TEXCOORD0;
};
float4 erf(float4 x)
{
float4 s = sign(x);
float4 a = abs(x);
x = 1.0 + (0.278393 + (0.230389 + 0.078108 * (a * a)) * a) * a;
x = x * x;
return s - s / (x * x);
return s;
}
float boxShadow(float2 lower, float2 upper, float2 pnt, float sigma)
{
float4 query = float4(pnt - lower, pnt - upper);
float4 integral = 0.5 + 0.5 * erf(query * (sqrt(0.5) / sigma));
return (integral.z - integral.x) * (integral.w - integral.y);
}
v2f vert(uint vertex_id: SV_VertexID, uint instance_id: SV_InstanceID){
v2f o;
vdata v = databuffer[indexbuffer[_startVertex + vertex_id]];
float padding = 3.0 * _sb_sigma;
o.coord = lerp(_sb_box.xy - padding, _sb_box.zw + padding, v.vertex.xy);
float3x3 mat = float3x3(_mat[0], _mat[1], _mat[2], _mat[3], _mat[4], _mat[5], 0, 0, 1);
float2 p = mul(mat, float3(o.coord.xy, 1.0)).xy - _viewport.xy;
#if UNITY_UV_STARTS_AT_TOP
o.vertex = float4(2.0 * p.x / _viewport.z - 1.0, 2.0 * p.y / _viewport.w - 1.0, 0, 1);
#else
o.vertex = float4(2.0 * p.x / _viewport.z - 1.0, 1.0 - 2.0 * p.y / _viewport.w, 0, 1);
#endif
return o;
}
float4 frag(v2f i) : SV_TARGET {
float4 fragColor = _sb_color;
fragColor.a = fragColor.a * boxShadow(_sb_box.xy, _sb_box.zw, i.coord, _sb_sigma);
return fragColor;
}
#pragma vertex vert
#pragma fragment frag
ENDCG
}
}
}

9
Runtime/Resources/shaders/computebuffer/UIWidgets_canvas_shadowBox_cb.shader.meta


fileFormatVersion: 2
guid: 444296b3078c944388a1f81cf1821808
ShaderImporter:
externalObjects: {}
defaultTextures: []
nonModifiableTextures: []
userData:
assetBundleName:
assetBundleVariant:

123
Runtime/Resources/shaders/computebuffer/UIWidgets_canvas_shadowRBox_cb.shader


Shader "UIWidgets/ShadowRBox_cb"
{
//originally from http://madebyevan.com/shaders/fast-rounded-rectangle-shadows/
Properties
{
_SrcBlend("_SrcBlend", Int) = 1 // One
_DstBlend("_DstBlend", Int) = 10 // OneMinusSrcAlpha
_StencilComp("_StencilComp", Float) = 8 // - Equal, 8 - Always
}
SubShader
{
ZTest Always
ZWrite Off
Blend [_SrcBlend] [_DstBlend]
Stencil {
Ref 128
Comp [_StencilComp]
}
Pass {
CGPROGRAM
float4 _sb_box;
float4 _viewport;
float _sb_sigma;
float4 _sb_color;
float _sb_corner;
float _mat[9];
struct vdata
{
float2 vertex;
float2 uv;
};
StructuredBuffer<vdata> databuffer;
StructuredBuffer<int> indexbuffer;
int _startVertex;
struct v2f
{
float4 vertex : SV_POSITION;
float2 coord : TEXCOORD0;
};
float gaussian(float x, float sigma)
{
float pi = 3.141592653589793;
return exp(-(x*x) / (2.0 * sigma * sigma)) / (sqrt(2.0 * pi) * sigma);
}
float2 erf(float2 x)
{
float2 s = sign(x);
float2 a = abs(x);
x = 1.0 + (0.278393 + (0.230389 + 0.078108 * (a * a)) * a) * a;
x = x * x;
return s - s / (x * x);
return s;
}
float roundedBoxShadowX(float x, float y, float sigma, float corner, float2 halfSize)
{
float delta = min(halfSize.y - corner - abs(y), 0.0);
float curved = halfSize.x - corner + sqrt(max(0.0, corner * corner - delta * delta));
float2 integral = 0.5 + 0.5 * erf((x + float2(-curved, curved)) * (sqrt(0.5)/sigma));
return integral.y - integral.x;
}
float roundedBoxShadow(float2 lower, float2 upper, float2 pnt, float sigma, float corner)
{
float2 center = (lower + upper) * 0.5;
float2 halfSize = (upper - lower) * 0.5;
pnt -= center;
float low = pnt.y - halfSize.y;
float high = pnt.y + halfSize.y;
float start = clamp(-3.0 * sigma, low, high);
float end = clamp(3.0 * sigma, low, high);
float step = (end - start) / 4.0;
float y = start + step * 0.5;
float value = 0.0;
for(int i=0; i<4;i++)
{
value += roundedBoxShadowX(pnt.x, pnt.y - y, sigma, corner, halfSize) * gaussian(y, sigma) * step;
y += step;
}
return value;
}
v2f vert(uint vertex_id: SV_VertexID, uint instance_id: SV_InstanceID){
v2f o;
vdata v = databuffer[indexbuffer[_startVertex + vertex_id]];
float padding = 3.0 * _sb_sigma;
o.coord = lerp(_sb_box.xy - padding, _sb_box.zw + padding, v.vertex.xy);
float3x3 mat = float3x3(_mat[0], _mat[1], _mat[2], _mat[3], _mat[4], _mat[5], 0, 0, 1);
float2 p = mul(mat, float3(o.coord.xy, 1.0)).xy - _viewport.xy;
#if UNITY_UV_STARTS_AT_TOP
o.vertex = float4(2.0 * p.x / _viewport.z - 1.0, 2.0 * p.y / _viewport.w - 1.0, 0, 1);
#else
o.vertex = float4(2.0 * p.x / _viewport.z - 1.0, 1.0 - 2.0 * p.y / _viewport.w, 0, 1);
#endif
return o;
}
float4 frag(v2f i) : SV_TARGET {
float4 fragColor = _sb_color;
fragColor.a = fragColor.a * roundedBoxShadow(_sb_box.xy, _sb_box.zw, i.coord, _sb_sigma, _sb_corner);
return fragColor;
}
#pragma vertex vert
#pragma fragment frag
ENDCG
}
}
}

9
Runtime/Resources/shaders/computebuffer/UIWidgets_canvas_shadowRBox_cb.shader.meta


fileFormatVersion: 2
guid: 4037f8954a4124abf93d3ff663baa78d
ShaderImporter:
externalObjects: {}
defaultTextures: []
nonModifiableTextures: []
userData:
assetBundleName:
assetBundleVariant:
正在加载...
取消
保存