查看: 3436|回复: 6
打印 上一主题 下一主题

[Shaders] 温度云图(温场)实现(转载)

[复制链接]

2722

主题

42

听众

3万

积分

资深设计师

Rank: 7Rank: 7Rank: 7

纳金币
38268
精华
111

最佳新人 活跃会员 热心会员 灌水之王 突出贡献

跳转到指定楼层
楼主
发表于 2014-6-24 11:50:54 |只看该作者 |倒序浏览
最近做一个项目,涉及到温度云图(温场)的问题,论坛里搜索到有一两个发帖问的,但没有具体实现。小弟接触unity3d时间也不长,作了一些学习研究,写了一个简单的shader来实现温度云图。基本原理是给定平面上的几个点的位置和该点的温度信息,然后通过距离比的关系来算出平面上任意点的温度数值,再通过颜色反映出来。(本来还向算法大牛讨教了什么线性差值法,后来决得太复杂,从大牛那里求来了这个距离比的简易方法)

具体看http://dong2008hong.blog.163.com

Shader "Custom/TemperatureField" {
Properties {
_MainTex ("Base (RGB)", 2D) = "white" {}
_Point1("Temperature1",Range(0,100)) = 50
_Point2("Temperature2",Range(0,100)) = 50
_Point3("Temperature3",Range(0,100)) = 50
_Point4("Temperature4",Range(0,100)) = 50
}
SubShader {
AlphaTest Greater 0.1
pass
{
CGPROGRAM
// Upgrade NOTE: excluded shader from DX11, Xbox360, OpenGL ES 2.0 because it uses unsized arrays
#pragma exclude_renderers d3d11 xbox360 gles
#pragma target 3.0
#pragma vertex vert
#pragma fragment frag
#include "UnityCG.cginc"
sampler2D _MainTex;
float4 _MainTex_ST;
float _Point1;
float _Point2;
float _Point3;
float _Point4;
bool computer = false;
struct v2f {
float4 pos:SV_POSITION;
float2 uv:TEXCOORD0;
};
v2f vert(appdata_base v)
{
v2f o;
o.pos=mul(UNITY_MATRIX_MVP,v.vertex);
o.uv = TRANSFORM_TEX(v.texcoord,_MainTex);
return o;
}
float computerTemperature(float2 uv)
{
int plength = 3;
float _midPointX[3] = {0.2,0.8,0.5};
float _midPointY[3] = {0.7,0.9,0.4};
float _midPointT[3] = {10,20,90};
float d1 = sqrt(uv.x*uv.x+uv.y*uv.y);
float d2 = sqrt((1-uv.x)*(1-uv.x)+(1-uv.y)*(1-uv.y));
float d3 = sqrt(uv.x*uv.x+(1-uv.y)*(1-uv.y));
float d4 = sqrt((1-uv.x)*(1-uv.x)+uv.y*uv.y);
float m = 1/d1+1/d2+1/d3+1/d4;
float n = 1/d1*_Point1+1/d2*_Point4+1/d3*_Point3+1/d4*_Point2;
for (int i = 0 ; i < plength ; i++)
{
float dp = sqrt((uv.x-_midPointX)*(uv.x-_midPointX)+(uv.y-_midPointY)*(uv.y-_midPointY));
m = m + 1/dp;
n = n + 1/dp*_midPointT;
}
return n/m;
}
float4 frag(v2f i):COLOR
{
float4 outp;
float4 texCol = tex2D(_MainTex,i.uv);
float temp = computerTemperature(i.uv);
//float temp = computeArray(i.uv);
//图像区域,判定设置为颜色的A > 0.5,输出为材质颜色+光亮值
if(texCol.w>0.5)
{
if(temp >= 60)
outp = float4(1,0,0,1)*(temp-60)/40+float4(1,1,0,1)*(1-(temp-60)/40);
else if(temp >= 30)
outp = float4(1,1,0,1)*(temp-30)/30+float4(0,1,0,1)*(1-(temp-30)/30);
else
outp = float4(0,1,0,1)*(temp)/30+float4(0,0,1,1)*(1-(temp)/30);
}
else
outp = float4(0,0,0,0);
return outp;
}
ENDCG
}
}
FallBack "Diffuse"
}


其中_Point1到4是平面4个顶点上的温度值
_midPointX,_midPointY,_midPointT给出了平面内三个点的位置和温度值,实际应用中可以相应修改和增删

具体的请看:http://dong2008hong.blog.163.com ... 827201311306919750/
分享到: QQ好友和群QQ好友和群 腾讯微博腾讯微博 腾讯朋友腾讯朋友 微信微信
转播转播0 分享淘帖0 收藏收藏0 支持支持0 反对反对0
回复

使用道具 举报

1088

主题

6

听众

6812

积分

高级设计师

Rank: 6Rank: 6

纳金币
2272
精华
0

最佳新人 活跃会员 热心会员 灌水之王 突出贡献

沙发
发表于 2014-6-24 12:49:46 |只看该作者
你的链接给这样 别人怎么看?
回复

使用道具 举报

0

主题

0

听众

6661

积分

高级设计师

Rank: 6Rank: 6

纳金币
168
精华
0

最佳新人 活跃会员 热心会员 灌水之王 突出贡献

板凳
发表于 2014-6-24 13:35:40 |只看该作者
great stuff
回复

使用道具 举报

115

主题

3

听众

5676

积分

高级设计师

Rank: 6Rank: 6

纳金币
7268
精华
0

最佳新人 活跃会员 热心会员 灌水之王 突出贡献

地板
发表于 2014-6-24 14:30:24 |只看该作者
Thanks for this!!!
回复

使用道具 举报

3

主题

1

听众

6189

积分

高级设计师

Rank: 6Rank: 6

纳金币
370
精华
0

最佳新人 活跃会员 热心会员 灌水之王 突出贡献

5#
发表于 2014-6-24 17:33:56 |只看该作者
好歹给点图啊
回复

使用道具 举报

hyui    

1

主题

2

听众

6671

积分

高级设计师

Rank: 6Rank: 6

纳金币
2715
精华
0

最佳新人 活跃会员 热心会员 灌水之王 突出贡献

6#
发表于 2014-6-24 17:52:33 |只看该作者
Thanks for this!
回复

使用道具 举报

wucnj    

1

主题

1

听众

3160

积分

中级设计师

Rank: 5Rank: 5

纳金币
1065
精华
0

最佳新人 活跃会员 热心会员 灌水之王 突出贡献

7#
发表于 2014-6-25 09:10:28 |只看该作者
感谢分享!!!
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

手机版|纳金网 ( 闽ICP备2021016425号-2/3

GMT+8, 2024-11-12 08:20 , Processed in 0.692445 second(s), 32 queries .

Powered by Discuz!-创意设计 X2.5

© 2008-2019 Narkii Inc.

回顶部