{"id":16207834,"url":"https://github.com/netpyoung/bs.physically_based_shader_develop_for_unity","last_synced_at":"2025-07-08T08:35:17.003Z","repository":{"id":139619130,"uuid":"335835534","full_name":"netpyoung/bs.physically_based_shader_develop_for_unity","owner":"netpyoung","description":":books:🌔책공부. 유니티 물리 기반 셰이더 개발","archived":false,"fork":false,"pushed_at":"2021-03-04T22:31:48.000Z","size":4786,"stargazers_count":6,"open_issues_count":0,"forks_count":1,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-04-07T20:16:53.086Z","etag":null,"topics":["bs","shader","urp"],"latest_commit_sha":null,"homepage":"","language":"ShaderLab","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/netpyoung.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2021-02-04T04:15:25.000Z","updated_at":"2023-11-11T17:58:12.000Z","dependencies_parsed_at":"2023-07-04T15:37:28.465Z","dependency_job_id":null,"html_url":"https://github.com/netpyoung/bs.physically_based_shader_develop_for_unity","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/netpyoung/bs.physically_based_shader_develop_for_unity","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/netpyoung%2Fbs.physically_based_shader_develop_for_unity","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/netpyoung%2Fbs.physically_based_shader_develop_for_unity/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/netpyoung%2Fbs.physically_based_shader_develop_for_unity/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/netpyoung%2Fbs.physically_based_shader_develop_for_unity/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/netpyoung","download_url":"https://codeload.github.com/netpyoung/bs.physically_based_shader_develop_for_unity/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/netpyoung%2Fbs.physically_based_shader_develop_for_unity/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":264232264,"owners_count":23576807,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["bs","shader","urp"],"created_at":"2024-10-10T10:14:37.277Z","updated_at":"2025-07-08T08:35:16.975Z","avatar_url":"https://github.com/netpyoung.png","language":"ShaderLab","funding_links":[],"categories":[],"sub_categories":[],"readme":"# 유니티 물리 기반 쉐이더 개발\n\n![./physically-based-shader-dev-for-unity-2017.jpg](./physically-based-shader-dev-for-unity-2017.jpg)\n\n- [번역판](http://www.acornpub.co.kr/book/physically-unity-shader)\n- [source](https://github.com/Apress/physically-based-shader-dev-for-unity-2017)\n\nLegacy(Built-in)쉐이더로 작성되어있는데, 어차피 Legacy사용법도 잘 모르고 URP로 곧바로 연습해 보도록 하자.\n\n## URP (Universal Render Pipeline)\n\n- [Dev Weeks: URP 기본 구성과 흐름](https://www.youtube.com/watch?v=QRlz4-pAtpY)\n- [Dev Weeks: URP 셰이더 뜯어보기](https://www.youtube.com/watch?v=9K1uOihvNyg)\n\n``` tree\nPackages/\n|-- Core RP Library/\n|  |-- ShaderLibrary/\n|  |  |-- SpaceTransform.hlsl - 공간변환 행렬. Tangent\u003c-\u003eWorld행렬\n|  |  |-- Common.hlsl - 각종 수학. 텍스쳐 유틸, 뎁스 계산 ..\n|  |  |-- \u003e\u003e\u003e EntityLighting.hlsl - SH, ProveVolume, Lightmap계산 ???\n|  |  |-- ImageBasedLighting - IBL관련 부분(GGX, Anisotropy, ImportanceSample)\n|-- Universal RP/\n|  |-- ShaderLibrary/\n|  |  |-- Core.hlsl - 버텍스 인풋 구조체, 스크린UV계산,Fog계산\n|  |  |-- Lighting.hlsl - 라이트 구조체, diffuse, specular, GI\n|  |  |-- Shadows.hlsl - 쉐도우맵 샘플링, 캐스케이드 계산, ShadowCoord계산 , Shadow Bias계산\n|  |-- Shaders/\n```\n\n## 1장. 셰이더 개발 과정\n\n### Forward\n\n``` ruby\nfor object in objects\n    for light in lights\n        FrameBuffer = LightModel(object, light);\n    end\nend\n\nfor light in lights\n    for object in GetObjectsAffectedByLight(light)\n        FrameBuffer += LightModel(object, light);\n    end\nend\n```\n\n![./forward-v2.png](./forward-v2.png)\n\n라이트 갯수 증가\u003e 연산량 증가\n\n### Deferred\n\n``` ruby\nfor object in objects:\n  GBuffer = GetLightingProperties(object)\nend\n\nfor light in lights\n  Framebuffer += LightModel(GBuffer, light)\nend\n```\n\n![./deferred-v2.png](./deferred-v2.png)\n\n- 반투명 불가\n- URP - 현재(10.3.1) deferred 지원 안함.\n  - [URP 로드맵](https://portal.productboard.com/8ufdwj59ehtmsvxenjumxo82/tabs/3-universal-render-pipeline)\n- [블라인드 렌더러 -  새로운 기법 != 새 장난감](https://kblog.popekim.com/2012/02/blog-post.html)\n\n## 2장. 첫 유니티 셰이더\n\n- [Built-in vs URP](https://docs.unity3d.com/Packages/com.unity.render-pipelines.universal@10.3/manual/universalrp-builtin-feature-comparison.html)\n\n``` txt\nCreate\u003e Rendering\u003e Universal Render Pipeline\u003e Pipeline Asset(Forward Renderer)\n\nAssets/\n|-- UniversalRenderPipelineAsset.asset\n|-- UniversalRenderPipelineAsset_Renderer.asset\n\nProject Settings\u003e Graphics\u003e Scriptable Render Pipeline Settings\u003e UniversalRenderPipelineAsset.asset\n\nUniversalRenderPipelineAsset.asset\u003e Quality\u003e HDR check\n\nProject Settings\u003e Player\u003e Other Settings\u003e Color Space\u003e Linear\n```\n\n- [URP unlit basic shader](https://docs.unity3d.com/Packages/com.unity.render-pipelines.universal@10.3/manual/writing-shaders-urp-basic-unlit-structure.html)\n\n``` hlsl\nTags { \"RenderType\" = \"Opaque\" \"RenderPipeline\" = \"UniversalPipeline\" }\nTags { \"LightMode\" = \"SRPDefaultUnlit\" } // 라이트 모드 태그 기본값\n```\n\n- [URP ShaderLab Pass tags](https://docs.unity3d.com/Packages/com.unity.render-pipelines.universal@10.3/manual/urp-shaders/urp-shaderlab-pass-tags.html)\n\n| LightMode            | URP Support |\n|----------------------|-------------|\n| UniversalForward     | O           |\n| UniversalGBuffer     | O           |\n| UniversalForwardOnly | O           |\n| Universal2D          | O           |\n| ShadowCaster         | O           |\n| DepthOnly            | O           |\n| Meta                 | O           |\n| SRPDefaultUnlit      | O(기본값)   |\n| Always               | X           |\n| ForwardAdd           | X           |\n| PrepassBase          | X           |\n| PrepassFinal         | X           |\n| Vertex               | X           |\n| VertexLMRGBM         | X           |\n| VertexLM             | X           |\n\n## 3장. 그래픽스 파이프라인\n\n``` cs\n// #include \"Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl\"\n// |-- #include \"Packages/com.unity.render-pipelines.core/ShaderLibrary/Common.hlsl\"\n\n// Core RP Library/ShaderLibrary/SpaceTransforms.hlsl\n\n// UNITY_MATRIX_M * (UNITY_MATRIX_VP * positionOS)\n\nfloat4 TransformObjectToHClip(float3 positionOS)\n{\n    // More efficient than computing M*VP matrix product\n    return mul(GetWorldToHClipMatrix(), mul(GetObjectToWorldMatrix(), float4(positionOS, 1.0)));\n}\n```\n\n## 4장. 좌표 공간 변환\n\n| Space |                        |\n|-------|------------------------|\n| WS    | world space            |\n| VS    | view space             |\n| OS    | object space           |\n| CS    | Homogenous clip spaces |\n| TS    | tangent space          |\n| TXS   | texture space          |\n\n| built-in(legacy)         | URP                          |\n|--------------------------|------------------------------|\n| UnityObjectToWorldDir    | TransformObjectToWorldDir    |\n| UnityObjectToWorldNormal | TransformObjectToWorldNormal |\n| UnityWorldSpaceViewDir   | TransformWorldToViewDir      |\n| UnityWorldSpaceLightDir  | x                            |\n\n``` hlsl\nfloat4x4 GetObjectToWorldMatrix() UNITY_MATRIX_M;\nfloat4x4 GetWorldToObjectMatrix() UNITY_MATRIX_I_M;\nfloat4x4 GetWorldToViewMatrix()   UNITY_MATRIX_V;\nfloat4x4 GetWorldToHClipMatrix()  UNITY_MATRIX_VP;\nfloat4x4 GetViewToHClipMatrix()   UNITY_MATRIX_P;\n```\n\n| built-in(legacy)     | URP                    |\n|----------------------|------------------------|\n| UnityObjectToClipPos | TransformObjectToHClip |\n| UnityWorldToClipPos  | TransformWorldToHClip  |\n| UnityViewToClipPos   | TransformWViewToHClip  |\n\n- \u003chttps://github.com/Unity-Technologies/Graphics/tree/master/com.unity.render-pipelines.core\u003e\n- \u003chttps://github.com/Unity-Technologies/Graphics/tree/master/com.unity.render-pipelines.universal\u003e\n\n## 5장. 최초 라이팅 셰이더\n\n``` hlsl\n// #include \"Packages/com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl\"\nstruct Light\n{\n    half3   direction;\n    half3   color;\n    half    distanceAttenuation;\n    half    shadowAttenuation;\n};\n\nLight GetMainLight()\n    light.direction = _MainLightPosition.xyz;\n\nLight GetMainLight(float4 shadowCoord)\n\n// #include \"Packages/com.unity.render-pipelines.core/ShaderLibrary/Macros.hlsl\"\n#define TRANSFORM_TEX(tex, name) ((tex.xy) * name##_ST.xy + name##_ST.zw)\n\n\n// #include \"Packages/com.unity.render-pipelines.core/ShaderLibrary/API/D3D11.hlsl\"\n#define SAMPLE_TEXTURE2D(textureName, samplerName, coord2)                               textureName.Sample(samplerName, coord2)\n```\n\n- [URP - Drawing a texture](https://docs.unity3d.com/Packages/com.unity.render-pipelines.universal@10.3/manual/writing-shaders-urp-unlit-texture.html)\n\n## 6장. 스펙큘러 구현\n\n- TODO 더 많은 광원 지원하기(2 Directional Light)\n- \u003chttps://catlikecoding.com/unity/tutorials/scriptable-render-pipeline/lights/\u003e\n\n## 7장. 서피스 셰이더\n\n- Surface는 URP에서 안쓸꺼라서 Vert/Frag로 구현\n  - 2개 Albedo를 lerp시키는것.\n  - NormapMap적용.\n\n## 8장. 물리 기반 셰이딩이란?\n\n- 빛을 측정하는 방법\n\n|                       | 단위               | 설명                                             |\n|-----------------------|--------------------|--------------------------------------------------|\n| 입체각 Solid Angle    | sr(steradian)      | 단위 구로 어떠한 형상을 사영한 것.               |\n| 파워 Power            | W                  | 여러 방향에서 표면을 통과해 전달되는 에너지 크기 |\n| 일레디안스 Irradiance | E (W/m^2)          | 모든 광선에서 점에 전달되는 빛의 크기            |\n| 레디안스 Radiance     | L_0 (W/(m^2 * sr)) | 하나의 광선에서 점에 전달되는 빛의 크기          |\n\n- 재질을 표현하는 방법\n\n양방향 반사 분포 함수 BRDF Bidirectional Reflectance Distribution Function\n빛이 표면에서 어떻게 반사될지에 대해 정의한 함수.\n\n| BRDF 속성              |                                                                                              |\n|------------------------|----------------------------------------------------------------------------------------------|\n| positivity             | BRDF값은 0이상이다                                                                           |\n| symmetry (reciprocity) | 빛이 들어오는 방향과 반사되는 방향의 값은 동일하다                                           |\n| conservation of energy | 나가는 빛의 양은 들어오는 빛의 양을 넘어설 수 없다(물체가 자체적으로 빛을 발산하지 않는다면) |\n\n## 9장. 물리 기반 셰이더 제작하기\n\n``` hlsl\nhalf3 LightingPhong(half3 lightColor, half3 lightDir, half3 normal, half3 viewDir, half4 specularColor, half3 albedo, half shininess)\n{\n    half NdotL = saturate(dot(normal, lightDir));\n    half3 diffuseTerm = NdotL * albedo * lightColor;\n\n    half3 reflectionDirection = reflect(-lightDir, normal);\n    half3 specularDot = max(0.0, dot(viewDir, reflectionDirection));\n    half3 specular = pow(specularDot, shininess);\n    half3 specularTerm = specularColor.rgb * specular * lightColor;\n\n    return diffuseTerm + specularTerm;\n}\n\n// Lafortune and Willems (1994)\nhalf3 LightingPhongModified(half3 lightColor, half3 lightDir, half3 normal, half3 viewDir, half4 specularColor, half3 albedo, half shininess)\n{\n    half NdotL = saturate(dot(normal, lightDir));\n    half3 diffuseTerm = NdotL * albedo * lightColor;\n\n    half norm = (shininess + 2) / (2 * PI);\n\n    half3 reflectionDirection = reflect(-lightDir, normal);\n    half3 specularDot = max(0.0, dot(viewDir, reflectionDirection));\n\n    half3 specular = norm * pow(specularDot, shininess);\n\n    half3 specularTerm = specularColor.rgb * specular * lightColor;\n\n    return diffuseTerm + specularTerm;\n}\n```\n\n## 10장. 후처리 효과\n\n``` hlsl\n// com.unity.render-pipelines.core/ShaderLibrary/API/D3D11.hlsl\n#define SAMPLE_TEXTURE2D(textureName, samplerName, coord2)                               textureName.Sample(samplerName, coord2)\n#define SAMPLE_DEPTH_TEXTURE(textureName, samplerName, coord2)          SAMPLE_TEXTURE2D(textureName, samplerName, coord2).r\n```\n\n``` hlsl\n// com.unity.render-pipelines.core/ShaderLibrary/API/Common.hlsl\n// Z buffer to linear 0..1 depth (0 at near plane, 1 at far plane).\n// Does NOT correctly handle oblique view frustums.\n// Does NOT work with orthographic projection.\n// zBufferParam = { (f-n)/n, 1, (f-n)/n*f, 1/f }\nfloat Linear01DepthFromNear(float depth, float4 zBufferParam)\n{\n    return 1.0 / (zBufferParam.x + zBufferParam.y / depth);\n}\n\n// Z buffer to linear 0..1 depth (0 at camera position, 1 at far plane).\n// Does NOT work with orthographic projections.\n// Does NOT correctly handle oblique view frustums.\n// zBufferParam = { (f-n)/n, 1, (f-n)/n*f, 1/f }\nfloat Linear01Depth(float depth, float4 zBufferParam)\n{\n    return 1.0 / (zBufferParam.x * depth + zBufferParam.y);\n}\n\n// Z buffer to linear depth.\n// Does NOT correctly handle oblique view frustums.\n// Does NOT work with orthographic projection.\n// zBufferParam = { (f-n)/n, 1, (f-n)/n*f, 1/f }\nfloat LinearEyeDepth(float depth, float4 zBufferParam)\n{\n    return 1.0 / (zBufferParam.z * depth + zBufferParam.w);\n}\n\n// Z buffer to linear depth.\n// Correctly handles oblique view frustums.\n// Does NOT work with orthographic projection.\n// Ref: An Efficient Depth Linearization Method for Oblique View Frustums, Eq. 6.\nfloat LinearEyeDepth(float2 positionNDC, float deviceDepth, float4 invProjParam)\n{\n    float4 positionCS = float4(positionNDC * 2.0 - 1.0, deviceDepth, 1.0);\n    float  viewSpaceZ = rcp(dot(positionCS, invProjParam));\n\n    // If the matrix is right-handed, we have to flip the Z axis to get a positive value.\n    return abs(viewSpaceZ);\n}\n\n// Z buffer to linear depth.\n// Works in all cases.\n// Typically, this is the cheapest variant, provided you've already computed 'positionWS'.\n// Assumes that the 'positionWS' is in front of the camera.\nfloat LinearEyeDepth(float3 positionWS, float4x4 viewMatrix)\n{\n    float viewSpaceZ = mul(viewMatrix, float4(positionWS, 1.0)).z;\n\n    // If the matrix is right-handed, we have to flip the Z axis to get a positive value.\n    return abs(viewSpaceZ);\n}\n```\n\n|        | Built-in      | URP                   |\n|--------|---------------|-----------------------|\n| Camera | Camera:       | RenderPipelineManager |\n|        | OnPreCull     | beginFrameRendering   |\n|        | OnPreRender   | beginCameraRendering  |\n|        | OnPostRender  | endCameraRendering    |\n|        | OnRenderImage | endFrameRendering     |\n\n`Create\u003e Rendering\u003e Universal Render Pipeline\u003e Renderer Feature`\n\n|                            | 자동 생성됨 |                                   |\n|----------------------------|-------------|-----------------------------------|\n| _CameraDepthTexture        | O           | Pipeline Settings\u003e Depth Texture  |\n| _CameraOpaqueTexture       | O           | Pipeline Settings\u003e Opaque Texture |\n| _CameraColorTexture        | ??          |                                   |\n| _CameraDepthNormalsTexture | X           |                                   |\n\n- \u003chttps://docs.unity3d.com/Packages/com.unity.render-pipelines.universal@10.3/manual/integration-with-post-processing.html\u003e\n\n``` txt\n- Camera\u003e Rendering\u003e Post-Processing 체크\n- Hierachy\u003e Volume\u003e Global Volume\n- Global Volume\u003e Volume\u003e Profile\u003e New\n- Global Volume\u003e Volume\u003e Add Override\n```\n\n## 11장. BRDF 누가 누구인가?\n\n- \u003chttps://github.com/wdas/brdf\u003e\n- \u003chttps://github.com/wdas/brdf/downloads\u003e\n- \u003chttps://www.disneyanimation.com/publications/physically-based-shading-at-disney/\u003e\n- [[ 번역 ] Physically-Based Shading at Disney](https://lifeisforu.tistory.com/350)\n\n![./brdf_vectors.png](./brdf_vectors.png)\n\n| 기호 | 설명                              |\n|------|-----------------------------------|\n| N    | 노말                              |\n| H    | 하프벡터 `H = normalize( L + V )` |\n| L    | 라이트(광원)                      |\n| V    | 뷰(카메라)                        |\n| T    | 탄젠트                            |\n| Θ    | (Theta) 방위각                    |\n| Φ    | (Phi)  앙각(올려본각)             |\n\n### BRDF 종류\n\n#### Ashikhmin Shirley 어크먼 셜리\n\n2000 - Michael Ashikhmin \u0026 Peter Shirley - An Anisotropic Phong BRDF Model\n\n퐁 스펙큘러\n\n#### Cook Torrance 쿡토렌스\n\n1982 - Robert L.Cook \u0026 Kenneth E. Torrance - A Reflectance Model For Computer Graphics\n\n미세면이론\n\n#### Oren Nayar 오렌네이어\n\n1994 - Michael Oren \u0026 Shree K. Nayar - Generalization of Lambert’s Reflectance Model\n\n디퓨즈 전용\n\n#### Ward 알드\n\n1992 - Gregory J. Ward - Measuring and modeling anisotropic reflection\n\n경험적 데이터 기반, 거의 사용되지 않음.\n\n#### Disney 디즈니\n\nSIGGRAPH 2012 - Brent Burley - Physically Based Shading at Disney\n\n여러 파라미터\n\n## 12장. BRDF 구현하기\n\n- 참고\n  - [[NDC19] 모바일에서 사용가능한 유니티 커스텀 섭스턴스 PBR 셰이더 만들기](https://www.slideshare.net/dongminpark71/ndc19-pbr-143928930)\n\n### 레퍼런스 BRDF\n\n#### Cook Torrance 레퍼런스\n\n|                                                                                      |                                                                    |\n|--------------------------------------------------------------------------------------|--------------------------------------------------------------------|\n| Physics and Math of Shading by Naty Hoffman                                          | SIGGRAPH every year from 2012 to 2015                              |\n| Real Shading in Unreal Engine 4 by Brian Karis                                       | SIGGRAPH, 2013                                                     |\n| BRDF Explorer (GLSL) - CookTorrance BRDF                                             |                                                                    |\n| Specular BRDF Reference on Brian Karis’ blog                                         | \u003cgraphicrants.blogspot.co.uk/2013/08/specular-brdf-reference.html\u003e |\n| Introduction to BRDF Models by Daniël Jimenez Kwast                                  |                                                                    |\n| A Reflectance Model for Computer Graphics from 1981                                  |                                                                    |\n| Understanding the Masking-Shadowing Function in Microfacet-Based BRDFs by Eric Heitz | SIGGRAPH, 2014 - 미세면이해 추천                                   |\n| Microfacet Models for Refraction through Rough Surfaces                              | EGSR, 2017                                                         |\n\n#### Disney 레퍼런스\n\n|                                                                           |                                                                                    |\n|---------------------------------------------------------------------------|------------------------------------------------------------------------------------|\n| Physically Based Shading at Disney                                        | SIGGRAPH, 2012, by Brent Burley                                                    |\n| BRDF Explorer (GLSL) - Disney BRDF                                        |                                                                                    |\n| Extending the Disney BRDF to a BSDF with Integrated Subsurface Scattering | SIGGRAPH, 2015, by Brent Burley                                                    |\n| Moving Frostbite to Physically Based Rendering                            | SIGGRAPH, 2015, by Sébastien Lagarde and Charlesde Rousiers (only for the Diffuse) |\n\n### 이론 BRDF\n\n#### Cook Torrance 이론\n\n미세면 이론\n|   |                                |              | 관여 벡터 |       |                                                                   |\n|---|--------------------------------|--------------|-----------|-------|-------------------------------------------------------------------|\n| D | Normal `Distribution` Function | 정규분포함수 | (H)       | 양수  | 크기, 밝기, 스펙큘러 모양                                         |\n| F | Fresnel                        | 프레넬       | (L, H)    | 0 ~ 1 | 보는 각도에 따른 반사율과 굴절율                                  |\n| G | Geometry                       | 기하함수     | (L, V, H) |       | 면이 서로 겹쳐서 빛을 차단하는 정도의 근사치를 통계적으로 구한다. |\n\n- NDF (Normal `Distribution` Function)\n  - Beckmann\n  - Phong\n  - GGX\n\n책의 구현에서는\n\n|   |                      |\n|---|----------------------|\n| D | Trowbridge-Reitz GGX |\n| F | Fresnel-Schlick      |\n| G | Smith's Schlick-GGX  |\n\n#### Disney 이론\n\n### 구현 BRDF\n\n#### Cook Torrance 구현\n\n#### Disney 구현\n\n## 13장. 표준 셰이더 후킹\n\n- 16장. 복잡도와 우버셰이더 참조.\n\n``` hlsl\n// com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl\n\nstruct BRDFData\n{\n    half3 albedo;\n    half3 diffuse;\n    half3 specular;\n    half reflectivity;\n    half perceptualRoughness;\n    half roughness;\n    half roughness2;\n    half grazingTerm;\n\n    // We save some light invariant BRDF terms so we don't have to recompute\n    // them in the light loop. Take a look at DirectBRDF function for detailed explaination.\n    half normalizationTerm;     // roughness * 4.0 + 2.0\n    half roughness2MinusOne;    // roughness^2 - 1.0\n};\n```\n\n- [Custom Shader GUI](https://docs.unity3d.com/2021.1/Documentation/Manual/SL-CustomShaderGUI.html)\n- [ShaderGUI: Custom Material Inspectors in Unity 5+](https://www.alanzucconi.com/2016/11/07/shadergui-custom-material-inspectors-unity-5/)\n\n## 14장. 고급 기술 구현\n\n### 반투명 (Translucency)\n\n반투명은 BRDF로 처리하기 곤란.\n|      |                                                   |                                                |\n|------|---------------------------------------------------|------------------------------------------------|\n| BRDF | Bidirectional reflectance distribution function   | 는 빛이 어떤 방향으로 반사가 되는지            |\n| BTDF | Bidirectional transmittance distribution function | 는 빛이 어떤 방향으로 투과가 되는지            |\n| BSDF | Bidirectional scattering distribution function    | 이 둘을 합쳐 빛이 재질과 어떻게 상호작용하는지 |\n\n- TODO 예제에서 2개의 Directional Light사용...\n\n``` hlsl\n// ref: GPG Pro 2\n\n//Translucency\n// - 노말과 라이트의 하프의 역방향에 (물체 뒷부분)\n// - 뷰를 닷연산으로 묶어준다. (확산효과)\n\nfloat thickness = SAMPLE_TEXTURE2D(_Thickness, sampler_Thickness, IN.uv).r;\nfloat3 translucencyLightDir = L + N * _Distortion;\nfloat translucencyDot = pow(saturate(dot(V, -translucencyLightDir)), _Power) * _Scale;\nfloat3 translucency = translucencyDot * thickness * _SubsurfaceColor.rgb;\ndiffuse += translucency;\n```\n\n### IBL\n\n- \u003chttps://github.com/netpyoung/vs.shader-developing-using-unity#50-image-based-lighting\u003e\n\n| Cubemap생성 도구                                         |             |\n|----------------------------------------------------------|-------------|\n| [cmftStudio](https://github.com/dariomanesku/cmftStudio) | BSD 2       |\n| [Knald's Lys](https://www.knaldtech.com/lys/)            | Commercial  |\n| [IBLBaker](https://github.com/derkreature/IBLBaker)      | MIT License |\n| [CubeMapGen](https://gpuopen.com/archived/cubemapgen/)   | old         |\n\n## 15장. 아티스트가 사용할 셰이더 제작\n\n아티스트가 조작하기 편하게\n\n1. 적절한 셋팅 갯수\n2. 적절한 셋팅 네이밍\n3. 상호 작용하는 셋팅값을 위한 문서화\n4. 텍스쳐에 여러 정보(albedo + specular등)을 넣는 경우가 많은데, 명확하게 셋팅값과 셋팅 네이밍을 표시\n5. 여러 범위 혼합사용 피하기(되도록이면 `0 ~ 1`로...)\n\n파라미터 변화값 별로 예제 씬 있으면 좋겠네..\n\n## 16장. 복잡도와 우버셰이더\n\n쉐이더 하나를 이용해서 여러가지 경우를 처리하고 싶은 경우, 필요한 모든 코드를 쉐이더 하나에 집어넣게되면 그게 바로 우버셰이더.\n\n- `if`와 같은 동적분기는 성능저하.\n- `#if`와 같이 전처리기를 이용한, 정적 분기를 이용하여 처리한다.\n\n유니티에서는 키워드를 이용 쉐이더 조합을 편리하게 해주는 기능이 있음.\n\n- [Shader variants and keywords](https://docs.unity3d.com/2021.1/Documentation/Manual/SL-MultipleProgramVariants.html)\n- 총 256개의 글로벌 키워드.\n- 64개의 로컬 키워드.\n\n- `#pragma shader_feature KEYWORD`\n- `#pragma multi_compile KEYWORD`\n\n|                | 게임빌드에 포함     |\n|----------------|---------------------|\n| shader_feature | 사용되는 것만       |\n| multi_compile  | 조합 가능한 모든 것 |\n\n``` txt\n#pragma multi_compile A B C\n#pragma multi_compile D E\n\n조합해서 나올 수 있는 총 갯수: 6개\nA+D, B+D, C+D\nA+E, B+E, C+E\n```\n\n``` hlsl\n[KeywordEnum(Off, On)] _UseNormal(\"Use Normal Map\", Float) = 0 \n#pragma shader_feature _USENORMAL_OFF _USENORMAL_ON\n#if _USENORMAL_ON\n#endif\n\n\n[Toggle] _ModifiedMode(\"Modified?\", Float) = 0\n#pragma shader_feature _MODIFIEDMODE_OFF _MODIFIEDMODE_ON\n#if _MODIFIEDMODE_ON\n#endif\n```\n\n## 17장. 셰이더가 정상작동하지 않을 때\n\n### 일반적 트릭\n\n- shader로 노말값 시각화\n\n``` hlsl\nstruct Attributes\n{\n    float4 positionOS   : POSITION;\n    float3 normalOS     : NORMAL;\n    float4 tangent      : TANGENT;\n    float2 uv           : TEXCOORD0;\n};\n\nstruct Varyings\n{\n    float4 positionHCS      : SV_POSITION;\n    float2 uv               : TEXCOORD0;\n\n    float3 T                : TEXCOORD1;\n    float3 B                : TEXCOORD2;\n    float3 N                : TEXCOORD3;\n\n    float3 positionWS       : TEXCOORD4;\n};\n\n// ----------\ninline void ExtractTBN(in half3 normalOS, in float4 tangent, inout half3 T, inout half3  B, inout half3 N)\n{\n    N = TransformObjectToWorldNormal(normalOS);\n    T = TransformObjectToWorldDir(tangent.xyz);\n    B = cross(N, T) * tangent.w * unity_WorldTransformParams.w;\n}\n\ninline half3 CombineTBN(in half3 tangentNormal, in half3 T, in half3  B, in half3 N)\n{\n    return mul(tangentNormal, float3x3(normalize(T), normalize(B), normalize(N)));\n}\n\nVaryings vert(Attributes IN)\n{\n    //Varyings OUT;\n    Varyings OUT = (Varyings)0;;\n    OUT.positionHCS = TransformObjectToHClip(IN.positionOS.xyz);\n    OUT.uv = TRANSFORM_TEX(IN.uv, _BumpMap);\n\n    ExtractTBN(IN.normalOS, IN.tangent, OUT.T, OUT.B, OUT.N);\n\n    OUT.positionWS = TransformObjectToWorld(IN.positionOS.xyz);\n    return OUT;\n}\n\n// ---------------\nhalf4 frag(Varyings IN) : SV_Target\n{\n#if _ENABLENORMALMAP_ON\n    float3 tangentNormal = UnpackNormal(SAMPLE_TEXTURE2D(_BumpMap, sampler_BumpMap, IN.uv));\n    tangentNormal.xy *= _BumpMapStrength; // BumpMap Strength.\n\n    float3 N = CombineTBN(tangentNormal, IN.T, IN.B, IN.N);\n#else\n    float3 N = normalize(IN.N);\n#endif\n    return half4(N * 0.5 + 0.5, 1);\n}\n```\n\n### 디버깅 도구\n\n- Window\u003e Analysis\u003e Frame Debugger\n- RenderDoc 프로그램\n  - \u003chttps://renderdoc.org/\u003e\n\n### 프로파일링\n\n|                                 |  |\n|---------------------------------|--|\n| 배치 수                         |  |\n| 드로우콜                        |  |\n| SetPass                         |  |\n| Vertex                          |  |\n| 텍스쳐 갯수/메모리 /스위치 횟수 |  |\n| Shadow Casters                  |  |\n| Vertex Buffer Object            |  |\n\n- CPU에 치중? GPU에 치중?\n- Static GameObject 활용 잘하기.\n\n## 18장. 최선 트렌드 따라잡기\n\n### 컨퍼런스\n\n|                 |                              |\n|-----------------|------------------------------|\n| GDC             | GDC Vault 구독 1년 400불정도 |\n| Siggraph        | 1년 45달러                   |\n| Unite           |                              |\n| Digital Dragons | 영상자료 공개                |\n| Eurographics    | 학술위주                     |\n\n### 서적\n\n어렵지만 구입해서 읽어볼 가치 있음.\n\n|          |  |\n|----------|--|\n| GPU Gems |  |\n| ShaderX  |  |\n| GPU PRO  |  |\n| GPU Zen  |  |\n\n### 사이트\n\n- \u003chttp://blog.selfshadow.com/publications/\u003e\n- \u003chttps://labs.unity.com/\u003e\n- \u003chttp://filmicworlds.com/\u003e\n- \u003chttp://aras-p.info/\u003e\n- \u003chttps://seblagarde.wordpress.com/\u003e\n- \u003chttp://c0de517e.blogspot.co.uk/\u003e\n- \u003chttp://blog.tobias-franke.eu/\u003e\n- \u003chttps://bartwronski.com/\u003e\n- \u003chttp://bitsquid.blogspot.co.uk/\u003e\n- \u003chttp://casual-effects.blogspot.co.uk/\u003e\n- \u003chttp://kesen.realtimerendering.com/\u003e\n- \u003chttp://graphicscodex.com\u003e\n- \u003chttps://www.scratchapixel.com/\u003e\n\n## etc\n\n- [Microfacet BRDF](http://www.pbr-book.org/3ed-2018/Reflection_Models/Microfacet_Models.html#)\n- \u003chttp://www.pbr-book.org/\u003e","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnetpyoung%2Fbs.physically_based_shader_develop_for_unity","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fnetpyoung%2Fbs.physically_based_shader_develop_for_unity","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnetpyoung%2Fbs.physically_based_shader_develop_for_unity/lists"}