Unity Shader学习日志七:溶解算法-使用噪声图制作火焰

部署运行你感兴趣的模型镜像


前言

本章用shader简单实现火焰,感谢Kerry大佬的教学在这里插入图片描述在这里插入图片描述

一、采样噪声图

//用平移uv的方法采用噪声图
float2 panner=-1.0*_Time.y * _NoiseSpeed + i.uv_noise;
float noiseTex=tex2D(_NoiseMap,panner).r;

panner是混合一个可以平移的uv,噪声图仅alpha通道处理,故只求r即可
在这里插入图片描述
噪声图
在这里插入图片描述

二、采样渐变图

//采样渐变图
float gradientTex=tex2D(_Gradient,i.uv).r;
//alpha通道进行插值混合,混合渐变图,只让噪声下边显示(SoftNess进行软边缘处理)
float finalAlpha=smoothstep((noiseTex-_SoftNess),noiseTex,gradientTex);    

渐变图
在这里插入图片描述

通过smoothstep与噪声图做插值,让渐变图可以下部分显示更多,而上部分显示更少,从而模拟火焰大致样貌,另外也可以让火焰边缘显得更加柔和,_SoftNess正是控制这一部分
在这里插入图片描述
若_SoftNess=0
在这里插入图片描述

三.火焰颜色

代码如下

//火焰颜色部分处理
float gradientEnd=(1.0-gradientTex)*_GradientEnd;//获取外火焰的alpha
float4 mainColor=_FireColor*_EmissIntensity;//主颜色
float endColor=_EndMiss*gradientEnd*noiseTex;//外火焰颜色//分界明显,多乘一个noise

float4 finalColor=float4(mainColor.r,(mainColor.g+endColor),mainColor.b,finalAlpha)*col;//总颜色/col为mainTex颜色

由于外焰和内焰颜色不一样,故分开取色,_EndMiss为外火焰强度,外火焰多乘一个noiseTex是为了让进行扰动不让分层太明显
在这里插入图片描述

四、火焰形状

代码如下

//火焰形状
float noiseDisturbance=(noiseTex*_Offset.x+_Offset.y)*_NoiseIns*0.01*gradientEnd;//噪声扰动,让形状不那么平整
float2 uv_shape=i.uv+noiseDisturbance;
float shape=tex2D(_FireShape,uv_shape).r;

finalColor.a=finalAlpha*shape;

形状图
在这里插入图片描述

听过调整_Offset和_NoiseIns可以调出合适的形状

大功告成
在这里插入图片描述

总代码

Shader "Unlit/Fire_Code"
{
    Properties
    {
        _MainTex ("Texture", 2D) = "white" {}
        _FireColor("FireColor",Color)=(0,0,0,0)
        _EmissIntensity("EmissIntensity",float)=0


        _NoiseMap("NoiseMap",2D)="white"{}
        _NoiseSpeed("NoiseSpeed",float)=0

        _Gradient("Gradient",2D)="white"{}
        _GradientEnd("GradientEnd",float)=0
        _EndMiss("EndMiss",float)=0

        _SoftNess("SoftNess",float)=0

        _FireShape("FireShape",2D)="white"{}
        _NoiseIns("NoiseIns",float)=0
        _Offset("Offset",vector)=(0,0,0,0)
    }
    SubShader
    {
        Tags { "RenderType" = "Transparent"  "Queue" = "Transparent" }
        LOD 100
        Blend SrcAlpha OneMinusSrcAlpha 
        Pass
        {
            CGPROGRAM
            #pragma vertex vert
            #pragma fragment frag
            

            #include "UnityCG.cginc"

            struct appdata
            {
                float4 vertex : POSITION;
                float2 texcoord : TEXCOORD0;
            };

            struct v2f
            {
                float2 uv : TEXCOORD0;
                float2 uv_noise:TEXCOORD1;
                float4 pos : SV_POSITION;
            };

            sampler2D _MainTex;
            float4 _MainTex_ST;
            float4 _FireColor;
            float _EmissIntensity;

            sampler2D _NoiseMap;
            float4 _NoiseMap_ST;
            float _NoiseSpeed;

            sampler2D _Gradient;
            float _GradientEnd;
            float _EndMiss;

            float _SoftNess;//软边缘强度

            sampler2D _FireShape;
            float _NoiseIns;
            vector _Offset;

            v2f vert (appdata v)
            {
                v2f o;
                o.pos = UnityObjectToClipPos(v.vertex);
                o.uv = TRANSFORM_TEX(v.texcoord, _MainTex);
                o.uv_noise = TRANSFORM_TEX(v.texcoord, _NoiseMap); // 噪声纹理坐标变换
                
                return o;
            }

            fixed4 frag (v2f i) : SV_Target
            {
                // sample the texture
                fixed4 col = tex2D(_MainTex, i.uv);
                
                //用平移uv的方法采用噪声图
                float2 panner=-1.0*_Time.y * _NoiseSpeed + i.uv_noise;
                float noiseTex=tex2D(_NoiseMap,panner).r;
                

                //采样渐变图
                float gradientTex=tex2D(_Gradient,i.uv).r;
                float gradientEnd=(1.0-gradientTex)*_GradientEnd;

                //alpha通道进行插值混合,混合渐变图,只让噪声下边显示(SoftNess进行软边缘处理)
                float finalAlpha=smoothstep((noiseTex-_SoftNess),noiseTex,gradientTex);            

                //火焰颜色部分处理
                float4 mainColor=_FireColor*_EmissIntensity;
                float endColor=_EndMiss*gradientEnd*noiseTex;//分界明显,多乘一个noise

                float4 finalColor=float4(mainColor.r,(mainColor.g+endColor),mainColor.b,1.0)*col;

                //火焰形状
                float noiseDisturbance=(noiseTex*_Offset.x+_Offset.y)*_NoiseIns*0.01*gradientEnd;//噪声扰动,让形状不那么平整
                float2 uv_shape=i.uv+noiseDisturbance;
                float shape=tex2D(_FireShape,uv_shape).r;

                finalColor.a=finalAlpha*shape;
                
                //return float4(col.xyz,finalAlpha);
                return finalColor;
            }
            ENDCG
        }
    }
}

本想贴一张ASE连连看,太糊了就算了😓

您可能感兴趣的与本文相关的镜像

ACE-Step

ACE-Step

音乐合成
ACE-Step

ACE-Step是由中国团队阶跃星辰(StepFun)与ACE Studio联手打造的开源音乐生成模型。 它拥有3.5B参数量,支持快速高质量生成、强可控性和易于拓展的特点。 最厉害的是,它可以生成多种语言的歌曲,包括但不限于中文、英文、日文等19种语言

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值