Unityで360Viewerのようなものを作ろうとしています。
ただし360度全体に画像を貼り付けたいわけではなく、以下のような画像のイメージになります。
用途としては、魚眼カメラを任意の領域に張り付けるためです。
環境は以下になりますが、Unityのバージョン依存等はないと考えております。
Unity: 2021.2
OS: Windows 10
VR: XR Toolkit(Steam VRで利用)
以下が現在実装しているコードになります。Unityのブログを参考にしました。
(コメントアウトしているあたりでなんとかできないのかなと画策しています…)
HLSL
1 2Shader "Custom/360Shader" 3{ 4 Properties 5 { 6 _Tint ("Tint Color", Color) = (.5, .5, .5, .5) 7 [Gamma] _Exposure ("Exposure", Range(0, 8)) = 1.0 8 _MarginColor ("Margin Color", Color) = (.5, .3, 0, 0) 9 10 _HorizontalRotation ("Horizontal Rotation", Range(0, 360)) = 0 11 _VerticalRotation ("Vertical Rotation", Range(0, 360)) = 0 12 13 _Horizontal ("Horizontal", Range(0, 360)) = 120 14 _Vertical ("Vertical", Range(0, 180)) = 120 15 16 [NoScaleOffset] _Tex ("Spherical (HDR)", 2D) = "grey" {} 17 } 18 19 SubShader 20 { 21 Tags 22 { 23 "Queue"="Background" 24 "RenderType"="Background" 25 "PreviewType"="Skybox" 26 } 27 28 Cull Off 29 ZWrite Off 30 31 Pass 32 { 33 CGPROGRAM 34 #pragma vertex vert 35 #pragma fragment frag 36 #pragma target 2.0 37 #pragma multi_compile __ _MAPPING_6_FRAMES_LAYOUT 38 #pragma enable_d3d11_debug_symbols 39 40 #include "UnityCG.cginc" 41 42 sampler2D _Tex; 43 half4 _Tex_HDR; 44 half4 _Tint; 45 half4 _MarginColor; 46 half _Exposure; 47 float _HorizontalRotation; 48 float _VerticalRotation; 49 float _Horizontal; 50 float _Vertical; 51 52 inline float2 ToRadialCoords(float3 coords) 53 { 54 float3 normalizedCoords = normalize(coords); 55 float latitude = acos(normalizedCoords.y); 56 float longitude = atan2(normalizedCoords.z, normalizedCoords.x); 57 float2 sphereCoords = float2(longitude, latitude) * float2(0.5 / UNITY_PI, 1.0 / UNITY_PI); 58 return float2(0.5, 1.0) - sphereCoords; 59 } 60 61 float3 RotateAroundCenter(float3 vertex, float xDegrees, float yDegrees) 62 { 63 float x = xDegrees * UNITY_PI / 360.0; 64 float y = yDegrees * UNITY_PI / 360.0; 65 66 float sinX, cosX, sinY, cosY; 67 68 sincos(x, sinX, cosX); 69 sincos(y, sinY, cosY); 70 71 float2x2 matrixX = float2x2(cosX, -sinX, sinX, cosX); 72 float2x2 matrixY = float2x2(cosY, -sinY, sinY, cosY); 73 float2 mulx = mul(matrixX, vertex.yz); 74 float2 muly = mul(matrixY, vertex.xz); 75 // return mul((vertex.x, mulx.x, mulx.y), float3(muly, vertex.y)); 76 // return float3(vertex.x, mulx.x, mulx.y).xzy; 77 return float3(muly, vertex.y).xzy; 78 } 79 80 81 82 struct appdata 83 { 84 float4 vertex : POSITION; 85 UNITY_VERTEX_INPUT_INSTANCE_ID 86 }; 87 88 struct v2f 89 { 90 float4 vertex : SV_POSITION; 91 float3 texcoord : TEXCOORD0; 92 float4 layout3DScaleAndOffset : TEXCOORD3; 93 UNITY_VERTEX_OUTPUT_STEREO 94 }; 95 96 v2f vert(appdata v) 97 { 98 v2f o; 99 UNITY_SETUP_INSTANCE_ID(v); 100 UNITY_INITIALIZE_VERTEX_OUTPUT_STEREO(o); 101 102 float3 rotated = RotateAroundCenter(v.vertex, _VerticalRotation, _HorizontalRotation); 103 104 o.vertex = UnityObjectToClipPos(rotated); 105 o.texcoord = v.vertex.xyz; 106 107 return o; 108 } 109 110 fixed4 frag(v2f i) : SV_Target 111 { 112 float2 tc = ToRadialCoords(i.texcoord); 113 114 // Cut around the vertical angles with center at 90 degrees 115 if (_Vertical/360 < tc.y) 116 return _MarginColor; 117 tc.y = fmod(tc.y * 360/_Vertical, 1); 118 119 // Cut around the horizontal angles 120 if (tc.x > _Horizontal/360) 121 return _MarginColor; 122 tc.x = fmod(tc.x * 360/_Horizontal, 1); 123 124 half4 tex = tex2D(_Tex, tc); 125 half3 c = DecodeHDR(tex, _Tex_HDR); 126 c = c * _Tint.rgb * unity_ColorSpaceDouble.rgb; 127 c *= _Exposure; 128 return half4(c, 1); 129 } 130 ENDCG 131 } 132 } 133 134 Fallback Off 135} 136
実行結果は以下のような感じになり、垂直方向が意図した結果になっていません。
Shaderを始めたばかりで、知見のある方の意見を頂戴したく、、、
(サンプル画像)
よろしくお願いします。

回答1件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2022/04/21 14:00