Unity 绿幕抠图 摄像头抠图 单色抠图


最近迷上了看直播,看到有些主播MM的背景很好看
所以就自己弄了一个非常好看的背景

首先,实验环境
 


背景图
 



最终效果
 


实现原理,就是将图片传入Shader,然后将材质放在一个物体上
Shader代码:
[C#]  纯文本查看  复制代码
?
 
01
02
03
04
05
06
07
08
09
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
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
Shader "我的Shader/自定义/05过滤纯色"
{
         Properties
         {
                 _MainTex( "主纹理" , 2D) = "white" { }
                 _TransparentColourKey( "过滤的颜色" , Color) = (0,0,0,1)
                 _TransparencyToleranceR( "透明公差R" , Range(0.01, 1.0)) = 0.01
                 _TransparencyToleranceG( "透明公差G" , Range(0.01, 1.0)) = 0.01
                 _TransparencyToleranceB( "透明公差B" , Range(0.01, 1.0)) = 0.01
         }
 
         SubShader
         {
                 Pass
                 {
                         Tags{ "RenderType" = "Opaque" "Queue" = "Transparent" }
                         //Tags{ "RenderType" = "Transparent" "Queue" = "Transparent" }
                         Blend SrcAlpha OneMinusSrcAlpha
                         //Blend One One
                         LOD 200
                         CGPROGRAM
 
                         #pragma vertex vert
                         #pragma fragment frag
                         #include "UnityCG.cginc"
 
                         struct vertInput
                         {
                                 float4 pos : POSITION;
                                 float2 uv : TEXCOORD0;
                         };
 
                         struct vertOnput
                         {
                                 float4 pos : SV_POSITION;
                                 float2 uv : TEXCOORD0;
                         };
 
                         vertOnput vert(vertInput input)
                         {
                                 vertOnput output;
                                 output.pos = mul(UNITY_MATRIX_MVP, input.pos);
                                 output.uv = input.uv;
                                 return output;
                         }
 
                         sampler2D _MainTex;
                         sampler2D _Background;
                         float3 _TransparentColourKey;
                         float _TransparencyToleranceR;
                         float _TransparencyToleranceG;
                         float _TransparencyToleranceB;
 
                 /*        float Overlay(float base, float top)
                         {
                                 if (base < 0.5)
                                 {
                                         return 2 * base*top;
                                 }
                                 else
                                 {
                                         return 1 - 2 * (1 - base) * (1 - top);
                                 }
                         }*/
 
                         float4 frag(vertInput input) : COLOR //SV_Target
                         {
                                 float4 color = tex2D(_MainTex, input.uv);
                                 float deltaR = abs(color.r - _TransparentColourKey.r);
                                 float deltaG = abs(color.g - _TransparentColourKey.g);
                                 float deltaB = abs(color.b - _TransparentColourKey.b);
                                 if (deltaR < _TransparencyToleranceR && deltaG < _TransparencyToleranceG && deltaB < _TransparencyToleranceB)
                                 {
                                         return float4(0.0f, 0.0f, 0.0f, 0.0f);
                                 }
                                 else
                                 {
                                         //float4 col = fixed4(0, 0, 0, 0);
                                         //col.r = Overlay(color.r, color2.r);
                                         //col.g = Overlay(color.g, color2.g);
                                         //col.b = Overlay(color.b, color2.b);
                                         //col.a = color.a;               
                                         return color;
                                 }               
                         }
                         ENDCG
                 }
         }
         Fallback "Diffuse"
}



最后新建一个脚本,定义变量
[C#]  纯文本查看  复制代码
?
 
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
public Material m_Material;
[Range(0, 255)]
public float transparentColourR = 1f;
[Range(0, 255)]
public float transparentColourG = 1f;
[Range(0, 255)]
public float transparentColourB = 1f;
[Range(0,100)]
public float transparencyToleranceR = 1f;
[Range(0, 100)]
public float transparencyToleranceG = 1f;
[Range(0, 100)]
public float transparencyToleranceB = 1f;
 
private int devId = 1;
public string deviceName;
private WebCamTexture photoTex;
static int FrameWidth = 1920;
static int FrameHeight = 1080;


在Update里写
[C#]  纯文本查看  复制代码
?
 
1
2
3
4
5
6
7
8
transparentColour.r = transparentColourR / 255;
transparentColour.g = transparentColourG / 255;
transparentColour.b = transparentColourB / 255;
transparentColour.a = 1;
m_Material.SetColor( "_TransparentColourKey" , transparentColour);
m_Material.SetFloat( "_TransparencyToleranceR" , transparencyToleranceR / 100);
m_Material.SetFloat( "_TransparencyToleranceG" , transparencyToleranceG / 100);
m_Material.SetFloat( "_TransparencyToleranceB" , transparencyToleranceB / 100);
m_Material.SetTexture( "_MainTex" , photoTex);



打开摄像头
[C#]  纯文本查看  复制代码
?
 
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
yield return Application.RequestUserAuthorization(UserAuthorization.WebCam);
 
if (Application.HasUserAuthorization(UserAuthorization.WebCam))
{
     WebCamDevice[] devices = WebCamTexture.devices; ;
 
     //如果有后置摄像头,调用后置摄像头   
     for ( int i = 0; i < devices.Length; i++)
     {
         if (!devices[i].isFrontFacing)
         {
             deviceName = devices[i].name;
             break ;
         }
     }
 
     photoTex = new WebCamTexture(deviceName, FrameWidth, FrameHeight, 24);
     photoTex.Play();
}

Demo:
链接:http://pan.baidu.com/s/1i4QuTyl 密码:lee6



评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值