イラスト、モデリング、Unity、VR関連

unityとかblenderとかvr関連の作業メモ

shader utils

https://qiita.com/keim_at_si/items/c2d1afd6443f3040e900 HSV

 

https://docs.unity3d.com/ja/2017.4/Manual/SL-UnityShaderVariables.html

ビルトインシェーダ変数 

 

プロジェクション行列の逆行列

unity_CameraInvProjection

 

カメラのアスペクト比の取得

https://qiita.com/Santarh/items/428d2e0f33852e6f37b5

//h-色,s-明暗,v-色の強さ
float3 HSVRGB(float h,float s,float v){
	return ((clamp(abs(frac(h+float3(0,2,1)/3.)*6.-3.)-1.,0.,1.)-1.)*s+1.)*v;
}
    
    
//カメラのアスペクト比
float2 Aspect(){
	float4 projectionSpaceUpperRight = float4(1, 1, UNITY_NEAR_CLIP_VALUE, _ProjectionParams.y);
	float4 viewSpaceUpperRight = mul(unity_CameraInvProjection, projectionSpaceUpperRight);
	return float2(viewSpaceUpperRight.x,viewSpaceUpperRight.y);
}

 

//外積-法線方向    
float4 v1 = vg[1].vertex - vg[0].vertex;
float4 v2 = vg[2].vertex - vg[0].vertex;
float3 nor = cross(v1,v2);


//四角の中かどうかを判定する関数
bool IsInBox(float2 p,float2 center,float2 size){
size /= 2;
p = center-p;
float len = max(abs(p.x) - size.x, abs(p.y) - size.y);
return len<0.001 ? true : false;
} float3 CameraDir(){ return UNITY_MATRIX_IT_MV[2].xyz; } void LookAtRot(inout float4 pnt,float3 at){ pnt.w = 1; float3 z = normalize(at - pnt.xyz); float3 x = normalize(cross(float3(0,1,0),z)); float3 y = normalize(cross(z,x)); float4x4 rot = float4x4(x.x, y.x, z.x, 0, x.y, y.y, z.y, 0, x.z, y.z, z.z, 0, 0, 0, 0, 1); pnt = mul(rot,pnt); }
//Position値 float3 GetWorldPos(){ float4x4 mt = unity_ObjectToWorld; return mul(unity_ObjectToWorld,float4(0,0,0,1)); }
//Scale値 float3 GetWorldScale(){ float4x4 mt = unity_ObjectToWorld; return float3(length(float3(mt._m00,mt._m01,mt._m02)), length(float3(mt._m10,mt._m11,mt._m12)), length(float3(mt._m20,mt._m21,mt._m22))); } //Unityの回転はZXYの順番で行われてるらしい http://light11.hatenadiary.com/entry/2019/01/24/223705 float4 Rot(float4 pos,float3 rot){ float rdc = UNITY_PI/180; return RotY(RotX(RotZ(pos,rdc*rot.z),rdc*rot.x),rdc*rot.y); } float4 RotX(float4 pos,float rad){ return mul(float4x4(1,0,0,0, 0,cos(rad),-sin(rad),0, 0,sin(rad),cos(rad),0, 0,0,0,1),pos); } float4 RotY(float4 pos,float rad){ return mul(float4x4(cos(rad),0,sin(rad),0, 0,1,0,0, -sin(rad),0,cos(rad),0, 0,0,0,1),pos); } float4 RotZ(float4 pos,float rad){ return mul(float4x4(cos(rad),-sin(rad),0,0, sin(rad),cos(rad),0,0, 0,0,1,0, 0,0,0,1),pos); } float2 Rot2D(float2 xy,float rad){ rad *= UNITY_PI/180; xy = xy*2-1; float2x2 rot = float2x2(cos(rad),-sin(rad),sin(rad),cos(rad)); xy = mul(rot,xy); return xy/2 + 0.5; } float2 Rot2D(float2 xy,float rad){
//rad *= UNITY_PI/180;
float2x2 rot = float2x2(cos(rad),-sin(rad),sin(rad),cos(rad));
return mul(rot,xy);
} //-1 => 1 => -1 を繰り返す uint tt = trunc(_Time.y); float ft = frac(_Time.y),rt = tt%4; if(rt == 0){ rt = -1 + ft;} else if(rt == 1){ rt = ft;} else if(rt == 2){ rt = 1 - ft;} else if(rt == 3){ rt = -ft;} //0=>1=>0を繰り返す float t_id = frac(_Time.y); t_id = t_id<=0.5 ? t_id*2 : 1 - (t_id-0.5)*2; float4 HSVToRGB(float4 hsv){ float4 K = float4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0); float3 p = abs(frac(hsv.xxx + K.xyz) * 6.0 - K.www); float3 o = hsv.z * lerp(K.xxx, saturate(p - K.xxx), hsv.y); return float4(o.rgb,hsv.a); } float4 RGBToHSV(float4 c){ float4 K = float4(0.0, -1.0 / 3.0, 2.0 / 3.0, -1.0); float4 p = lerp(float4(c.bg, K.wz), float4(c.gb, K.xy), step(c.b, c.g)); float4 q = lerp(float4(p.xyw, c.r), float4(c.r, p.yzx), step(p.x, c.r)); float d = q.x - min(q.w, q.y); float e = 1.0e-10; return float4(abs(q.z + (q.w - q.y) / (6.0 * d + e)), d / (q.x + e), q.x,c.a); } float3 hsv2rgb(float3 hsv){ float4 K = float4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0); float3 p = abs(frac(hsv.xxx + K.xyz) * 6.0 - K.www); return hsv.z * lerp(K.xxx, saturate(p - K.xxx), hsv.y); } float rand(float2 co){ co = fmod(co,10000); return frac(sin(dot(co.xy ,float2(12.9898,78.233))) * 43758.5453); } float GetNumByTime(float digit,float change_frec){ int d = trunc(digit); float tm = _Time.y/changeFrec*Pow(10,d);//小数部をd桁分、整数部に移動 float mx = trunc(tm);//小数部切り捨て return frac(mx/10000);//整数部5桁を小数部に移動,整数部切り捨て } float Pow(float val,int times){ float res = 1; for(int k=0;k<times;k++){ res *= val; } return res; } //階上 int upstairs(int top,int num){ int res = 1; for(int i=0;i<num;i++){ res *= top - i; } return res; //二項係数 //nCk https://mathtrain.jp/nikouteiri int coef(int n ,int k){ return upstairs(n,k) / upstairs(k,k); } //ガンマ関数による階乗 //z>0.5とする //これ合ってるのか分からん //元ネタは以下のc#の実装 //https://rosettacode.org/wiki/Gamma_function#C.23 float Ganma(float z){ z -= 1; float x = 0.99999999999980993; x += 676.5203681218851/(z+1); x += -1259.1392167224028/(z+2); x += 771.32342877765313/(z+3); x += -176.61502916214059/(z+4); x += 12.507343278686905/(z+5); x += -0.13857109526572012/(z+6); x += 9.9843695780195716e-6/(z+7); x += 1.5056327351493116e-7/(z+8); float t = z + 7 + 0.5; return sqrt(2*PI)*pow(t,z+0.5)*pow(NAPIER,-t)*x; }