├── .gitattributes ├── .gitmodules ├── README.md ├── abstract.md ├── assets ├── .gitattributes ├── DamagedHelmet │ ├── README.md │ ├── glTF │ │ ├── DamagedHelmet.bin │ │ ├── DamagedHelmet.gltf │ │ ├── Default_AO.jpg │ │ ├── Default_albedo.jpg │ │ ├── Default_emissive.jpg │ │ ├── Default_metalRoughness.jpg │ │ └── Default_normal.jpg │ └── screenshot │ │ └── screenshot.png ├── brdfLUT.png ├── helipad │ ├── charlie │ │ └── sheen.ktx2 │ ├── ggx │ │ └── specular.ktx2 │ └── lambertian │ │ └── diffuse.ktx2 ├── lut_charlie.png ├── lut_ggx.png ├── thisisfine.jpg ├── tyrian.png └── tyrian.sprites ├── attributes ├── attrib1.cxx └── attrib2.cxx ├── cube ├── CMakeLists.txt └── cube.cxx ├── cube2 ├── CMakeLists.txt └── cube2.cxx ├── dxil ├── WaveIntrinsics │ ├── D3D12SM6WaveIntrinsics.cpp │ ├── D3D12SM6WaveIntrinsics.h │ ├── DXSample.cpp │ ├── DXSample.h │ ├── DXSampleHelper.h │ ├── Main.cpp │ ├── UILayer.cpp │ ├── UILayer.h │ ├── WaveIntrinsics.vcxproj │ ├── Win32Application.cpp │ ├── Win32Application.h │ ├── build_shaders.bat │ ├── d3dx12.h │ ├── mag_frag.dxil │ ├── mag_vert.dxil │ ├── readme.md │ ├── shaders.cxx │ ├── stdafx.cpp │ ├── stdafx.h │ ├── wave_frag.dxil │ └── wave_vert.dxil ├── dxil-signing │ ├── CLI11.hpp │ ├── README.md │ ├── dxcapi.h │ ├── dxil-signing.vcxproj │ └── main.cpp ├── dxil.sln ├── nbody │ ├── D3D12nBodyGravity.cpp │ ├── D3D12nBodyGravity.h │ ├── D3D12nBodyGravity.vcxproj │ ├── DXSample.cpp │ ├── DXSample.h │ ├── DXSampleHelper.h │ ├── Main.cpp │ ├── SimpleCamera.cpp │ ├── SimpleCamera.h │ ├── StepTimer.h │ ├── Win32Application.cpp │ ├── Win32Application.h │ ├── build_shaders.bat │ ├── d3dx12.h │ ├── frag.dxil │ ├── geom.dxil │ ├── integrate.dxil │ ├── nbody.vcxproj │ ├── nbody.vcxproj.filters │ ├── nbody.vcxproj.user │ ├── readme.md │ ├── shaders.cxx │ ├── stdafx.cpp │ ├── stdafx.h │ └── vert.dxil ├── semantic.cxx ├── shadertoy │ ├── D3D12HelloConstBuffers.cpp │ ├── D3D12HelloConstBuffers.h │ ├── DXSample.cpp │ ├── DXSample.h │ ├── DXSampleHelper.h │ ├── Main.cpp │ ├── Win32Application.cpp │ ├── Win32Application.h │ ├── band1.dxil │ ├── band2.dxil │ ├── bands.dxil │ ├── build_shaders.bat │ ├── clouds.dxil │ ├── comparison.dxil │ ├── d3dx12.h │ ├── devil.dxil │ ├── fractal.dxil │ ├── hypercomplex.dxil │ ├── menger.dxil │ ├── modulation.dxil │ ├── paint.dxil │ ├── raymarch.dxil │ ├── segment.dxil │ ├── shaders.cxx │ ├── shadertoy.vcxproj │ ├── sphere.dxil │ ├── square.dxil │ ├── stdafx.cpp │ ├── stdafx.h │ ├── thumbnails.dxil │ ├── triangle_grid.dxil │ └── vert.dxil └── tessellation │ ├── BasicTessellationApp.cpp │ ├── Camera.cpp │ ├── Camera.h │ ├── DDSTextureLoader.cpp │ ├── DDSTextureLoader.h │ ├── FrameResource.cpp │ ├── FrameResource.h │ ├── GameTimer.cpp │ ├── GameTimer.h │ ├── GeometryGenerator.cpp │ ├── GeometryGenerator.h │ ├── MathHelper.cpp │ ├── MathHelper.h │ ├── Textures │ ├── bricks.dds │ ├── checkboard.dds │ ├── ice.dds │ └── white1x1.dds │ ├── UploadBuffer.h │ ├── build_shaders.bat │ ├── d3dApp.cpp │ ├── d3dApp.h │ ├── d3dUtil.cpp │ ├── d3dUtil.h │ ├── d3dx12.h │ ├── frag.dxil │ ├── shaders.cxx │ ├── tesc.dxil │ ├── tese.dxil │ ├── tessellation.vcxproj │ └── vert.dxil ├── geom ├── CMakeLists.txt └── geom.cxx ├── images ├── bandlimited.png ├── bandlimited_small.png ├── bands.png ├── bands_small.png ├── bunny.png ├── cpu_flip.png ├── cpu_flip_small.png ├── cube.png ├── cube_small.png ├── debug1.png ├── debug1_small.png ├── debug2.png ├── debug2_small.png ├── dxil_nbody.png ├── dxil_nbody_small.png ├── dxil_shadertoy.png ├── dxil_shadertoy_small.png ├── dxil_tessellation.png ├── dxil_tessellation_small.png ├── dxil_wave.png ├── dxil_wave_small.png ├── egg.png ├── egg_cpu.png ├── egg_small.png ├── geom.png ├── geom_small.png ├── hypercomplex.png ├── hypercomplex_small.png ├── menger.png ├── menger_small.png ├── meshlet1.png ├── meshlet1_small.png ├── meshlet2.png ├── meshlet2_small.png ├── meshlet2_small2.png ├── mini_path_tracer.png ├── mini_path_tracer_small.png ├── modulation.png ├── modulation_small.png ├── nbody.png ├── nbody2.png ├── nbody2_small.png ├── nbody_small.png ├── paint.png ├── paint_small.png ├── particles.png ├── particles_small.png ├── ray_tracing1.png ├── ray_tracing1_small.png ├── ray_tracing2.png ├── ray_tracing2_small.png ├── ray_tracing_tutorial.png ├── ray_tracing_tutorial_small.png ├── raymarch_json.png ├── raymarcher.png ├── raymarcher2.png ├── raymarcher2_small.png ├── raymarcher_small.png ├── segment_tracer.png ├── segment_tracer_small.png ├── shader_flip.png ├── shader_flip_small.png ├── shader_params.png ├── spheres_many_sizes.png ├── sprites.png ├── sprites_small.png ├── square.png ├── square_small.png ├── teapot.png ├── teapot_small.png ├── temple.png ├── viewer.png └── viewer_small.png ├── implicit └── spirv.cxx ├── include ├── appglfw.hxx └── texture.hxx ├── nbody ├── CMakeLists.txt ├── galaxy_20K.bin ├── nbody.cxx └── tipsy.h ├── particles-cuda ├── CMakeLists.txt └── particles-cuda.cxx ├── particles ├── CMakeLists.txt └── particles.cxx ├── push ├── README.md ├── push1.cxx ├── push2.cxx ├── push3.cxx └── push4.cxx ├── shadertoy-cuda ├── CMakeLists.txt ├── adam7.hxx └── shadertoy.cxx ├── shadertoy ├── CMakeLists.txt ├── adam7.hxx └── shadertoy.cxx ├── shadertoy2 ├── CMakeLists.txt ├── adam7.hxx ├── json.hpp ├── scene.json └── shadertoy2.cxx ├── shadertoy3 ├── CMakeLists.txt ├── bunny.json ├── json.hpp └── shadertoy3.cxx ├── sprites ├── CMakeLists.txt └── sprites.cxx ├── sprites2 ├── CMakeLists.txt └── sprites2.cxx ├── teapot ├── CMakeLists.txt ├── teapot.cxx └── teapot.h ├── thirdparty └── stbi.c └── viewer ├── CMakeLists.txt ├── brdf.hxx ├── tonemapping.hxx └── viewer.cxx /.gitattributes: -------------------------------------------------------------------------------- 1 | *.ktx2 filter=lfs diff=lfs merge=lfs -text 2 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "thirdparty/cgltf"] 2 | path = thirdparty/cgltf 3 | url = git@github.com:jkuhlmann/cgltf 4 | [submodule "thirdparty/imgui"] 5 | path = thirdparty/imgui 6 | url = git@github.com:ocornut/imgui 7 | [submodule "thirdparty/stb"] 8 | path = thirdparty/stb 9 | url = git@github.com:nothings/stb 10 | [submodule "RayTracingInVulkan"] 11 | path = RayTracingInVulkan 12 | url = git@github.com:seanbaxter/RayTracingInVulkan 13 | branch = circle 14 | [submodule "mgpu-shaders"] 15 | path = mgpu-shaders 16 | url = git@github.com:seanbaxter/mgpu-shaders 17 | [submodule "thirdparty/thrust"] 18 | path = thirdparty/thrust 19 | url = git@github.com:allisonvacanti/thrust 20 | [submodule "thirdparty/cub"] 21 | path = thirdparty/cub 22 | url = git@github.com:allisonvacanti/cub 23 | -------------------------------------------------------------------------------- /abstract.md: -------------------------------------------------------------------------------- 1 | ## Abstract 2 | 3 | The Circle C++ Shaders extension aims to bring the entire capability of the OpenGL Shading Language (GLSL) into C++ as a first-class embedded language. Write graphics code using Standard C++ and mark interface variables and shader functions with C++ attributes to indicate their role in the raster, ray-tracing or compute pipelines. When the program is compiled, all shader declarations are lowered to the SPIR-V intermediate representation, which is the portable shader storage format for Vulkan and OpenGL programs. 4 | 5 | The guiding vision behind this extension was to make shader programming feel idiomatic to both C++ and GLSL users. Features imported from GLSL include vector component swizzling, layout modifiers, and the complete set of GLSL texture, derivative and utility functions. By embedding these features into a C++ compiler frontend, most C++ language features are now available for shader programming, including classes, templates and concepts. Circle's features go beyond Standard C++, providing shader developers with metaprogramming tools like reflection and user-attributes. 6 | 7 | ## Bio 8 | 9 | Sean Baxter is an independent programmer working on the next-gen C++ compiler, Circle. He previously worked in scientific computing in the Earth Science directorate at JPL, developed molecular dynamics simulations at DE Shaw Research, and hacked on CUDA algorithms at NVIDIA Research. 10 | -------------------------------------------------------------------------------- /assets/.gitattributes: -------------------------------------------------------------------------------- 1 | *.ktx2 filter=lfs diff=lfs merge=lfs -text 2 | -------------------------------------------------------------------------------- /assets/DamagedHelmet/README.md: -------------------------------------------------------------------------------- 1 | # Damaged Helmet 2 | 3 | ## Screenshot 4 | 5 | ![screenshot](screenshot/screenshot.png) 6 | 7 | ## License Information 8 | 9 | Battle Damaged Sci-fi Helmet - PBR by [theblueturtle_](https://sketchfab.com/theblueturtle_), published under a Creative Commons Attribution-NonCommercial license 10 | 11 | https://sketchfab.com/models/b81008d513954189a063ff901f7abfe4 12 | 13 | ## Modifications 14 | 15 | The original model was built on an early draft of glTF 2.0 that did not become final. This new model has been imported and re-exported from Blender to bring it into alignment with the final release glTF 2.0 specification. 16 | -------------------------------------------------------------------------------- /assets/DamagedHelmet/glTF/DamagedHelmet.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/DamagedHelmet/glTF/DamagedHelmet.bin -------------------------------------------------------------------------------- /assets/DamagedHelmet/glTF/DamagedHelmet.gltf: -------------------------------------------------------------------------------- 1 | { 2 | "accessors" : [ 3 | { 4 | "bufferView" : 0, 5 | "componentType" : 5123, 6 | "count" : 46356, 7 | "max" : [ 8 | 14555 9 | ], 10 | "min" : [ 11 | 0 12 | ], 13 | "type" : "SCALAR" 14 | }, 15 | { 16 | "bufferView" : 1, 17 | "componentType" : 5126, 18 | "count" : 14556, 19 | "max" : [ 20 | 0.9424954056739807, 21 | 0.8128451108932495, 22 | 0.900973916053772 23 | ], 24 | "min" : [ 25 | -0.9474585652351379, 26 | -1.18715500831604, 27 | -0.9009949564933777 28 | ], 29 | "type" : "VEC3" 30 | }, 31 | { 32 | "bufferView" : 2, 33 | "componentType" : 5126, 34 | "count" : 14556, 35 | "max" : [ 36 | 1.0, 37 | 1.0, 38 | 1.0 39 | ], 40 | "min" : [ 41 | -1.0, 42 | -1.0, 43 | -1.0 44 | ], 45 | "type" : "VEC3" 46 | }, 47 | { 48 | "bufferView" : 3, 49 | "componentType" : 5126, 50 | "count" : 14556, 51 | "max" : [ 52 | 0.9999759793281555, 53 | 1.998665988445282 54 | ], 55 | "min" : [ 56 | 0.002448640065267682, 57 | 1.0005531199858524 58 | ], 59 | "type" : "VEC2" 60 | } 61 | ], 62 | "asset" : { 63 | "generator" : "Khronos Blender glTF 2.0 exporter", 64 | "version" : "2.0" 65 | }, 66 | "bufferViews" : [ 67 | { 68 | "buffer" : 0, 69 | "byteLength" : 92712, 70 | "byteOffset" : 0, 71 | "target" : 34963 72 | }, 73 | { 74 | "buffer" : 0, 75 | "byteLength" : 174672, 76 | "byteOffset" : 92712, 77 | "target" : 34962 78 | }, 79 | { 80 | "buffer" : 0, 81 | "byteLength" : 174672, 82 | "byteOffset" : 267384, 83 | "target" : 34962 84 | }, 85 | { 86 | "buffer" : 0, 87 | "byteLength" : 116448, 88 | "byteOffset" : 442056, 89 | "target" : 34962 90 | } 91 | ], 92 | "buffers" : [ 93 | { 94 | "byteLength" : 558504, 95 | "uri" : "DamagedHelmet.bin" 96 | } 97 | ], 98 | "images" : [ 99 | { 100 | "uri" : "Default_albedo.jpg" 101 | }, 102 | { 103 | "uri" : "Default_metalRoughness.jpg" 104 | }, 105 | { 106 | "uri" : "Default_emissive.jpg" 107 | }, 108 | { 109 | "uri" : "Default_AO.jpg" 110 | }, 111 | { 112 | "uri" : "Default_normal.jpg" 113 | } 114 | ], 115 | "materials" : [ 116 | { 117 | "emissiveFactor" : [ 118 | 1.0, 119 | 1.0, 120 | 1.0 121 | ], 122 | "emissiveTexture" : { 123 | "index" : 2 124 | }, 125 | "name" : "Material_MR", 126 | "normalTexture" : { 127 | "index" : 4 128 | }, 129 | "occlusionTexture" : { 130 | "index" : 3 131 | }, 132 | "pbrMetallicRoughness" : { 133 | "baseColorTexture" : { 134 | "index" : 0 135 | }, 136 | "metallicRoughnessTexture" : { 137 | "index" : 1 138 | } 139 | } 140 | } 141 | ], 142 | "meshes" : [ 143 | { 144 | "name" : "mesh_helmet_LP_13930damagedHelmet", 145 | "primitives" : [ 146 | { 147 | "attributes" : { 148 | "NORMAL" : 2, 149 | "POSITION" : 1, 150 | "TEXCOORD_0" : 3 151 | }, 152 | "indices" : 0, 153 | "material" : 0 154 | } 155 | ] 156 | } 157 | ], 158 | "nodes" : [ 159 | { 160 | "mesh" : 0, 161 | "name" : "node_damagedHelmet_-6514", 162 | "rotation" : [ 163 | 0.7071068286895752, 164 | 0.0, 165 | -0.0, 166 | 0.7071068286895752 167 | ] 168 | } 169 | ], 170 | "samplers" : [ 171 | {} 172 | ], 173 | "scene" : 0, 174 | "scenes" : [ 175 | { 176 | "name" : "Scene", 177 | "nodes" : [ 178 | 0 179 | ] 180 | } 181 | ], 182 | "textures" : [ 183 | { 184 | "sampler" : 0, 185 | "source" : 0 186 | }, 187 | { 188 | "sampler" : 0, 189 | "source" : 1 190 | }, 191 | { 192 | "sampler" : 0, 193 | "source" : 2 194 | }, 195 | { 196 | "sampler" : 0, 197 | "source" : 3 198 | }, 199 | { 200 | "sampler" : 0, 201 | "source" : 4 202 | } 203 | ] 204 | } 205 | -------------------------------------------------------------------------------- /assets/DamagedHelmet/glTF/Default_AO.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/DamagedHelmet/glTF/Default_AO.jpg -------------------------------------------------------------------------------- /assets/DamagedHelmet/glTF/Default_albedo.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/DamagedHelmet/glTF/Default_albedo.jpg -------------------------------------------------------------------------------- /assets/DamagedHelmet/glTF/Default_emissive.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/DamagedHelmet/glTF/Default_emissive.jpg -------------------------------------------------------------------------------- /assets/DamagedHelmet/glTF/Default_metalRoughness.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/DamagedHelmet/glTF/Default_metalRoughness.jpg -------------------------------------------------------------------------------- /assets/DamagedHelmet/glTF/Default_normal.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/DamagedHelmet/glTF/Default_normal.jpg -------------------------------------------------------------------------------- /assets/DamagedHelmet/screenshot/screenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/DamagedHelmet/screenshot/screenshot.png -------------------------------------------------------------------------------- /assets/brdfLUT.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/brdfLUT.png -------------------------------------------------------------------------------- /assets/helipad/charlie/sheen.ktx2: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:70e4a12ea4e454bbc188867f7e9e9275ee1c66e4a04d6746b68ecf06c61401c5 3 | size 67109256 4 | -------------------------------------------------------------------------------- /assets/helipad/ggx/specular.ktx2: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:7c5885cc118e1aa114e48b776e86eec93301562b2cf0b92ea538e0561aaf0952 3 | size 67109256 4 | -------------------------------------------------------------------------------- /assets/helipad/lambertian/diffuse.ktx2: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:0173a9e4ecb689314ccde0cc25877daf14e5a6f59a91acab2003474aadc4bbd5 3 | size 50331816 4 | -------------------------------------------------------------------------------- /assets/lut_charlie.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/lut_charlie.png -------------------------------------------------------------------------------- /assets/lut_ggx.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/lut_ggx.png -------------------------------------------------------------------------------- /assets/thisisfine.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/thisisfine.jpg -------------------------------------------------------------------------------- /assets/tyrian.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/assets/tyrian.png -------------------------------------------------------------------------------- /assets/tyrian.sprites: -------------------------------------------------------------------------------- 1 | 191 220 191 2 | one_shot 0 42 12 56 3 | two_shot 12 42 24 56 4 | three_shot 24 42 36 56 5 | four_shot 36 42 48 56 6 | five_shot 48 42 60 56 7 | energy 60 42 72 56 8 | reg_fireball 72 42 84 56 9 | blue_fireball 84 42 96 56 10 | arched_energy 96 42 108 56 11 | one_thin 108 42 120 56 12 | missile 120 42 132 56 13 | two_missile 132 42 144 56 14 | two_thin 144 42 156 56 15 | eagle 156 42 168 56 16 | nuke 168 42 180 56 17 | double_energy 180 42 192 56 18 | blue_haduken 192 42 204 56 19 | red_haduken 204 42 216 56 20 | missile2 216 42 228 56 -------------------------------------------------------------------------------- /attributes/attrib1.cxx: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | template 4 | const char* enum_to_name(type_t x) { 5 | switch(x) { 6 | @meta for enum(type_t x2 : type_t) 7 | case x2: 8 | return @enum_name(x2); 9 | default: 10 | return ""; 11 | } 12 | } 13 | 14 | // Three kinds of attributes: 15 | // 1. Class types. 16 | // 2. Enum type. 17 | // 3. Attribute aliases to any other type. 18 | 19 | // Define a class type to be used as an attribute. 20 | struct extent_t { 21 | int width, height; 22 | }; 23 | 24 | // Name the class type after a dot in the attribute sequence. 25 | // Because this is an aggregate (no user-provided constructor), use the 26 | // braced aggregate initializer. 27 | [[.extent_t { 800, 600 }]] int X; 28 | 29 | // Define an enum for an attribute. 30 | enum class shape_t { 31 | circle, 32 | square, 33 | triangle, 34 | }; 35 | 36 | // Name the enum after the dot. For enum attributes, a single-identifier 37 | // token initializer will be matched to enumeration names. 38 | [[.shape_t=triangle]] int Y; 39 | 40 | // Define an attribute alias to some other type. This lets us reuse types 41 | // without ambiguity. 42 | using title_t [[attribute]] = const char*; 43 | 44 | // Name the attribute alias. We can't name the underlying type. 45 | // The attribute alias is like an opaque typedef. 46 | [[.title_t="A great var"]] int Z; 47 | 48 | int main() { 49 | // The @attribute keyword is provided a declaration and an 50 | // attribute type or attribute alias. It gives an lvalue to that 51 | // compile-time attribute. 52 | printf("X width = %d\n", @attribute(X, extent_t).width); 53 | 54 | // If non-const, you can even modify it at compile time. This is helpful 55 | // for keeping counters. 56 | @meta ++@attribute(X, extent_t).width; 57 | printf("X width = %d\n", @attribute(X, extent_t).width); 58 | 59 | // Use Circle reflection to turn this enum attribute into a string: 60 | printf("Y shape = %s\n", enum_to_name(@attribute(Y, shape_t))); 61 | 62 | // Print directly from a compile-time const char*. 63 | printf("Z title = %s\n", @attribute(Z, title_t)); 64 | } 65 | -------------------------------------------------------------------------------- /attributes/attrib2.cxx: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | template 5 | const char* enum_to_name(type_t x) { 6 | switch(x) { 7 | @meta for enum(type_t x2 : type_t) 8 | case x2: 9 | return @enum_name(x2); 10 | default: 11 | return ""; 12 | } 13 | } 14 | 15 | using title [[attribute]] = const char*; 16 | using url [[attribute]] = const char*; 17 | using magic [[attribute]] = int; 18 | 19 | enum class edge { 20 | left, top, right, bottom, 21 | }; 22 | enum class corner { 23 | nw, ne, se, sw, 24 | }; 25 | 26 | template 27 | std::string to_string(type_t x) { 28 | if constexpr(std::is_enum_v) { 29 | return enum_to_name(x); 30 | 31 | } else if constexpr(std::is_same_v) { 32 | return x ? "true" : "false"; 33 | 34 | } else if constexpr(std::is_arithmetic_v) { 35 | return std::to_string(x); 36 | 37 | } else { 38 | static_assert(std::is_same_v); 39 | return x; 40 | } 41 | } 42 | 43 | struct foo_t { 44 | [[.edge=right, .url="https://www.fake.url/"]] int x; 45 | [[.title="Sometimes a vowel", .corner=ne]] int y; 46 | [[.magic=10101, .title="The magic number"]] int z; 47 | }; 48 | 49 | template 50 | void print_member_attributes() { 51 | std::cout<< "Member attributes for "<< @type_string(type_t)<< "\n"; 52 | 53 | @meta for(int i = 0; i < @member_count(type_t); ++i) {{ 54 | // Loop over each member. 55 | std::cout<< " "<< @member_name(type_t, i)<< ":\n"; 56 | 57 | // @member_attribute_list is a type parameter pack of all attribute names. 58 | // Loop over them and print them out. 59 | @meta for typename(t : { @member_attribute_list(type_t, i)... }) { 60 | std::cout<< " "<< @type_string(t)<< " = "<< 61 | to_string(@member_attribute(type_t, i, t))<< "\n"; 62 | } 63 | }} 64 | } 65 | 66 | int main() { 67 | print_member_attributes(); 68 | } -------------------------------------------------------------------------------- /cube/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | project(cube) 3 | 4 | include_directories(../include) 5 | 6 | set(SOURCE_FILES 7 | cube.cxx 8 | ) 9 | 10 | set_source_files_properties(cube.cxx PROPERTIES COMPILE_FLAGS -shader) 11 | 12 | add_executable(cube ${SOURCE_FILES}) 13 | 14 | target_link_libraries(cube 15 | glfw 16 | gl3w 17 | GL 18 | ) 19 | -------------------------------------------------------------------------------- /cube/cube.cxx: -------------------------------------------------------------------------------- 1 | #include "appglfw.hxx" 2 | 3 | #define STB_IMAGE_IMPLEMENTATION 4 | #include "texture.hxx" 5 | 6 | [[spirv::in(0)]] 7 | vec3 in_position_vs; 8 | 9 | [[spirv::in(1)]] 10 | vec2 in_texcoord_vs; 11 | 12 | [[spirv::out(1)]] 13 | vec2 out_texcoord_vs; 14 | 15 | [[spirv::in(1)]] 16 | vec2 in_texcoord_fs; 17 | 18 | [[spirv::out(0)]] 19 | vec4 out_color_fs; 20 | 21 | [[spirv::uniform(0)]] 22 | sampler2D texture_sampler; 23 | 24 | struct uniforms_t { 25 | mat4 view_proj; 26 | float seconds; 27 | }; 28 | 29 | [[spirv::uniform(0)]] 30 | uniforms_t uniforms; 31 | 32 | [[spirv::vert]] 33 | void vert_main() { 34 | // Create a rotation matrix. 35 | mat4 rotate = make_rotateY(uniforms.seconds); 36 | 37 | // Rotate the position. 38 | vec4 position = rotate * vec4(in_position_vs, 1); 39 | 40 | // Write to a builtin variable. 41 | glvert_Output.Position = uniforms.view_proj * position; 42 | 43 | // Pass texcoord through. 44 | out_texcoord_vs = in_texcoord_vs; 45 | } 46 | 47 | [[spirv::frag]] 48 | void frag_main() { 49 | // Load the inputs. The locations correspond to the outputs from the 50 | // vertex shader. 51 | vec2 texcoord = in_texcoord_fs; 52 | vec4 color = texture(texture_sampler, texcoord); 53 | 54 | // Write to a variable template. 55 | out_color_fs = color; 56 | } 57 | 58 | //////////////////////////////////////////////////////////////////////////////// 59 | 60 | struct myapp_t : app_t { 61 | myapp_t(); 62 | void display() override; 63 | void create_shaders(); 64 | void create_vao(); 65 | 66 | GLuint program; 67 | GLuint texture; 68 | GLuint vao; 69 | GLuint ubo; 70 | }; 71 | 72 | myapp_t::myapp_t() : app_t("C++ shaders") { 73 | // Set the camera. 74 | camera.distance = 4; 75 | camera.pitch = radians(30.f); 76 | 77 | create_shaders(); 78 | create_vao(); 79 | } 80 | 81 | void myapp_t::create_shaders() { 82 | GLuint vs = glCreateShader(GL_VERTEX_SHADER); 83 | GLuint fs = glCreateShader(GL_FRAGMENT_SHADER); 84 | GLuint shaders[] { vs, fs }; 85 | glShaderBinary(2, shaders, GL_SHADER_BINARY_FORMAT_SPIR_V_ARB, 86 | __spirv_data, __spirv_size); 87 | 88 | glSpecializeShader(vs, @spirv(vert_main), 0, nullptr, nullptr); 89 | glSpecializeShader(fs, @spirv(frag_main), 0, nullptr, nullptr); 90 | 91 | program = glCreateProgram(); 92 | glAttachShader(program, vs); 93 | glAttachShader(program, fs); 94 | glLinkProgram(program); 95 | } 96 | 97 | void myapp_t::create_vao() { 98 | // Create the vertex array. 99 | struct vertex_t { 100 | vec3 pos; 101 | uint16_t u, v; 102 | }; 103 | 104 | const vertex_t vertices[36] { 105 | +1, +1, +1, 0x0000, 0xffff, 106 | +1, +1, -1, 0x0000, 0x0000, 107 | +1, -1, -1, 0xffff, 0x0000, 108 | +1, +1, +1, 0x0000, 0xffff, 109 | +1, -1, -1, 0xffff, 0x0000, 110 | +1, -1, +1, 0xffff, 0xffff, 111 | +1, +1, +1, 0x0000, 0xffff, 112 | +1, -1, +1, 0x0000, 0x0000, 113 | -1, -1, +1, 0xffff, 0x0000, 114 | +1, +1, +1, 0x0000, 0xffff, 115 | -1, -1, +1, 0xffff, 0x0000, 116 | -1, +1, +1, 0xffff, 0xffff, 117 | +1, +1, +1, 0x0000, 0xffff, 118 | -1, +1, +1, 0x0000, 0x0000, 119 | -1, +1, -1, 0xffff, 0x0000, 120 | +1, +1, +1, 0x0000, 0xffff, 121 | -1, +1, -1, 0xffff, 0x0000, 122 | +1, +1, -1, 0xffff, 0xffff, 123 | -1, -1, -1, 0x0000, 0xffff, 124 | +1, -1, -1, 0x0000, 0x0000, 125 | +1, +1, -1, 0xffff, 0x0000, 126 | -1, -1, -1, 0x0000, 0xffff, 127 | +1, +1, -1, 0xffff, 0x0000, 128 | -1, +1, -1, 0xffff, 0xffff, 129 | -1, -1, -1, 0x0000, 0xffff, 130 | -1, +1, -1, 0x0000, 0x0000, 131 | -1, +1, +1, 0xffff, 0x0000, 132 | -1, -1, -1, 0x0000, 0xffff, 133 | -1, +1, +1, 0xffff, 0x0000, 134 | -1, -1, +1, 0xffff, 0xffff, 135 | -1, -1, -1, 0x0000, 0xffff, 136 | -1, -1, +1, 0x0000, 0x0000, 137 | +1, -1, +1, 0xffff, 0x0000, 138 | -1, -1, -1, 0x0000, 0xffff, 139 | +1, -1, +1, 0xffff, 0x0000, 140 | +1, -1, -1, 0xffff, 0xffff, 141 | }; 142 | GLuint vbo; 143 | glCreateBuffers(1, &vbo); 144 | glNamedBufferStorage(vbo, sizeof(vertices), vertices, 0); 145 | 146 | // Create the VAO. 147 | // Associate vbo into bindingindex 0. 148 | glCreateVertexArrays(1, &vao); 149 | glVertexArrayVertexBuffer(vao, 0, vbo, 0, sizeof(vertex_t)); 150 | 151 | // Enable vertex attribute 0. Associate with binding index 0. 152 | glEnableVertexArrayAttrib(vao, 0); 153 | glVertexArrayAttribBinding(vao, 0, 0); 154 | glVertexArrayAttribFormat(vao, 0, 3, GL_FLOAT, GL_FALSE, 155 | offsetof(vertex_t, pos)); 156 | 157 | glEnableVertexArrayAttrib(vao, 1); 158 | glVertexArrayAttribBinding(vao, 1, 0); 159 | glVertexArrayAttribFormat(vao, 1, 2, GL_UNSIGNED_SHORT, 160 | GL_TRUE, offsetof(vertex_t, u)); 161 | 162 | // Make an OpenGL texture. 163 | texture = load_texture("../assets/thisisfine.jpg"); 164 | 165 | // Make a UBO. 166 | glCreateBuffers(1, &ubo); 167 | glNamedBufferStorage(ubo, sizeof(uniforms_t), nullptr, 168 | GL_DYNAMIC_STORAGE_BIT); 169 | } 170 | 171 | void myapp_t::display() { 172 | glEnable(GL_DEPTH_TEST); 173 | glDepthFunc(GL_LESS); 174 | 175 | glEnable(GL_CULL_FACE); 176 | glFrontFace(GL_CW); 177 | 178 | const float bg[4] { .2, 0, 0, 0 }; 179 | glClearBufferfv(GL_COLOR, 0, bg); 180 | glClear(GL_DEPTH_BUFFER_BIT); 181 | 182 | glUseProgram(program); 183 | double timer = glfwGetTime(); 184 | 185 | // Set the view matrix. 186 | int width, height; 187 | glfwGetWindowSize(window, &width, &height); 188 | 189 | mat4 projection = camera.get_perspective(width, height); 190 | mat4 view = camera.get_view(); 191 | 192 | uniforms_t uniforms; 193 | uniforms.view_proj = projection * view; 194 | uniforms.seconds = glfwGetTime(); 195 | glNamedBufferSubData(ubo, 0, sizeof(uniforms), &uniforms); 196 | 197 | // Bind the UBO. 198 | glBindBufferBase(GL_UNIFORM_BUFFER, 0, ubo); 199 | 200 | // Bind the texture. 201 | glBindTextureUnit(0, texture); 202 | 203 | glBindVertexArray(vao); 204 | glDrawArrays(GL_TRIANGLES, 0, 36); 205 | } 206 | 207 | int main() { 208 | glfwInit(); 209 | gl3wInit(); 210 | myapp_t app; 211 | app.loop(); 212 | return 0; 213 | } 214 | -------------------------------------------------------------------------------- /cube2/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | project(cube2) 3 | 4 | include_directories(../include) 5 | 6 | set(SOURCE_FILES 7 | cube2.cxx 8 | ) 9 | 10 | set_source_files_properties(cube2.cxx PROPERTIES COMPILE_FLAGS -shader) 11 | 12 | add_executable(cube2 ${SOURCE_FILES}) 13 | 14 | target_link_libraries(cube2 15 | glfw 16 | gl3w 17 | GL 18 | ) 19 | -------------------------------------------------------------------------------- /cube2/cube2.cxx: -------------------------------------------------------------------------------- 1 | #include "appglfw.hxx" 2 | 3 | #define STB_IMAGE_IMPLEMENTATION 4 | #include "texture.hxx" 5 | 6 | // Use typed enums to associate binding attributes with types. 7 | enum typename vattrib_t { 8 | vattrib_position = vec3, 9 | vattrib_texcoord = vec2, 10 | }; 11 | 12 | // Can do it for samplers too. 13 | enum typename sampler_t { 14 | sampler_color = sampler2D, 15 | }; 16 | 17 | struct uniforms_t { 18 | mat4 view_proj; 19 | float seconds; 20 | }; 21 | 22 | [[spirv::vert]] 23 | void vert_main() { 24 | // Create a rotation matrix. 25 | mat4 rotate = make_rotateY(shader_ubo<0, uniforms_t>.seconds); 26 | 27 | // Rotate the position. 28 | vec4 position = rotate * vec4(shader_in, 1); 29 | 30 | // Write to a builtin variable. 31 | glvert_Output.Position = shader_ubo<0, uniforms_t>.view_proj * position; 32 | 33 | // Pass texcoord through. 34 | shader_out = shader_in; 35 | } 36 | 37 | [[spirv::frag]] 38 | void frag_main() { 39 | // Load the inputs. The locations correspond to the outputs from the 40 | // vertex shader. 41 | vec2 texcoord = shader_in; 42 | vec4 color = texture(shader_sampler, texcoord); 43 | 44 | // Write to a variable template. 45 | shader_out<0, vec4> = color; 46 | } 47 | 48 | //////////////////////////////////////////////////////////////////////////////// 49 | 50 | struct myapp_t : app_t { 51 | myapp_t(); 52 | void display() override; 53 | void create_shaders(); 54 | void create_vao(); 55 | 56 | GLuint program; 57 | GLuint texture; 58 | GLuint vao; 59 | GLuint ubo; 60 | }; 61 | 62 | myapp_t::myapp_t() : app_t("C++ shaders") { 63 | // Set the camera. 64 | camera.distance = 4; 65 | camera.pitch = radians(30.f); 66 | 67 | create_shaders(); 68 | create_vao(); 69 | } 70 | 71 | void myapp_t::create_shaders() { 72 | GLuint vs = glCreateShader(GL_VERTEX_SHADER); 73 | GLuint fs = glCreateShader(GL_FRAGMENT_SHADER); 74 | GLuint shaders[] { vs, fs }; 75 | glShaderBinary(2, shaders, GL_SHADER_BINARY_FORMAT_SPIR_V_ARB, 76 | __spirv_data, __spirv_size); 77 | 78 | glSpecializeShader(vs, @spirv(vert_main), 0, nullptr, nullptr); 79 | glSpecializeShader(fs, @spirv(frag_main), 0, nullptr, nullptr); 80 | 81 | program = glCreateProgram(); 82 | glAttachShader(program, vs); 83 | glAttachShader(program, fs); 84 | glLinkProgram(program); 85 | } 86 | 87 | void myapp_t::create_vao() { 88 | // Create the vertex array. 89 | struct vertex_t { 90 | vec3 pos; 91 | uint16_t u, v; 92 | }; 93 | 94 | const vertex_t vertices[36] { 95 | +1, +1, +1, 0x0000, 0xffff, 96 | +1, +1, -1, 0x0000, 0x0000, 97 | +1, -1, -1, 0xffff, 0x0000, 98 | +1, +1, +1, 0x0000, 0xffff, 99 | +1, -1, -1, 0xffff, 0x0000, 100 | +1, -1, +1, 0xffff, 0xffff, 101 | +1, +1, +1, 0x0000, 0xffff, 102 | +1, -1, +1, 0x0000, 0x0000, 103 | -1, -1, +1, 0xffff, 0x0000, 104 | +1, +1, +1, 0x0000, 0xffff, 105 | -1, -1, +1, 0xffff, 0x0000, 106 | -1, +1, +1, 0xffff, 0xffff, 107 | +1, +1, +1, 0x0000, 0xffff, 108 | -1, +1, +1, 0x0000, 0x0000, 109 | -1, +1, -1, 0xffff, 0x0000, 110 | +1, +1, +1, 0x0000, 0xffff, 111 | -1, +1, -1, 0xffff, 0x0000, 112 | +1, +1, -1, 0xffff, 0xffff, 113 | -1, -1, -1, 0x0000, 0xffff, 114 | +1, -1, -1, 0x0000, 0x0000, 115 | +1, +1, -1, 0xffff, 0x0000, 116 | -1, -1, -1, 0x0000, 0xffff, 117 | +1, +1, -1, 0xffff, 0x0000, 118 | -1, +1, -1, 0xffff, 0xffff, 119 | -1, -1, -1, 0x0000, 0xffff, 120 | -1, +1, -1, 0x0000, 0x0000, 121 | -1, +1, +1, 0xffff, 0x0000, 122 | -1, -1, -1, 0x0000, 0xffff, 123 | -1, +1, +1, 0xffff, 0x0000, 124 | -1, -1, +1, 0xffff, 0xffff, 125 | -1, -1, -1, 0x0000, 0xffff, 126 | -1, -1, +1, 0x0000, 0x0000, 127 | +1, -1, +1, 0xffff, 0x0000, 128 | -1, -1, -1, 0x0000, 0xffff, 129 | +1, -1, +1, 0xffff, 0x0000, 130 | +1, -1, -1, 0xffff, 0xffff, 131 | }; 132 | GLuint vbo; 133 | glCreateBuffers(1, &vbo); 134 | glNamedBufferStorage(vbo, sizeof(vertices), vertices, 0); 135 | 136 | // Create the VAO. 137 | // Associate vbo into bindingindex 0. 138 | glCreateVertexArrays(1, &vao); 139 | glVertexArrayVertexBuffer(vao, 0, vbo, 0, sizeof(vertex_t)); 140 | 141 | // Enable vertex attribute 0. Associate with binding index 0. 142 | glEnableVertexArrayAttrib(vao, vattrib_position); 143 | glVertexArrayAttribBinding(vao, vattrib_position, 0); 144 | glVertexArrayAttribFormat(vao, vattrib_position, 3, GL_FLOAT, GL_FALSE, 145 | offsetof(vertex_t, pos)); 146 | 147 | glEnableVertexArrayAttrib(vao, vattrib_texcoord); 148 | glVertexArrayAttribBinding(vao, vattrib_texcoord, 0); 149 | glVertexArrayAttribFormat(vao, vattrib_texcoord, 2, GL_UNSIGNED_SHORT, 150 | GL_TRUE, offsetof(vertex_t, u)); 151 | 152 | // Make an OpenGL texture. 153 | texture = load_texture("../assets/thisisfine.jpg"); 154 | 155 | // Make a UBO. 156 | glCreateBuffers(1, &ubo); 157 | glNamedBufferStorage(ubo, sizeof(uniforms_t), nullptr, 158 | GL_DYNAMIC_STORAGE_BIT); 159 | } 160 | 161 | void myapp_t::display() { 162 | glEnable(GL_DEPTH_TEST); 163 | glDepthFunc(GL_LESS); 164 | 165 | glEnable(GL_CULL_FACE); 166 | glFrontFace(GL_CW); 167 | 168 | const float bg[4] { .2, 0, 0, 0 }; 169 | glClearBufferfv(GL_COLOR, 0, bg); 170 | glClear(GL_DEPTH_BUFFER_BIT); 171 | 172 | glUseProgram(program); 173 | double timer = glfwGetTime(); 174 | 175 | // Set the view matrix. 176 | int width, height; 177 | glfwGetWindowSize(window, &width, &height); 178 | 179 | mat4 projection = camera.get_perspective(width, height); 180 | mat4 view = camera.get_view(); 181 | 182 | uniforms_t uniforms; 183 | uniforms.view_proj = projection * view; 184 | uniforms.seconds = glfwGetTime(); 185 | glNamedBufferSubData(ubo, 0, sizeof(uniforms), &uniforms); 186 | 187 | // Bind the UBO. 188 | glBindBufferBase(GL_UNIFORM_BUFFER, 0, ubo); 189 | 190 | // Bind the texture. 191 | glBindTextureUnit(sampler_color, texture); 192 | 193 | glBindVertexArray(vao); 194 | glDrawArrays(GL_TRIANGLES, 0, 36); 195 | } 196 | 197 | int main() { 198 | glfwInit(); 199 | gl3wInit(); 200 | myapp_t app; 201 | app.loop(); 202 | return 0; 203 | } 204 | -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/D3D12SM6WaveIntrinsics.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "DXSample.h" 15 | 16 | using namespace DirectX; 17 | 18 | // Note that while ComPtr is used to manage the lifetime of resources on the CPU, 19 | // it has no understanding of the lifetime of resources on the GPU. Apps must account 20 | // for the GPU lifetime of resources to avoid destroying objects that may still be 21 | // referenced by the GPU. 22 | // An example of this can be found in the class method: OnDestroy(). 23 | using Microsoft::WRL::ComPtr; 24 | 25 | class UILayer; 26 | 27 | class D3D12SM6WaveIntrinsics : public DXSample 28 | { 29 | public: 30 | D3D12SM6WaveIntrinsics(UINT width, UINT height, std::wstring name); 31 | inline ID3D12Device* GetDevice() { return m_d3d12Device.Get(); } 32 | inline ID3D12CommandQueue* GetCommandQueue() { return m_commandQueue.Get(); } 33 | inline ID3D12Resource* GetUIRenderTarget() { return m_uiRenderTarget.Get(); } 34 | virtual void OnInit(); 35 | virtual void OnUpdate(); 36 | virtual void OnRender(); 37 | virtual void OnDestroy(); 38 | virtual void OnKeyDown(UINT8 key); 39 | virtual void OnSizeChanged(UINT width, UINT height, bool minimized); 40 | virtual void OnMouseMove(UINT x, UINT y); 41 | virtual void OnLeftButtonDown(UINT x, UINT y); 42 | virtual void OnLeftButtonUp(UINT x, UINT y); 43 | virtual IDXGISwapChain* GetSwapchain() { return m_swapChain.Get(); } 44 | 45 | private: 46 | // In this sample we overload the meaning of FrameCount to mean both the maximum 47 | // number of frames that will be queued to the GPU at a time, as well as the number 48 | // of back buffers in the DXGI swap chain. For the majority of applications, this 49 | // is convenient and works well. However, there will be certain cases where an 50 | // application may want to queue up more frames than there are back buffers 51 | // available. 52 | // It should be noted that excessive buffering of frames dependent on user input 53 | // may result in noticeable latency in your app. 54 | static const UINT FrameCount = 2; 55 | 56 | struct Vertex 57 | { 58 | XMFLOAT3 position; 59 | XMFLOAT4 color; 60 | }; 61 | 62 | struct Vertex2 63 | { 64 | XMFLOAT3 position; 65 | XMFLOAT2 uv; 66 | }; 67 | 68 | struct SceneConstantBuffer 69 | { 70 | XMMATRIX orthProjMatrix; 71 | XMFLOAT2 mousePosition; 72 | XMFLOAT2 resolution; 73 | float time; 74 | UINT renderingMode; 75 | UINT laneSize; 76 | UINT padding[40]; // Padding so the struct is 256-byte aligned. 77 | }; 78 | 79 | // Pipeline objects. 80 | CD3DX12_VIEWPORT m_viewport; 81 | CD3DX12_RECT m_scissorRect; 82 | ComPtr m_swapChain; 83 | ComPtr m_d3d12Device; 84 | ComPtr m_renderPass1RenderTargets; 85 | ComPtr m_renderPass2RenderTargets[FrameCount]; 86 | ComPtr m_uiRenderTarget; 87 | ComPtr m_commandAllocators[FrameCount]; 88 | ComPtr m_commandQueue; 89 | ComPtr m_renderPass1RootSignature; 90 | ComPtr m_renderPass2RootSignature; 91 | ComPtr m_rtvHeap; 92 | ComPtr m_cbSrvHeap; 93 | ComPtr m_renderPass1PSO; 94 | ComPtr m_renderPass2PSO; 95 | ComPtr m_commandList; 96 | UINT m_rtvDescriptorSize; 97 | UINT m_cbSrvDescriptorSize; 98 | 99 | // App resources. 100 | ComPtr m_renderPass1VertexBuffer; 101 | ComPtr m_renderPass2VertexBuffer; 102 | D3D12_VERTEX_BUFFER_VIEW m_renderPass1VertexBufferView; 103 | D3D12_VERTEX_BUFFER_VIEW m_renderPass2VertexBufferView; 104 | ComPtr m_constantBuffer; 105 | SceneConstantBuffer m_constantBufferData; 106 | UINT8* m_pCbSrvDataBegin; 107 | float m_mousePosition[2]; 108 | bool m_mouseLeftButtonDown; 109 | 110 | // Synchronization objects. 111 | UINT m_frameIndex; 112 | HANDLE m_fenceEvent; 113 | ComPtr m_fence; 114 | UINT64 m_fenceValues[FrameCount]; 115 | 116 | // Shader Model 6 feature support result 117 | D3D12_FEATURE_DATA_D3D12_OPTIONS1 m_WaveIntrinsicsSupport; 118 | UINT m_rendermode; 119 | 120 | // UILayer 121 | std::shared_ptr m_uiLayer; 122 | 123 | void CreateDevice(const ComPtr& factory); 124 | void LoadPipeline(); 125 | void LoadAssets(); 126 | void RestoreD3DResources(); 127 | void ReleaseD3DResources(); 128 | void LoadSizeDependentResources(); 129 | void MoveToNextFrame(); 130 | void WaitForGpu(); 131 | void RenderScene(); 132 | void RenderUI(); 133 | }; 134 | -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/DXSample.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "DXSample.h" 14 | 15 | using namespace Microsoft::WRL; 16 | using namespace std; 17 | 18 | DXSample::DXSample(UINT width, UINT height, std::wstring name) : 19 | m_width(width), 20 | m_height(height), 21 | m_windowBounds{0,0,0,0}, 22 | m_title(name), 23 | m_aspectRatio(0.0f), 24 | m_useWarpDevice(false), 25 | m_enableUI(true) 26 | { 27 | WCHAR assetsPath[512]; 28 | GetAssetsPath(assetsPath, _countof(assetsPath)); 29 | m_assetsPath = assetsPath; 30 | 31 | UpdateForSizeChange(width, height); 32 | CheckTearingSupport(); 33 | } 34 | 35 | DXSample::~DXSample() 36 | { 37 | } 38 | 39 | void DXSample::UpdateForSizeChange(UINT clientWidth, UINT clientHeight) 40 | { 41 | m_width = clientWidth; 42 | m_height = clientHeight; 43 | m_aspectRatio = static_cast(clientWidth) / static_cast(clientHeight); 44 | } 45 | 46 | // Helper function for resolving the full path of assets. 47 | std::wstring DXSample::GetAssetFullPath(LPCWSTR assetName) 48 | { 49 | return m_assetsPath + assetName; 50 | } 51 | 52 | // Helper function for acquiring the first available hardware adapter that supports Direct3D 12. 53 | // If no such adapter can be found, *ppAdapter will be set to nullptr. 54 | _Use_decl_annotations_ 55 | void DXSample::GetHardwareAdapter( 56 | IDXGIFactory2* pFactory, 57 | IDXGIAdapter1** ppAdapter, 58 | bool requestHighPerformanceAdapter) 59 | { 60 | *ppAdapter = nullptr; 61 | 62 | ComPtr adapter; 63 | 64 | ComPtr factory6; 65 | if (SUCCEEDED(pFactory->QueryInterface(IID_PPV_ARGS(&factory6)))) 66 | { 67 | for ( 68 | UINT adapterIndex = 0; 69 | DXGI_ERROR_NOT_FOUND != factory6->EnumAdapterByGpuPreference( 70 | adapterIndex, 71 | requestHighPerformanceAdapter == true ? DXGI_GPU_PREFERENCE_HIGH_PERFORMANCE : DXGI_GPU_PREFERENCE_UNSPECIFIED, 72 | IID_PPV_ARGS(&adapter)); 73 | ++adapterIndex) 74 | { 75 | DXGI_ADAPTER_DESC1 desc; 76 | adapter->GetDesc1(&desc); 77 | 78 | if (desc.Flags & DXGI_ADAPTER_FLAG_SOFTWARE) 79 | { 80 | // Don't select the Basic Render Driver adapter. 81 | // If you want a software adapter, pass in "/warp" on the command line. 82 | continue; 83 | } 84 | 85 | // Check to see whether the adapter supports Direct3D 12, but don't create the 86 | // actual device yet. 87 | if (SUCCEEDED(D3D12CreateDevice(adapter.Get(), D3D_FEATURE_LEVEL_11_0, _uuidof(ID3D12Device), nullptr))) 88 | { 89 | break; 90 | } 91 | } 92 | } 93 | else 94 | { 95 | for (UINT adapterIndex = 0; DXGI_ERROR_NOT_FOUND != pFactory->EnumAdapters1(adapterIndex, &adapter); ++adapterIndex) 96 | { 97 | DXGI_ADAPTER_DESC1 desc; 98 | adapter->GetDesc1(&desc); 99 | 100 | if (desc.Flags & DXGI_ADAPTER_FLAG_SOFTWARE) 101 | { 102 | // Don't select the Basic Render Driver adapter. 103 | // If you want a software adapter, pass in "/warp" on the command line. 104 | continue; 105 | } 106 | 107 | // Check to see whether the adapter supports Direct3D 12, but don't create the 108 | // actual device yet. 109 | if (SUCCEEDED(D3D12CreateDevice(adapter.Get(), D3D_FEATURE_LEVEL_11_0, _uuidof(ID3D12Device), nullptr))) 110 | { 111 | break; 112 | } 113 | } 114 | } 115 | *ppAdapter = adapter.Detach(); 116 | } 117 | 118 | // Helper function for setting the window's title text. 119 | void DXSample::SetCustomWindowText(LPCWSTR text) 120 | { 121 | std::wstring windowText = m_title + L": " + text; 122 | SetWindowText(Win32Application::GetHwnd(), windowText.c_str()); 123 | } 124 | 125 | // Helper function for parsing any supplied command line args. 126 | _Use_decl_annotations_ 127 | void DXSample::ParseCommandLineArgs(WCHAR* argv[], int argc) 128 | { 129 | for (int i = 1; i < argc; ++i) 130 | { 131 | if (_wcsnicmp(argv[i], L"-warp", wcslen(argv[i])) == 0 || 132 | _wcsnicmp(argv[i], L"/warp", wcslen(argv[i])) == 0) 133 | { 134 | m_useWarpDevice = true; 135 | m_title = m_title + L" (WARP)"; 136 | } 137 | else if (_wcsnicmp(argv[i], L"-disableUI", wcslen(argv[i])) == 0 || 138 | _wcsnicmp(argv[i], L"/disableUI", wcslen(argv[i])) == 0) 139 | { 140 | m_enableUI = false; 141 | } 142 | } 143 | } 144 | 145 | // Determines whether tearing support is available for fullscreen borderless windows. 146 | void DXSample::CheckTearingSupport() 147 | { 148 | #ifndef PIXSUPPORT 149 | ComPtr factory; 150 | HRESULT hr = CreateDXGIFactory1(IID_PPV_ARGS(&factory)); 151 | BOOL allowTearing = FALSE; 152 | if (SUCCEEDED(hr)) 153 | { 154 | hr = factory->CheckFeatureSupport(DXGI_FEATURE_PRESENT_ALLOW_TEARING, &allowTearing, sizeof(allowTearing)); 155 | } 156 | 157 | m_tearingSupport = SUCCEEDED(hr) && allowTearing; 158 | #else 159 | m_tearingSupport = TRUE; 160 | #endif 161 | } 162 | 163 | void DXSample::SetWindowBounds(int left, int top, int right, int bottom) 164 | { 165 | m_windowBounds.left = static_cast(left); 166 | m_windowBounds.top = static_cast(top); 167 | m_windowBounds.right = static_cast(right); 168 | m_windowBounds.bottom = static_cast(bottom); 169 | } -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/DXSample.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "DXSampleHelper.h" 15 | #include "Win32Application.h" 16 | 17 | class DXSample 18 | { 19 | public: 20 | DXSample(UINT width, UINT height, std::wstring name); 21 | virtual ~DXSample(); 22 | 23 | virtual void OnInit() = 0; 24 | virtual void OnUpdate() = 0; 25 | virtual void OnRender() = 0; 26 | virtual void OnSizeChanged(UINT width, UINT height, bool minimized) = 0; 27 | virtual void OnDestroy() = 0; 28 | 29 | // Samples override the event handlers to handle specific messages. 30 | virtual void OnKeyDown(UINT8 /*key*/) {} 31 | virtual void OnKeyUp(UINT8 /*key*/) {} 32 | virtual void OnWindowMoved(int /*x*/, int /*y*/) {} 33 | virtual void OnMouseMove(UINT /*x*/, UINT /*y*/) {} 34 | virtual void OnLeftButtonDown(UINT /*x*/, UINT /*y*/) {} 35 | virtual void OnLeftButtonUp(UINT /*x*/, UINT /*y*/) {} 36 | virtual void OnDisplayChanged() {} 37 | 38 | // Accessors. 39 | UINT GetWidth() const { return m_width; } 40 | UINT GetHeight() const { return m_height; } 41 | const WCHAR* GetTitle() const { return m_title.c_str(); } 42 | bool GetTearingSupport() const { return m_tearingSupport; } 43 | RECT GetWindowsBounds() const { return m_windowBounds; } 44 | virtual IDXGISwapChain* GetSwapchain() { return nullptr; } 45 | 46 | void ParseCommandLineArgs(_In_reads_(argc) WCHAR* argv[], int argc); 47 | void UpdateForSizeChange(UINT clientWidth, UINT clientHeight); 48 | void SetWindowBounds(int left, int top, int right, int bottom); 49 | std::wstring GetAssetFullPath(LPCWSTR assetName); 50 | 51 | protected: 52 | void GetHardwareAdapter( 53 | _In_ IDXGIFactory2* pFactory, 54 | _Outptr_result_maybenull_ IDXGIAdapter1** ppAdapter, 55 | bool requestHighPerformanceAdapter = false); 56 | 57 | void SetCustomWindowText(LPCWSTR text); 58 | void CheckTearingSupport(); 59 | 60 | // Viewport dimensions. 61 | UINT m_width; 62 | UINT m_height; 63 | float m_aspectRatio; 64 | 65 | // Window bounds 66 | RECT m_windowBounds; 67 | 68 | // Whether or not tearing is available for fullscreen borderless windowed mode. 69 | bool m_tearingSupport; 70 | 71 | // Adapter info. 72 | bool m_useWarpDevice; 73 | 74 | // Override to be able to start without Dx11on12 UI for PIX. PIX doesn't support 11 on 12. 75 | bool m_enableUI; 76 | 77 | private: 78 | // Root assets path. 79 | std::wstring m_assetsPath; 80 | 81 | // Window title. 82 | std::wstring m_title; 83 | }; 84 | -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/Main.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "D3D12SM6WaveIntrinsics.h" 14 | 15 | _Use_decl_annotations_ 16 | int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR, int nCmdShow) 17 | { 18 | D3D12SM6WaveIntrinsics sample(1280, 720, L"D3D12 Shader Model 6 WaveIntrinsics Sample"); 19 | return Win32Application::Run(&sample, hInstance, nCmdShow); 20 | } 21 | -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/UILayer.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "D3D12SM6WaveIntrinsics.h" 15 | 16 | using Microsoft::WRL::ComPtr; 17 | 18 | class UILayer 19 | { 20 | public: 21 | UILayer(D3D12SM6WaveIntrinsics* pSample); 22 | 23 | void UpdateLabels(UINT selectedRenderMode=1); 24 | void Render(); 25 | void ReleaseResources(); 26 | void Resize(); 27 | 28 | private: 29 | struct TextBlock 30 | { 31 | std::wstring text; 32 | D2D1_RECT_F layout; 33 | IDWriteTextFormat* pFormat; 34 | }; 35 | 36 | enum Labels 37 | { 38 | RenderModeSelection = 0, 39 | RenderMode1, 40 | RenderMode2, 41 | RenderMode3, 42 | RenderMode4, 43 | RenderMode5, 44 | RenderMode6, 45 | RenderMode7, 46 | RenderMode8, 47 | RenderMode9, 48 | LabelCount 49 | }; 50 | 51 | D3D12SM6WaveIntrinsics* m_pSample; 52 | 53 | ComPtr m_d3d11DeviceContext; 54 | ComPtr m_d3d11On12Device; 55 | ComPtr m_dWriteFactory; 56 | ComPtr m_d2dFactory; 57 | ComPtr m_d2dDevice; 58 | ComPtr m_d2dDeviceContext; 59 | ComPtr m_wrappedRenderTarget; 60 | ComPtr m_d2dRenderTarget; 61 | ComPtr m_textBrush; 62 | ComPtr m_textFormat; 63 | ComPtr m_textLayout; 64 | std::vector m_labels; 65 | std::vector m_textBlocks; 66 | UINT m_selectedRenderMode; 67 | void Initialize(); 68 | }; -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/Win32Application.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "DXSample.h" 15 | 16 | class DXSample; 17 | 18 | class Win32Application 19 | { 20 | public: 21 | static int Run(DXSample* pSample, HINSTANCE hInstance, int nCmdShow); 22 | static void ToggleFullscreenWindow(IDXGISwapChain* pOutput = nullptr); 23 | static void SetWindowZorderToTopMost(bool setToTopMost); 24 | static HWND GetHwnd() { return m_hwnd; } 25 | static bool IsFullscreen() { return m_fullscreenMode; } 26 | 27 | protected: 28 | static LRESULT CALLBACK WindowProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam); 29 | 30 | private: 31 | static HWND m_hwnd; 32 | static bool m_fullscreenMode; 33 | static const UINT m_windowStyle = WS_OVERLAPPEDWINDOW; 34 | static RECT m_windowRect; 35 | }; 36 | -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/build_shaders.bat: -------------------------------------------------------------------------------- 1 | wsl -e circle -shader -emit-dxil -c -E wave_vert shaders.cxx -o wave_vert.dxil 2 | dxil-signing.exe wave_vert.dxil 3 | wsl -e circle -shader -emit-dxil -c -E wave_frag shaders.cxx -o wave_frag.dxil 4 | dxil-signing.exe wave_frag.dxil 5 | 6 | wsl -e circle -shader -emit-dxil -c -E mag_vert shaders.cxx -o mag_vert.dxil 7 | dxil-signing.exe mag_vert.dxil 8 | wsl -e circle -shader -emit-dxil -c -E mag_frag shaders.cxx -o mag_frag.dxil 9 | dxil-signing.exe mag_frag.dxil -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/mag_frag.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/WaveIntrinsics/mag_frag.dxil -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/mag_vert.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/WaveIntrinsics/mag_vert.dxil -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/readme.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_type: sample 3 | languages: 4 | - cpp 5 | products: 6 | - windows-api-win32 7 | name: Direct3D 12 shader model 6 wave intrinsics sample 8 | urlFragment: d3d12-shader-model-6-wave-intrinsics-sample-win32 9 | description: This sample visualizes how wave intrinsics work. 10 | extendedZipContent: 11 | - path: LICENSE 12 | target: LICENSE 13 | --- 14 | 15 | # Direct3D 12 shader model 6 wave intrinsics sample 16 | This sample visualizes how wave intrinsics work. Wave intrinsics are a new set of intrinsics for use in HLSL shader model 6. They enable operations across lanes in the SIMD processor cores, helping the performance of certain algorithms such as culling and packing sparse data sets. 17 | 18 | Doc and other resources: 19 | *) Wave intrinsics Wiki: https://github.com/Microsoft/DirectXShaderCompiler/wiki/Wave-Intrinsics 20 | *) DirectX MiniEngine: This engine takes advantage of the wave intrinsics to improve the performance of forward plus lighting. https://github.com/Microsoft/DirectX-Graphics-Samples/tree/master/MiniEngine 21 | 22 | Requirement: 23 | *) OS: Windows 10 Creators Update 15063+. 24 | *) Windows SDK: Install Windows 10 SDK 15063+ to obtain DXC, the new shader compiler that supports SM6. Note that you might need to modify the paths in CompileShader_SM6.bat if you are using a SDK that is newer than 15063. For simplicity we point the dxc.exe path to 15063 SDK folder. 25 | *) Graphics Driver: See this page for details. https://github.com/Microsoft/DirectXShaderCompiler/wiki/Running-Shaders 26 | -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/shaders.cxx: -------------------------------------------------------------------------------- 1 | template 2 | [[spirv::in(location)]] 3 | type_t shader_in; 4 | 5 | template 6 | [[spirv::out(location)]] 7 | type_t shader_out; 8 | 9 | struct uniforms_t { 10 | mat4 proj; 11 | vec2 mouse_pos; 12 | vec2 resolution; 13 | float time; 14 | uint render_mode; 15 | uint lane_size; 16 | }; 17 | 18 | [[spirv::uniform(0)]] 19 | uniforms_t u; 20 | 21 | extern "C" [[spirv::vert]] 22 | void wave_vert() { 23 | glvert_Output.Position = u.proj * shader_in<0, vec4>; 24 | shader_out<0, vec4> = shader_in<1, vec4>; 25 | } 26 | 27 | inline float tex_pattern(vec2 texcoord) { 28 | float scale = .13; 29 | float t = sin(texcoord.x * scale) + cos(texcoord.y * scale); 30 | float c = smoothstep(0.f, 0.2f, t * t); 31 | return c; 32 | } 33 | 34 | inline uint get_num_active_lanes() { 35 | // Submit a flag for each active lane and add up the bits. 36 | ivec4 bc = bitCount(gl_subgroupBallot(true)); 37 | uint num_active_lanes = bc.x + bc.y + bc.z + bc.w; 38 | return num_active_lanes; 39 | } 40 | 41 | extern "C" [[spirv::frag]] 42 | void wave_frag() { 43 | vec4 pos = glfrag_FragCoord; 44 | float texP = tex_pattern(pos.xy); 45 | vec4 color = texP * shader_in<0, vec4>; 46 | 47 | switch(u.render_mode) { 48 | 49 | case 1: 50 | // Default coloring. 51 | break; 52 | 53 | case 2: { 54 | // Color by lane ID. 55 | float x = gl_SubgroupInvocationID / float(u.lane_size); 56 | color = vec4(x, x, x, 1); 57 | break; 58 | } 59 | 60 | case 3: 61 | // Mark the first lane as white pixel. 62 | if(gl_subgroupElect()) 63 | color = vec4(1); 64 | break; 65 | 66 | case 4: 67 | // Color the first lane white and the last active lane red. 68 | if(gl_subgroupElect()) 69 | color = vec4(1); 70 | else if(gl_SubgroupInvocationID == gl_subgroupMax(gl_SubgroupInvocationID)) 71 | color = vec4(1, 0, 0, 1); 72 | break; 73 | 74 | case 5: { 75 | float active_ratio = get_num_active_lanes() / float(u.lane_size); 76 | color = vec4(active_ratio, active_ratio, active_ratio, 1); 77 | break; 78 | } 79 | 80 | case 6: 81 | // Broadcast the color in the first lane. 82 | color = gl_subgroupBroadcastFirst(color); 83 | break; 84 | 85 | case 7: { 86 | // Paint the wave with the averaged color inside the wave. 87 | color = gl_subgroupAdd(color) / get_num_active_lanes(); 88 | break; 89 | } 90 | 91 | case 8: { 92 | // First, compute the prefix sum of distance each lane to first lane. 93 | vec4 base_pos = gl_subgroupBroadcastFirst(pos); 94 | vec4 prefix_sum = gl_subgroupExclusiveAdd(pos - base_pos); 95 | 96 | // Then, normalize by the number of active lanes. 97 | color = prefix_sum / get_num_active_lanes(); 98 | break; 99 | } 100 | 101 | case 9: { 102 | float dx = gl_subgroupQuadSwapHorizontal(pos.x) - pos.x; 103 | float dy = gl_subgroupQuadSwapVertical(pos.y) - pos.y; 104 | 105 | if(dx > 0 && dy > 0) 106 | color = vec4(1, 0, 0, 1); 107 | else if(dx < 0 && dy > 0) 108 | color = vec4(0, 1, 0, 1); 109 | else if(dx > 0 && dy < 0) 110 | color = vec4(0, 0, 1, 1); 111 | else if(dx < 0 && dy < 0) 112 | color = vec4(1, 1, 1, 1); 113 | else 114 | color = vec4(0, 0, 0, 1); 115 | break; 116 | } 117 | 118 | } 119 | 120 | shader_out<0, vec4> = color; 121 | } 122 | 123 | //////////////////////////////////////////////////////////////////////////////// 124 | 125 | [[spirv::uniform(0)]] texture2D g_texture; 126 | [[spirv::uniform(1)]] texture2D g_ui_layer; 127 | [[spirv::uniform(0)]] sampler g_sampler; 128 | 129 | extern "C" [[spirv::vert]] 130 | void mag_vert() { 131 | glvert_Output.Position = u.proj * shader_in<0, vec4>; 132 | shader_out<0, vec2> = shader_in<1, vec2>; 133 | } 134 | 135 | extern "C" [[spirv::frag]] 136 | void mag_frag() { 137 | 138 | float ar = u.resolution.x / u.resolution.y; 139 | float mag_factor = 6; 140 | float mag_area_size = .05; 141 | float mag_area_border = .005; 142 | 143 | // Check the distance between this pixel and mouse location in UV space. 144 | vec2 norm_pixel_pos = shader_in<0, vec2>; 145 | vec2 norm_mouse_pos = u.mouse_pos / u.resolution; 146 | vec2 diff = abs(norm_pixel_pos - norm_mouse_pos); 147 | 148 | vec4 color = texture(combine(g_texture, g_sampler), norm_pixel_pos); 149 | vec4 ui = texture(combine(g_ui_layer, g_sampler), norm_pixel_pos); 150 | 151 | color = mix(color, ui, ui.a); 152 | 153 | if(diff.x < (mag_area_size + mag_area_border) && 154 | diff.y < (mag_area_size + mag_area_border) * ar) 155 | color = vec4(0, 1, 1, 1); 156 | 157 | if(diff.x < mag_area_size && diff.y < mag_area_size * ar) 158 | color = texture(combine(g_texture, g_sampler), 159 | norm_mouse_pos + (norm_pixel_pos - norm_mouse_pos) / mag_factor); 160 | 161 | shader_out<0, vec4> = color; 162 | } 163 | 164 | -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/stdafx.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/stdafx.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | // stdafx.h : include file for standard system include files, 13 | // or project specific include files that are used frequently, but 14 | // are changed infrequently. 15 | 16 | #pragma once 17 | 18 | #ifndef WIN32_LEAN_AND_MEAN 19 | #define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers. 20 | #endif 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | #include 30 | #include 31 | #include "d3dx12.h" 32 | #include 33 | 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/wave_frag.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/WaveIntrinsics/wave_frag.dxil -------------------------------------------------------------------------------- /dxil/WaveIntrinsics/wave_vert.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/WaveIntrinsics/wave_vert.dxil -------------------------------------------------------------------------------- /dxil/dxil-signing/README.md: -------------------------------------------------------------------------------- 1 | # DXIL Signing Utility 2 | 3 | Based on work from Graham Wihlidal's post: 4 | https://www.wihlidal.com/blog/pipeline/2018-09-16-dxil-signing-post-compile/ 5 | 6 | And this github repo: 7 | https://github.com/gwihlidal/dxil-signing -------------------------------------------------------------------------------- /dxil/dxil-signing/main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include "CLI11.hpp" 6 | #include "dxcapi.h" 7 | 8 | #pragma comment(lib, "d3dcompiler") 9 | 10 | using Microsoft::WRL::ComPtr; 11 | 12 | struct DxilMinimalHeader 13 | { 14 | UINT32 four_cc; 15 | UINT32 hash_digest[4]; 16 | }; 17 | 18 | inline bool is_dxil_signed(void* buffer) 19 | { 20 | DxilMinimalHeader* header = reinterpret_cast(buffer); 21 | bool has_digest = false; 22 | has_digest |= header->hash_digest[0] != 0x0; 23 | has_digest |= header->hash_digest[1] != 0x0; 24 | has_digest |= header->hash_digest[2] != 0x0; 25 | has_digest |= header->hash_digest[3] != 0x0; 26 | return has_digest; 27 | } 28 | 29 | int main(int argc, const char* argv[]) 30 | { 31 | CLI::App app{ "DXIL Signing Utility" }; 32 | 33 | std::string filename = ""; 34 | app.add_option("filename", filename, "File to change in-place")->required(); 35 | 36 | CLI11_PARSE(app, argc, argv); 37 | 38 | std::cout << "Loading input file: " << filename << std::endl; 39 | 40 | FILE* f = fopen(filename.c_str(), "r+b"); 41 | if (f == nullptr) 42 | { 43 | std::cout << "Failed to open input file" << std::endl; 44 | exit(1); 45 | } 46 | 47 | fseek(f, 0, SEEK_END); 48 | size_t input_size = ftell(f); 49 | fseek(f, 0, SEEK_SET); 50 | 51 | std::vector dxil_data; 52 | dxil_data.resize(input_size); 53 | 54 | size_t bytes_read = fread(dxil_data.data(), 1, dxil_data.size(), f); 55 | 56 | if (bytes_read != dxil_data.size() || bytes_read < sizeof(DxilMinimalHeader)) 57 | { 58 | std::cout << "Failed to read input file" << std::endl; 59 | exit(1); 60 | } 61 | 62 | // Ensure the binary isn't already signed 63 | if (is_dxil_signed(dxil_data.data())) 64 | { 65 | std::cout << "Input file is already signed" << std::endl; 66 | exit(1); 67 | } 68 | 69 | HMODULE dxil_module = ::LoadLibrary(L"C:\\Program Files (x86)\\Windows Kits\\10\\Redist\\D3D\\x64\\dxil.dll"); 70 | if (dxil_module == nullptr) 71 | { 72 | std::cout << "Failed to load dxil.dll" << std::endl; 73 | exit(1); 74 | } 75 | 76 | DxcCreateInstanceProc dxil_create_func = (DxcCreateInstanceProc)GetProcAddress(dxil_module, "DxcCreateInstance"); 77 | if (dxil_create_func == nullptr) 78 | { 79 | std::cout << "Failed to get dxil create proc" << std::endl; 80 | exit(1); 81 | } 82 | 83 | ComPtr blob; 84 | D3DCreateBlob(dxil_data.size(), &blob); 85 | 86 | // Copy into the blob. 87 | memcpy(blob->GetBufferPointer(), dxil_data.data(), dxil_data.size()); 88 | 89 | ComPtr validator; 90 | if (FAILED(dxil_create_func(CLSID_DxcValidator, __uuidof(IDxcValidator), (void**)&validator))) 91 | { 92 | std::cout << "Failed to create validator instance" << std::endl; 93 | exit(1); 94 | } 95 | 96 | // Query validation version info 97 | { 98 | ComPtr version_info; 99 | if (FAILED(validator->QueryInterface(__uuidof(IDxcVersionInfo), (void**)&version_info))) 100 | { 101 | std::cout << "Failed to query version info interface" << std::endl; 102 | exit(1); 103 | } 104 | 105 | UINT32 major = 0; 106 | UINT32 minor = 0; 107 | version_info->GetVersion(&major, &minor); 108 | std::cout << "Validator version: " << major << "." << minor << std::endl; 109 | } 110 | 111 | ComPtr result; 112 | if (FAILED(validator->Validate((IDxcBlob*)blob.Get(), DxcValidatorFlags_InPlaceEdit /* avoid extra copy owned by dxil.dll */, &result))) 113 | { 114 | std::cout << "Failed to validate dxil container" << std::endl; 115 | exit(1); 116 | } 117 | 118 | HRESULT validateStatus; 119 | if (FAILED(result->GetStatus(&validateStatus))) 120 | { 121 | std::cout << "Failed to get dxil validate status" << std::endl; 122 | exit(1); 123 | } 124 | 125 | if (FAILED(validateStatus)) 126 | { 127 | std::cout << "The dxil container failed validation" << std::endl; 128 | 129 | ComPtr error; 130 | result->GetErrorBuffer((IDxcBlobEncoding**)error.GetAddressOf()); 131 | 132 | std::string errorString((const char*)error->GetBufferPointer(), error->GetBufferSize()); 133 | 134 | std::cout << "Error: " << std::endl << errorString << std::endl; 135 | 136 | exit(2); 137 | } 138 | result.Reset(); 139 | 140 | validator = nullptr; 141 | 142 | // Ensure the binary is now signed 143 | if (!is_dxil_signed(blob->GetBufferPointer())) 144 | { 145 | std::cout << "Signing failed!" << std::endl; 146 | exit(1); 147 | } 148 | 149 | std::cout << "Saving output file: " << filename << std::endl; 150 | 151 | fseek(f, 0, SEEK_SET); 152 | size_t bytes_written = fwrite(blob->GetBufferPointer(), 1, blob->GetBufferSize(), f); 153 | 154 | if (bytes_written != dxil_data.size()) 155 | { 156 | std::cout << "Failed to write output file" << std::endl; 157 | exit(1); 158 | } 159 | 160 | blob->Release(); 161 | 162 | fclose(f); 163 | 164 | ::FreeLibrary(dxil_module); 165 | } -------------------------------------------------------------------------------- /dxil/dxil.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 12.00 3 | # Visual Studio Version 16 4 | VisualStudioVersion = 16.0.31005.135 5 | MinimumVisualStudioVersion = 10.0.40219.1 6 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shadertoy", "shadertoy\shadertoy.vcxproj", "{8A49F3D0-6B84-4314-91CC-9C936484C258}" 7 | EndProject 8 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tessellation", "tessellation\tessellation.vcxproj", "{48201281-F953-4A7C-82C7-29D403D808A7}" 9 | EndProject 10 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "WaveIntrinsics", "WaveIntrinsics\WaveIntrinsics.vcxproj", "{778D355D-3E50-401A-BCA0-A8A786D31292}" 11 | EndProject 12 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "nbody", "nbody\nbody.vcxproj", "{5BF9B015-02CB-426C-8FDC-2A03384D0DBE}" 13 | EndProject 14 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "dxil-signing", "dxil-signing\dxil-signing.vcxproj", "{190FA3CB-63EC-42F4-A4E6-605234532C46}" 15 | EndProject 16 | Global 17 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 18 | Debug|x64 = Debug|x64 19 | Debug|x86 = Debug|x86 20 | Release|x64 = Release|x64 21 | Release|x86 = Release|x86 22 | EndGlobalSection 23 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 24 | {8A49F3D0-6B84-4314-91CC-9C936484C258}.Debug|x64.ActiveCfg = Debug|x64 25 | {8A49F3D0-6B84-4314-91CC-9C936484C258}.Debug|x64.Build.0 = Debug|x64 26 | {8A49F3D0-6B84-4314-91CC-9C936484C258}.Debug|x86.ActiveCfg = Debug|Win32 27 | {8A49F3D0-6B84-4314-91CC-9C936484C258}.Debug|x86.Build.0 = Debug|Win32 28 | {8A49F3D0-6B84-4314-91CC-9C936484C258}.Release|x64.ActiveCfg = Release|x64 29 | {8A49F3D0-6B84-4314-91CC-9C936484C258}.Release|x64.Build.0 = Release|x64 30 | {8A49F3D0-6B84-4314-91CC-9C936484C258}.Release|x86.ActiveCfg = Release|Win32 31 | {8A49F3D0-6B84-4314-91CC-9C936484C258}.Release|x86.Build.0 = Release|Win32 32 | {48201281-F953-4A7C-82C7-29D403D808A7}.Debug|x64.ActiveCfg = Debug|x64 33 | {48201281-F953-4A7C-82C7-29D403D808A7}.Debug|x64.Build.0 = Debug|x64 34 | {48201281-F953-4A7C-82C7-29D403D808A7}.Debug|x86.ActiveCfg = Debug|Win32 35 | {48201281-F953-4A7C-82C7-29D403D808A7}.Debug|x86.Build.0 = Debug|Win32 36 | {48201281-F953-4A7C-82C7-29D403D808A7}.Release|x64.ActiveCfg = Release|x64 37 | {48201281-F953-4A7C-82C7-29D403D808A7}.Release|x64.Build.0 = Release|x64 38 | {48201281-F953-4A7C-82C7-29D403D808A7}.Release|x86.ActiveCfg = Release|Win32 39 | {48201281-F953-4A7C-82C7-29D403D808A7}.Release|x86.Build.0 = Release|Win32 40 | {778D355D-3E50-401A-BCA0-A8A786D31292}.Debug|x64.ActiveCfg = Debug|x64 41 | {778D355D-3E50-401A-BCA0-A8A786D31292}.Debug|x64.Build.0 = Debug|x64 42 | {778D355D-3E50-401A-BCA0-A8A786D31292}.Debug|x86.ActiveCfg = Debug|Win32 43 | {778D355D-3E50-401A-BCA0-A8A786D31292}.Debug|x86.Build.0 = Debug|Win32 44 | {778D355D-3E50-401A-BCA0-A8A786D31292}.Release|x64.ActiveCfg = Release|x64 45 | {778D355D-3E50-401A-BCA0-A8A786D31292}.Release|x64.Build.0 = Release|x64 46 | {778D355D-3E50-401A-BCA0-A8A786D31292}.Release|x86.ActiveCfg = Release|Win32 47 | {778D355D-3E50-401A-BCA0-A8A786D31292}.Release|x86.Build.0 = Release|Win32 48 | {5BF9B015-02CB-426C-8FDC-2A03384D0DBE}.Debug|x64.ActiveCfg = Debug|x64 49 | {5BF9B015-02CB-426C-8FDC-2A03384D0DBE}.Debug|x64.Build.0 = Debug|x64 50 | {5BF9B015-02CB-426C-8FDC-2A03384D0DBE}.Debug|x86.ActiveCfg = Debug|Win32 51 | {5BF9B015-02CB-426C-8FDC-2A03384D0DBE}.Debug|x86.Build.0 = Debug|Win32 52 | {5BF9B015-02CB-426C-8FDC-2A03384D0DBE}.Release|x64.ActiveCfg = Release|x64 53 | {5BF9B015-02CB-426C-8FDC-2A03384D0DBE}.Release|x64.Build.0 = Release|x64 54 | {5BF9B015-02CB-426C-8FDC-2A03384D0DBE}.Release|x86.ActiveCfg = Release|Win32 55 | {5BF9B015-02CB-426C-8FDC-2A03384D0DBE}.Release|x86.Build.0 = Release|Win32 56 | {190FA3CB-63EC-42F4-A4E6-605234532C46}.Debug|x64.ActiveCfg = Debug|x64 57 | {190FA3CB-63EC-42F4-A4E6-605234532C46}.Debug|x64.Build.0 = Debug|x64 58 | {190FA3CB-63EC-42F4-A4E6-605234532C46}.Debug|x86.ActiveCfg = Debug|Win32 59 | {190FA3CB-63EC-42F4-A4E6-605234532C46}.Debug|x86.Build.0 = Debug|Win32 60 | {190FA3CB-63EC-42F4-A4E6-605234532C46}.Release|x64.ActiveCfg = Release|x64 61 | {190FA3CB-63EC-42F4-A4E6-605234532C46}.Release|x64.Build.0 = Release|x64 62 | {190FA3CB-63EC-42F4-A4E6-605234532C46}.Release|x86.ActiveCfg = Release|Win32 63 | {190FA3CB-63EC-42F4-A4E6-605234532C46}.Release|x86.Build.0 = Release|Win32 64 | EndGlobalSection 65 | GlobalSection(SolutionProperties) = preSolution 66 | HideSolutionNode = FALSE 67 | EndGlobalSection 68 | GlobalSection(ExtensibilityGlobals) = postSolution 69 | SolutionGuid = {46C9E0C8-CAAB-44C2-A585-41ECF7BCC484} 70 | EndGlobalSection 71 | EndGlobal 72 | -------------------------------------------------------------------------------- /dxil/nbody/DXSample.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "DXSample.h" 14 | 15 | using namespace Microsoft::WRL; 16 | 17 | DXSample::DXSample(UINT width, UINT height, std::wstring name) : 18 | m_width(width), 19 | m_height(height), 20 | m_title(name), 21 | m_useWarpDevice(false) 22 | { 23 | WCHAR assetsPath[512]; 24 | GetAssetsPath(assetsPath, _countof(assetsPath)); 25 | m_assetsPath = assetsPath; 26 | 27 | m_aspectRatio = static_cast(width) / static_cast(height); 28 | } 29 | 30 | DXSample::~DXSample() 31 | { 32 | } 33 | 34 | // Helper function for resolving the full path of assets. 35 | std::wstring DXSample::GetAssetFullPath(LPCWSTR assetName) 36 | { 37 | return m_assetsPath + assetName; 38 | } 39 | 40 | // Helper function for acquiring the first available hardware adapter that supports Direct3D 12. 41 | // If no such adapter can be found, *ppAdapter will be set to nullptr. 42 | _Use_decl_annotations_ 43 | void DXSample::GetHardwareAdapter( 44 | IDXGIFactory1* pFactory, 45 | IDXGIAdapter1** ppAdapter, 46 | bool requestHighPerformanceAdapter) 47 | { 48 | *ppAdapter = nullptr; 49 | 50 | ComPtr adapter; 51 | 52 | ComPtr factory6; 53 | if (SUCCEEDED(pFactory->QueryInterface(IID_PPV_ARGS(&factory6)))) 54 | { 55 | for ( 56 | UINT adapterIndex = 0; 57 | DXGI_ERROR_NOT_FOUND != factory6->EnumAdapterByGpuPreference( 58 | adapterIndex, 59 | requestHighPerformanceAdapter == true ? DXGI_GPU_PREFERENCE_HIGH_PERFORMANCE : DXGI_GPU_PREFERENCE_UNSPECIFIED, 60 | IID_PPV_ARGS(&adapter)); 61 | ++adapterIndex) 62 | { 63 | DXGI_ADAPTER_DESC1 desc; 64 | adapter->GetDesc1(&desc); 65 | 66 | if (desc.Flags & DXGI_ADAPTER_FLAG_SOFTWARE) 67 | { 68 | // Don't select the Basic Render Driver adapter. 69 | // If you want a software adapter, pass in "/warp" on the command line. 70 | continue; 71 | } 72 | 73 | // Check to see whether the adapter supports Direct3D 12, but don't create the 74 | // actual device yet. 75 | if (SUCCEEDED(D3D12CreateDevice(adapter.Get(), D3D_FEATURE_LEVEL_11_0, _uuidof(ID3D12Device), nullptr))) 76 | { 77 | break; 78 | } 79 | } 80 | } 81 | else 82 | { 83 | for (UINT adapterIndex = 0; DXGI_ERROR_NOT_FOUND != pFactory->EnumAdapters1(adapterIndex, &adapter); ++adapterIndex) 84 | { 85 | DXGI_ADAPTER_DESC1 desc; 86 | adapter->GetDesc1(&desc); 87 | 88 | if (desc.Flags & DXGI_ADAPTER_FLAG_SOFTWARE) 89 | { 90 | // Don't select the Basic Render Driver adapter. 91 | // If you want a software adapter, pass in "/warp" on the command line. 92 | continue; 93 | } 94 | 95 | // Check to see whether the adapter supports Direct3D 12, but don't create the 96 | // actual device yet. 97 | if (SUCCEEDED(D3D12CreateDevice(adapter.Get(), D3D_FEATURE_LEVEL_11_0, _uuidof(ID3D12Device), nullptr))) 98 | { 99 | break; 100 | } 101 | } 102 | } 103 | 104 | *ppAdapter = adapter.Detach(); 105 | } 106 | 107 | // Helper function for setting the window's title text. 108 | void DXSample::SetCustomWindowText(LPCWSTR text) 109 | { 110 | std::wstring windowText = m_title + L": " + text; 111 | SetWindowText(Win32Application::GetHwnd(), windowText.c_str()); 112 | } 113 | 114 | // Helper function for parsing any supplied command line args. 115 | _Use_decl_annotations_ 116 | void DXSample::ParseCommandLineArgs(WCHAR* argv[], int argc) 117 | { 118 | for (int i = 1; i < argc; ++i) 119 | { 120 | if (_wcsnicmp(argv[i], L"-warp", wcslen(argv[i])) == 0 || 121 | _wcsnicmp(argv[i], L"/warp", wcslen(argv[i])) == 0) 122 | { 123 | m_useWarpDevice = true; 124 | m_title = m_title + L" (WARP)"; 125 | } 126 | } 127 | } 128 | -------------------------------------------------------------------------------- /dxil/nbody/DXSample.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "DXSampleHelper.h" 15 | #include "Win32Application.h" 16 | 17 | class DXSample 18 | { 19 | public: 20 | DXSample(UINT width, UINT height, std::wstring name); 21 | virtual ~DXSample(); 22 | 23 | virtual void OnInit() = 0; 24 | virtual void OnUpdate() = 0; 25 | virtual void OnRender() = 0; 26 | virtual void OnDestroy() = 0; 27 | 28 | // Samples override the event handlers to handle specific messages. 29 | virtual void OnKeyDown(UINT8 /*key*/) {} 30 | virtual void OnKeyUp(UINT8 /*key*/) {} 31 | 32 | // Accessors. 33 | UINT GetWidth() const { return m_width; } 34 | UINT GetHeight() const { return m_height; } 35 | const WCHAR* GetTitle() const { return m_title.c_str(); } 36 | 37 | void ParseCommandLineArgs(_In_reads_(argc) WCHAR* argv[], int argc); 38 | 39 | protected: 40 | std::wstring GetAssetFullPath(LPCWSTR assetName); 41 | 42 | void GetHardwareAdapter( 43 | _In_ IDXGIFactory1* pFactory, 44 | _Outptr_result_maybenull_ IDXGIAdapter1** ppAdapter, 45 | bool requestHighPerformanceAdapter = false); 46 | 47 | void SetCustomWindowText(LPCWSTR text); 48 | 49 | // Viewport dimensions. 50 | UINT m_width; 51 | UINT m_height; 52 | float m_aspectRatio; 53 | 54 | // Adapter info. 55 | bool m_useWarpDevice; 56 | 57 | private: 58 | // Root assets path. 59 | std::wstring m_assetsPath; 60 | 61 | // Window title. 62 | std::wstring m_title; 63 | }; 64 | -------------------------------------------------------------------------------- /dxil/nbody/Main.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "D3D12nBodyGravity.h" 14 | 15 | _Use_decl_annotations_ 16 | int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR, int nCmdShow) 17 | { 18 | D3D12nBodyGravity sample(1280, 720, L"D3D12 n-Body Gravity Simulation"); 19 | return Win32Application::Run(&sample, hInstance, nCmdShow); 20 | } 21 | -------------------------------------------------------------------------------- /dxil/nbody/SimpleCamera.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "SimpleCamera.h" 14 | 15 | SimpleCamera::SimpleCamera(): 16 | m_initialPosition(0, 0, 0), 17 | m_position(m_initialPosition), 18 | m_yaw(XM_PI), 19 | m_pitch(0.0f), 20 | m_lookDirection(0, 0, -1), 21 | m_upDirection(0, 1, 0), 22 | m_moveSpeed(20.0f), 23 | m_turnSpeed(XM_PIDIV2), 24 | m_keysPressed{} 25 | { 26 | } 27 | 28 | void SimpleCamera::Init(XMFLOAT3 position) 29 | { 30 | m_initialPosition = position; 31 | Reset(); 32 | } 33 | 34 | void SimpleCamera::SetMoveSpeed(float unitsPerSecond) 35 | { 36 | m_moveSpeed = unitsPerSecond; 37 | } 38 | 39 | void SimpleCamera::SetTurnSpeed(float radiansPerSecond) 40 | { 41 | m_turnSpeed = radiansPerSecond; 42 | } 43 | 44 | void SimpleCamera::Reset() 45 | { 46 | m_position = m_initialPosition; 47 | m_yaw = XM_PI; 48 | m_pitch = 0.0f; 49 | m_lookDirection = { 0, 0, -1 }; 50 | } 51 | 52 | void SimpleCamera::Update(float elapsedSeconds) 53 | { 54 | // Calculate the move vector in camera space. 55 | XMFLOAT3 move(0, 0, 0); 56 | 57 | if (m_keysPressed.a) 58 | move.x -= 1.0f; 59 | if (m_keysPressed.d) 60 | move.x += 1.0f; 61 | if (m_keysPressed.w) 62 | move.z -= 1.0f; 63 | if (m_keysPressed.s) 64 | move.z += 1.0f; 65 | 66 | if (fabs(move.x) > 0.1f && fabs(move.z) > 0.1f) 67 | { 68 | XMVECTOR vector = XMVector3Normalize(XMLoadFloat3(&move)); 69 | move.x = XMVectorGetX(vector); 70 | move.z = XMVectorGetZ(vector); 71 | } 72 | 73 | float moveInterval = m_moveSpeed * elapsedSeconds; 74 | float rotateInterval = m_turnSpeed * elapsedSeconds; 75 | 76 | if (m_keysPressed.left) 77 | m_yaw += rotateInterval; 78 | if (m_keysPressed.right) 79 | m_yaw -= rotateInterval; 80 | if (m_keysPressed.up) 81 | m_pitch += rotateInterval; 82 | if (m_keysPressed.down) 83 | m_pitch -= rotateInterval; 84 | 85 | // Prevent looking too far up or down. 86 | m_pitch = min(m_pitch, XM_PIDIV4); 87 | m_pitch = max(-XM_PIDIV4, m_pitch); 88 | 89 | // Move the camera in model space. 90 | float x = move.x * -cosf(m_yaw) - move.z * sinf(m_yaw); 91 | float z = move.x * sinf(m_yaw) - move.z * cosf(m_yaw); 92 | m_position.x += x * moveInterval; 93 | m_position.z += z * moveInterval; 94 | 95 | // Determine the look direction. 96 | float r = cosf(m_pitch); 97 | m_lookDirection.x = r * sinf(m_yaw); 98 | m_lookDirection.y = sinf(m_pitch); 99 | m_lookDirection.z = r * cosf(m_yaw); 100 | } 101 | 102 | XMMATRIX SimpleCamera::GetViewMatrix() 103 | { 104 | return XMMatrixLookToRH(XMLoadFloat3(&m_position), XMLoadFloat3(&m_lookDirection), XMLoadFloat3(&m_upDirection)); 105 | } 106 | 107 | XMMATRIX SimpleCamera::GetProjectionMatrix(float fov, float aspectRatio, float nearPlane, float farPlane) 108 | { 109 | return XMMatrixPerspectiveFovRH(fov, aspectRatio, nearPlane, farPlane); 110 | } 111 | 112 | void SimpleCamera::OnKeyDown(WPARAM key) 113 | { 114 | switch (key) 115 | { 116 | case 'W': 117 | m_keysPressed.w = true; 118 | break; 119 | case 'A': 120 | m_keysPressed.a = true; 121 | break; 122 | case 'S': 123 | m_keysPressed.s = true; 124 | break; 125 | case 'D': 126 | m_keysPressed.d = true; 127 | break; 128 | case VK_LEFT: 129 | m_keysPressed.left = true; 130 | break; 131 | case VK_RIGHT: 132 | m_keysPressed.right = true; 133 | break; 134 | case VK_UP: 135 | m_keysPressed.up = true; 136 | break; 137 | case VK_DOWN: 138 | m_keysPressed.down = true; 139 | break; 140 | case VK_ESCAPE: 141 | Reset(); 142 | break; 143 | } 144 | } 145 | 146 | void SimpleCamera::OnKeyUp(WPARAM key) 147 | { 148 | switch (key) 149 | { 150 | case 'W': 151 | m_keysPressed.w = false; 152 | break; 153 | case 'A': 154 | m_keysPressed.a = false; 155 | break; 156 | case 'S': 157 | m_keysPressed.s = false; 158 | break; 159 | case 'D': 160 | m_keysPressed.d = false; 161 | break; 162 | case VK_LEFT: 163 | m_keysPressed.left = false; 164 | break; 165 | case VK_RIGHT: 166 | m_keysPressed.right = false; 167 | break; 168 | case VK_UP: 169 | m_keysPressed.up = false; 170 | break; 171 | case VK_DOWN: 172 | m_keysPressed.down = false; 173 | break; 174 | } 175 | } 176 | -------------------------------------------------------------------------------- /dxil/nbody/SimpleCamera.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | using namespace DirectX; 15 | 16 | class SimpleCamera 17 | { 18 | public: 19 | SimpleCamera(); 20 | 21 | void Init(XMFLOAT3 position); 22 | void Update(float elapsedSeconds); 23 | XMMATRIX GetViewMatrix(); 24 | XMMATRIX GetProjectionMatrix(float fov, float aspectRatio, float nearPlane = 1.0f, float farPlane = 1000.0f); 25 | void SetMoveSpeed(float unitsPerSecond); 26 | void SetTurnSpeed(float radiansPerSecond); 27 | 28 | void OnKeyDown(WPARAM key); 29 | void OnKeyUp(WPARAM key); 30 | 31 | private: 32 | void Reset(); 33 | 34 | struct KeysPressed 35 | { 36 | bool w; 37 | bool a; 38 | bool s; 39 | bool d; 40 | 41 | bool left; 42 | bool right; 43 | bool up; 44 | bool down; 45 | }; 46 | 47 | XMFLOAT3 m_initialPosition; 48 | XMFLOAT3 m_position; 49 | float m_yaw; // Relative to the +z axis. 50 | float m_pitch; // Relative to the xz plane. 51 | XMFLOAT3 m_lookDirection; 52 | XMFLOAT3 m_upDirection; 53 | float m_moveSpeed; // Speed at which the camera moves, in units per second. 54 | float m_turnSpeed; // Speed at which the camera turns, in radians per second. 55 | 56 | KeysPressed m_keysPressed; 57 | }; 58 | -------------------------------------------------------------------------------- /dxil/nbody/Win32Application.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "Win32Application.h" 14 | 15 | HWND Win32Application::m_hwnd = nullptr; 16 | 17 | int Win32Application::Run(DXSample* pSample, HINSTANCE hInstance, int nCmdShow) 18 | { 19 | // Parse the command line parameters 20 | int argc; 21 | LPWSTR* argv = CommandLineToArgvW(GetCommandLineW(), &argc); 22 | pSample->ParseCommandLineArgs(argv, argc); 23 | LocalFree(argv); 24 | 25 | // Initialize the window class. 26 | WNDCLASSEX windowClass = { 0 }; 27 | windowClass.cbSize = sizeof(WNDCLASSEX); 28 | windowClass.style = CS_HREDRAW | CS_VREDRAW; 29 | windowClass.lpfnWndProc = WindowProc; 30 | windowClass.hInstance = hInstance; 31 | windowClass.hCursor = LoadCursor(NULL, IDC_ARROW); 32 | windowClass.lpszClassName = L"DXSampleClass"; 33 | RegisterClassEx(&windowClass); 34 | 35 | RECT windowRect = { 0, 0, static_cast(pSample->GetWidth()), static_cast(pSample->GetHeight()) }; 36 | AdjustWindowRect(&windowRect, WS_OVERLAPPEDWINDOW, FALSE); 37 | 38 | // Create the window and store a handle to it. 39 | m_hwnd = CreateWindow( 40 | windowClass.lpszClassName, 41 | pSample->GetTitle(), 42 | WS_OVERLAPPEDWINDOW, 43 | CW_USEDEFAULT, 44 | CW_USEDEFAULT, 45 | windowRect.right - windowRect.left, 46 | windowRect.bottom - windowRect.top, 47 | nullptr, // We have no parent window. 48 | nullptr, // We aren't using menus. 49 | hInstance, 50 | pSample); 51 | 52 | // Initialize the sample. OnInit is defined in each child-implementation of DXSample. 53 | pSample->OnInit(); 54 | 55 | ShowWindow(m_hwnd, nCmdShow); 56 | 57 | // Main sample loop. 58 | MSG msg = {}; 59 | while (msg.message != WM_QUIT) 60 | { 61 | // Process any messages in the queue. 62 | if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE)) 63 | { 64 | TranslateMessage(&msg); 65 | DispatchMessage(&msg); 66 | } 67 | } 68 | 69 | pSample->OnDestroy(); 70 | 71 | // Return this part of the WM_QUIT message to Windows. 72 | return static_cast(msg.wParam); 73 | } 74 | 75 | // Main message handler for the sample. 76 | LRESULT CALLBACK Win32Application::WindowProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) 77 | { 78 | DXSample* pSample = reinterpret_cast(GetWindowLongPtr(hWnd, GWLP_USERDATA)); 79 | 80 | switch (message) 81 | { 82 | case WM_CREATE: 83 | { 84 | // Save the DXSample* passed in to CreateWindow. 85 | LPCREATESTRUCT pCreateStruct = reinterpret_cast(lParam); 86 | SetWindowLongPtr(hWnd, GWLP_USERDATA, reinterpret_cast(pCreateStruct->lpCreateParams)); 87 | } 88 | return 0; 89 | 90 | case WM_KEYDOWN: 91 | if (pSample) 92 | { 93 | pSample->OnKeyDown(static_cast(wParam)); 94 | } 95 | return 0; 96 | 97 | case WM_KEYUP: 98 | if (pSample) 99 | { 100 | pSample->OnKeyUp(static_cast(wParam)); 101 | } 102 | return 0; 103 | 104 | case WM_PAINT: 105 | if (pSample) 106 | { 107 | pSample->OnUpdate(); 108 | pSample->OnRender(); 109 | } 110 | return 0; 111 | 112 | case WM_DESTROY: 113 | PostQuitMessage(0); 114 | return 0; 115 | } 116 | 117 | // Handle any messages the switch statement didn't. 118 | return DefWindowProc(hWnd, message, wParam, lParam); 119 | } 120 | -------------------------------------------------------------------------------- /dxil/nbody/Win32Application.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "DXSample.h" 15 | 16 | class DXSample; 17 | 18 | class Win32Application 19 | { 20 | public: 21 | static int Run(DXSample* pSample, HINSTANCE hInstance, int nCmdShow); 22 | static HWND GetHwnd() { return m_hwnd; } 23 | 24 | protected: 25 | static LRESULT CALLBACK WindowProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam); 26 | 27 | private: 28 | static HWND m_hwnd; 29 | }; 30 | -------------------------------------------------------------------------------- /dxil/nbody/build_shaders.bat: -------------------------------------------------------------------------------- 1 | wsl -e circle -shader -emit-dxil -c -E integrate_shader shaders.cxx -o integrate.dxil 2 | dxil-signing.exe integrate.dxil 3 | wsl -e circle -shader -emit-dxil -c -E vert shaders.cxx -o vert.dxil 4 | dxil-signing.exe vert.dxil 5 | wsl -e circle -shader -emit-dxil -c -E geom shaders.cxx -o geom.dxil 6 | dxil-signing.exe geom.dxil 7 | wsl -e circle -shader -emit-dxil -c -E frag shaders.cxx -o frag.dxil 8 | dxil-signing.exe frag.dxil -------------------------------------------------------------------------------- /dxil/nbody/frag.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/nbody/frag.dxil -------------------------------------------------------------------------------- /dxil/nbody/geom.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/nbody/geom.dxil -------------------------------------------------------------------------------- /dxil/nbody/integrate.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/nbody/integrate.dxil -------------------------------------------------------------------------------- /dxil/nbody/nbody.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | {4FC737F1-C7A5-4376-A066-2A32D752A2FF} 6 | cpp;c;cc;cxx;c++;cppm;ixx;def;odl;idl;hpj;bat;asm;asmx 7 | 8 | 9 | {93995380-89BD-4b04-88EB-625FBE52EBFB} 10 | h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd 11 | 12 | 13 | {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} 14 | rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms 15 | 16 | 17 | 18 | 19 | Header Files 20 | 21 | 22 | Header Files 23 | 24 | 25 | Header Files 26 | 27 | 28 | Header Files 29 | 30 | 31 | Header Files 32 | 33 | 34 | Header Files 35 | 36 | 37 | Header Files 38 | 39 | 40 | Header Files 41 | 42 | 43 | 44 | 45 | Source Files 46 | 47 | 48 | Source Files 49 | 50 | 51 | Source Files 52 | 53 | 54 | Source Files 55 | 56 | 57 | Source Files 58 | 59 | 60 | Source Files 61 | 62 | 63 | -------------------------------------------------------------------------------- /dxil/nbody/nbody.vcxproj.user: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | -------------------------------------------------------------------------------- /dxil/nbody/readme.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_type: sample 3 | languages: 4 | - cpp 5 | products: 6 | - windows-api-win32 7 | name: Direct3D 12 n-body gravity sample 8 | urlFragment: d3d12-n-body-gravity-sample-win32 9 | description: This sample demonstrates the use of asynchronous compute shaders (multi-engine) to simulate an n-body gravity system. 10 | extendedZipContent: 11 | - path: LICENSE 12 | target: LICENSE 13 | --- 14 | 15 | # Direct3D 12 n-body gravity sample 16 | ![nBodyGravity GUI](src/D3D12nBodyGravity.png) 17 | 18 | This sample demonstrates the use of asynchronous compute shaders (multi-engine) to simulate an n-body gravity system. Graphics commands and compute commands can be recorded simultaneously, and submitted to their respective command queues when the work is ready to begin execution on the GPU. This sample also demonstrates advanced usage of fences to synchronize tasks across command queues. 19 | 20 | ### Optional features 21 | This sample has been updated to build against the Windows 10 Anniversary Update SDK. In this SDK a new revision of Root Signatures is available for Direct3D 12 apps to use. Root Signature 1.1 allows for apps to declare when descriptors in a descriptor heap won't change or the data descriptors point to won't change. This allows the option for drivers to make optimizations that might be possible knowing that something (like a descriptor or the memory it points to) is static for some period of time. -------------------------------------------------------------------------------- /dxil/nbody/shaders.cxx: -------------------------------------------------------------------------------- 1 | template 2 | [[using spirv: in, location(location)]] 3 | type_t shader_in; 4 | 5 | template 6 | [[using spirv: out, location(location)]] 7 | type_t shader_out; 8 | 9 | template 10 | [[using spirv: buffer, readonly, binding(binding)]] 11 | type_t StructuredBuffer[]; 12 | 13 | template 14 | [[using spirv: buffer, binding(binding)]] 15 | type_t RWStructuredBuffer[]; 16 | 17 | struct uniforms_t { 18 | int num_particles; 19 | int num_tiles; 20 | float dt; 21 | float damping; 22 | float G; // gravitational constant 23 | float m; // mass of each particle 24 | float softening = .00125; 25 | float padding; 26 | }; 27 | 28 | // The uniform buffer is bound for integration and rendering. 29 | [[using spirv: uniform, binding(0)]] 30 | uniforms_t uniforms; 31 | 32 | struct particle_t { 33 | vec4 pos, vel; 34 | }; 35 | 36 | // Return the force on a from the influence of b. 37 | inline vec3 interaction(vec3 a, vec3 b, float mass) { 38 | vec3 r = b.xyz - a; 39 | 40 | float softeningSq = uniforms.softening * uniforms.softening; 41 | float dist2 = dot(r, r) + softeningSq; 42 | float invDist = inversesqrt(dist2); 43 | float invDistCube = invDist * invDist * invDist; 44 | 45 | float s = mass * invDistCube; 46 | return s * r; 47 | } 48 | 49 | const int NT = 128; 50 | 51 | extern "C" [[using spirv: comp, local_size(NT)]] 52 | void integrate_shader() { 53 | int tid = glcomp_LocalInvocationID.x; 54 | int gid = glcomp_GlobalInvocationID.x; 55 | 56 | // Load the position for this thread. 57 | particle_t p0; 58 | if(gid < uniforms.num_particles) 59 | p0 = StructuredBuffer<0, particle_t>[gid]; 60 | 61 | // Compute the total acceleration on pos. 62 | vec3 pos = p0.pos.xyz; 63 | vec3 acc { }; 64 | for(int tile = 0; tile < uniforms.num_tiles; ++tile) { 65 | [[spirv::shared]] vec4 cache[NT]; 66 | int index2 = NT * tile + tid; 67 | cache[tid] = index2 < uniforms.num_particles ? 68 | StructuredBuffer<0, particle_t>[index2].pos : vec4(); 69 | glcomp_barrier(); 70 | 71 | // Use @meta for to unroll all NT number of particle interactions. 72 | @meta for(int j = 0; j < NT; ++j) 73 | acc += interaction(pos.xyz, cache[tid].xyz, uniforms.m); 74 | 75 | glcomp_barrier(); 76 | } 77 | 78 | if(gid < uniforms.num_particles) { 79 | // Load the velocity for this thread. 80 | vec3 vel = p0.vel.xyz; 81 | 82 | // Update the velocity and position. 83 | // Draw the particle back to the center. 84 | vel += uniforms.dt * acc; 85 | vel *= uniforms.damping; 86 | 87 | pos += uniforms.dt * vel; 88 | 89 | // Store the updated position and velocity. 90 | RWStructuredBuffer<0, particle_t>[gid] = { vec4(pos, 0), vec4(vel, 0) }; 91 | } 92 | } 93 | 94 | //////////////////////////////////////////////////////////////////////////////// 95 | 96 | extern "C" [[spirv::vert]] 97 | void vert() { 98 | // Load the particle data. 99 | particle_t particle = StructuredBuffer<0, particle_t>[glvert_VertexIndex]; 100 | 101 | // Modulate the color. 102 | float mag = particle.vel.w / 9; 103 | shader_out<0, vec4> = mix(vec4(1, .1, .1, 1), shader_in<0, vec4>, mag); 104 | 105 | // Pass the position out. 106 | // shader_out<1, vec3> = particle.pos.xyz; 107 | glvert_Output.Position = particle.pos; 108 | } 109 | 110 | struct gs_uniforms_t { 111 | mat4 worldViewProj; 112 | mat4 invView; 113 | }; 114 | [[using spirv: uniform, binding(0)]] 115 | gs_uniforms_t gs_uniforms; 116 | 117 | extern "C" [[spirv::geom(points, triangle_strip, 4)]] 118 | void geom() { 119 | 120 | static constexpr vec3 corners[] { 121 | -1, 1, 0, 122 | 1, 1, 0, 123 | -1, -1, 0, 124 | 1, -1, 0 125 | }; 126 | static constexpr vec2 uv[] { 127 | 0, 0, 128 | 1, 0, 129 | 0, 1, 130 | 1, 1 131 | }; 132 | float radius = 10; 133 | 134 | // Load color and position from the vertex shader. 135 | vec4 color = shader_in<0, vec4[1]>[0]; 136 | vec3 center = glgeom_Input[0].Position.xyz;// shader_in<1, vec3[1]>[0]; 137 | 138 | @meta for(int i = 0; i < 4; ++i) {{ 139 | // Write a billboard corner. 140 | vec3 pos = center + (mat3)gs_uniforms.invView * (radius * corners[i]); 141 | glgeom_Output.Position = gs_uniforms.worldViewProj * vec4(pos, 1); 142 | 143 | // Pass uv and color to the frag shader. 144 | shader_out<0, vec2> = uv[i]; 145 | shader_out<1, vec4> = color; 146 | 147 | glgeom_EmitVertex(); 148 | }} 149 | 150 | glgeom_EndPrimitive(); 151 | } 152 | 153 | extern "C" [[spirv::frag]] 154 | void frag() { 155 | vec2 uv = shader_in<0, vec2>; 156 | vec4 color = shader_in<1, vec4>; 157 | 158 | float intensity = .5f - length(vec2(.5) - uv); 159 | intensity = 2 * clamp(intensity, 0.f, .5f); 160 | shader_out<0, vec4> = vec4(color.xyz, intensity); 161 | } 162 | 163 | -------------------------------------------------------------------------------- /dxil/nbody/stdafx.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | -------------------------------------------------------------------------------- /dxil/nbody/stdafx.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | // stdafx.h : include file for standard system include files, 13 | // or project specific include files that are used frequently, but 14 | // are changed infrequently. 15 | 16 | #pragma once 17 | 18 | #ifndef WIN32_LEAN_AND_MEAN 19 | #define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers. 20 | #endif 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include "d3dx12.h" 29 | 30 | #include 31 | #include 32 | #include 33 | -------------------------------------------------------------------------------- /dxil/nbody/vert.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/nbody/vert.dxil -------------------------------------------------------------------------------- /dxil/semantic.cxx: -------------------------------------------------------------------------------- 1 | // Semantic index 0 is implicit. 2 | [[spirv::in, dxil::semantic("POSITION")]] 3 | vec4 pos0; 4 | 5 | extern "C" [[spirv::vert]] 6 | void f0() { 7 | glvert_Output.Position = pos0; 8 | } 9 | 10 | // Semantic index 1 is explicit. 11 | [[spirv::in, dxil::semantic("POSITION1")]] 12 | vec4 pos1; 13 | 14 | extern "C" [[spirv::vert]] 15 | void f1() { 16 | glvert_Output.Position = pos1; 17 | } 18 | 19 | // Semantic index is a template parameter. 20 | template 21 | [[spirv::in, dxil::semantic("POSITION", index)]] 22 | type_t input_index; 23 | 24 | extern "C" [[spirv::vert]] 25 | void f2() { 26 | glvert_Output.Position = input_index; 27 | } 28 | 29 | // Both semantic name and index are template parameters. 30 | template 31 | [[spirv::in, dxil::semantic(name, index)]] 32 | type_t input_name_index; 33 | 34 | extern "C" [[spirv::vert]] 35 | void f3() { 36 | glvert_Output.Position = input_name_index; 37 | } -------------------------------------------------------------------------------- /dxil/shadertoy/D3D12HelloConstBuffers.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "DXSample.h" 15 | 16 | using namespace DirectX; 17 | 18 | // Note that while ComPtr is used to manage the lifetime of resources on the CPU, 19 | // it has no understanding of the lifetime of resources on the GPU. Apps must account 20 | // for the GPU lifetime of resources to avoid destroying objects that may still be 21 | // referenced by the GPU. 22 | // An example of this can be found in the class method: OnDestroy(). 23 | using Microsoft::WRL::ComPtr; 24 | 25 | class D3D12HelloConstBuffers : public DXSample 26 | { 27 | public: 28 | D3D12HelloConstBuffers(UINT width, UINT height, std::wstring name); 29 | 30 | virtual void OnInit(); 31 | virtual void OnUpdate(); 32 | virtual void OnRender(); 33 | virtual void OnDestroy(); 34 | virtual void OnKeyDown(UINT8 key); 35 | 36 | private: 37 | static const UINT FrameCount = 2; 38 | 39 | struct Vertex 40 | { 41 | float x, y; 42 | }; 43 | 44 | struct alignas(256) SceneConstantBuffer 45 | { 46 | // shader-specific parameters. 47 | float mouse[4]; // .xy is current or last drag position. 48 | // .zw is current or last click. 49 | // .zw is negative if mouse button is up. 50 | float resolution[2]; // width and height of viewport in pixels. 51 | float time; // seconds since simulation started. 52 | }; 53 | 54 | // Pipeline objects. 55 | CD3DX12_VIEWPORT m_viewport; 56 | CD3DX12_RECT m_scissorRect; 57 | ComPtr m_swapChain; 58 | ComPtr m_device; 59 | ComPtr m_renderTargets[FrameCount]; 60 | ComPtr m_commandAllocator; 61 | ComPtr m_commandQueue; 62 | ComPtr m_rootSignature; 63 | ComPtr m_rtvHeap; 64 | ComPtr m_cbvHeap; 65 | std::vector > m_pipelineStates; 66 | ComPtr m_commandList; 67 | UINT m_rtvDescriptorSize; 68 | 69 | // App resources. 70 | ComPtr m_vertexBuffer; 71 | D3D12_VERTEX_BUFFER_VIEW m_vertexBufferView; 72 | ComPtr m_constantBuffer; 73 | SceneConstantBuffer m_constantBufferData; 74 | UINT8* m_pCbvDataBegin; 75 | 76 | // Synchronization objects. 77 | UINT m_frameIndex; 78 | HANDLE m_fenceEvent; 79 | ComPtr m_fence; 80 | UINT64 m_fenceValue; 81 | 82 | LARGE_INTEGER clock_begin; 83 | LARGE_INTEGER clock_frequency; 84 | float elapsed; // Elapsed simulation time. May run at a different rate than the system clock. 85 | int cur_shader = 0; 86 | 87 | void LoadPipeline(); 88 | void LoadAssets(); 89 | void PopulateCommandList(); 90 | void WaitForPreviousFrame(); 91 | }; 92 | -------------------------------------------------------------------------------- /dxil/shadertoy/DXSample.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "DXSample.h" 14 | 15 | using namespace Microsoft::WRL; 16 | 17 | DXSample::DXSample(UINT width, UINT height, std::wstring name) : 18 | m_width(width), 19 | m_height(height), 20 | m_title(name), 21 | m_useWarpDevice(false) 22 | { 23 | WCHAR assetsPath[512]; 24 | GetAssetsPath(assetsPath, _countof(assetsPath)); 25 | m_assetsPath = assetsPath; 26 | 27 | m_aspectRatio = static_cast(width) / static_cast(height); 28 | } 29 | 30 | DXSample::~DXSample() 31 | { 32 | } 33 | 34 | // Helper function for resolving the full path of assets. 35 | std::wstring DXSample::GetAssetFullPath(LPCWSTR assetName) 36 | { 37 | return m_assetsPath + assetName; 38 | } 39 | 40 | // Helper function for acquiring the first available hardware adapter that supports Direct3D 12. 41 | // If no such adapter can be found, *ppAdapter will be set to nullptr. 42 | _Use_decl_annotations_ 43 | void DXSample::GetHardwareAdapter( 44 | IDXGIFactory1* pFactory, 45 | IDXGIAdapter1** ppAdapter, 46 | bool requestHighPerformanceAdapter) 47 | { 48 | *ppAdapter = nullptr; 49 | 50 | ComPtr adapter; 51 | 52 | ComPtr factory6; 53 | if (SUCCEEDED(pFactory->QueryInterface(IID_PPV_ARGS(&factory6)))) 54 | { 55 | for ( 56 | UINT adapterIndex = 0; 57 | DXGI_ERROR_NOT_FOUND != factory6->EnumAdapterByGpuPreference( 58 | adapterIndex, 59 | requestHighPerformanceAdapter == true ? DXGI_GPU_PREFERENCE_HIGH_PERFORMANCE : DXGI_GPU_PREFERENCE_UNSPECIFIED, 60 | IID_PPV_ARGS(&adapter)); 61 | ++adapterIndex) 62 | { 63 | DXGI_ADAPTER_DESC1 desc; 64 | adapter->GetDesc1(&desc); 65 | 66 | if (desc.Flags & DXGI_ADAPTER_FLAG_SOFTWARE) 67 | { 68 | // Don't select the Basic Render Driver adapter. 69 | // If you want a software adapter, pass in "/warp" on the command line. 70 | continue; 71 | } 72 | 73 | // Check to see whether the adapter supports Direct3D 12, but don't create the 74 | // actual device yet. 75 | if (SUCCEEDED(D3D12CreateDevice(adapter.Get(), D3D_FEATURE_LEVEL_11_0, _uuidof(ID3D12Device), nullptr))) 76 | { 77 | break; 78 | } 79 | } 80 | } 81 | else 82 | { 83 | for (UINT adapterIndex = 0; DXGI_ERROR_NOT_FOUND != pFactory->EnumAdapters1(adapterIndex, &adapter); ++adapterIndex) 84 | { 85 | DXGI_ADAPTER_DESC1 desc; 86 | adapter->GetDesc1(&desc); 87 | 88 | if (desc.Flags & DXGI_ADAPTER_FLAG_SOFTWARE) 89 | { 90 | // Don't select the Basic Render Driver adapter. 91 | // If you want a software adapter, pass in "/warp" on the command line. 92 | continue; 93 | } 94 | 95 | // Check to see whether the adapter supports Direct3D 12, but don't create the 96 | // actual device yet. 97 | if (SUCCEEDED(D3D12CreateDevice(adapter.Get(), D3D_FEATURE_LEVEL_11_0, _uuidof(ID3D12Device), nullptr))) 98 | { 99 | break; 100 | } 101 | } 102 | } 103 | 104 | *ppAdapter = adapter.Detach(); 105 | } 106 | 107 | // Helper function for setting the window's title text. 108 | void DXSample::SetCustomWindowText(LPCWSTR text) 109 | { 110 | std::wstring windowText = m_title + L": " + text; 111 | SetWindowText(Win32Application::GetHwnd(), windowText.c_str()); 112 | } 113 | 114 | // Helper function for parsing any supplied command line args. 115 | _Use_decl_annotations_ 116 | void DXSample::ParseCommandLineArgs(WCHAR* argv[], int argc) 117 | { 118 | for (int i = 1; i < argc; ++i) 119 | { 120 | if (_wcsnicmp(argv[i], L"-warp", wcslen(argv[i])) == 0 || 121 | _wcsnicmp(argv[i], L"/warp", wcslen(argv[i])) == 0) 122 | { 123 | m_useWarpDevice = true; 124 | m_title = m_title + L" (WARP)"; 125 | } 126 | } 127 | } 128 | -------------------------------------------------------------------------------- /dxil/shadertoy/DXSample.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "DXSampleHelper.h" 15 | #include "Win32Application.h" 16 | 17 | class DXSample 18 | { 19 | public: 20 | DXSample(UINT width, UINT height, std::wstring name); 21 | virtual ~DXSample(); 22 | 23 | virtual void OnInit() = 0; 24 | virtual void OnUpdate() = 0; 25 | virtual void OnRender() = 0; 26 | virtual void OnDestroy() = 0; 27 | 28 | // Samples override the event handlers to handle specific messages. 29 | virtual void OnKeyDown(UINT8 /*key*/) {} 30 | virtual void OnKeyUp(UINT8 /*key*/) {} 31 | 32 | // Accessors. 33 | UINT GetWidth() const { return m_width; } 34 | UINT GetHeight() const { return m_height; } 35 | const WCHAR* GetTitle() const { return m_title.c_str(); } 36 | 37 | void ParseCommandLineArgs(_In_reads_(argc) WCHAR* argv[], int argc); 38 | 39 | protected: 40 | std::wstring GetAssetFullPath(LPCWSTR assetName); 41 | 42 | void GetHardwareAdapter( 43 | _In_ IDXGIFactory1* pFactory, 44 | _Outptr_result_maybenull_ IDXGIAdapter1** ppAdapter, 45 | bool requestHighPerformanceAdapter = false); 46 | 47 | void SetCustomWindowText(LPCWSTR text); 48 | 49 | // Viewport dimensions. 50 | UINT m_width; 51 | UINT m_height; 52 | float m_aspectRatio; 53 | 54 | // Adapter info. 55 | bool m_useWarpDevice; 56 | 57 | private: 58 | // Root assets path. 59 | std::wstring m_assetsPath; 60 | 61 | // Window title. 62 | std::wstring m_title; 63 | }; 64 | -------------------------------------------------------------------------------- /dxil/shadertoy/Main.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "D3D12HelloConstBuffers.h" 14 | 15 | _Use_decl_annotations_ 16 | int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR, int nCmdShow) { 17 | D3D12HelloConstBuffers sample(1280, 720, L"Shadertoy sample"); 18 | 19 | 20 | return Win32Application::Run(&sample, GetModuleHandle(0), SW_SHOW); 21 | } 22 | -------------------------------------------------------------------------------- /dxil/shadertoy/Win32Application.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | #include "Win32Application.h" 14 | 15 | HWND Win32Application::m_hwnd = nullptr; 16 | 17 | int Win32Application::Run(DXSample* pSample, HINSTANCE hInstance, int nCmdShow) 18 | { 19 | // Parse the command line parameters 20 | int argc; 21 | LPWSTR* argv = CommandLineToArgvW(GetCommandLineW(), &argc); 22 | pSample->ParseCommandLineArgs(argv, argc); 23 | LocalFree(argv); 24 | 25 | // Initialize the window class. 26 | WNDCLASSEX windowClass = { 0 }; 27 | windowClass.cbSize = sizeof(WNDCLASSEX); 28 | windowClass.style = CS_HREDRAW | CS_VREDRAW; 29 | windowClass.lpfnWndProc = WindowProc; 30 | windowClass.hInstance = hInstance; 31 | windowClass.hCursor = LoadCursor(NULL, IDC_ARROW); 32 | windowClass.lpszClassName = L"DXSampleClass"; 33 | RegisterClassEx(&windowClass); 34 | 35 | RECT windowRect = { 0, 0, static_cast(pSample->GetWidth()), static_cast(pSample->GetHeight()) }; 36 | AdjustWindowRect(&windowRect, WS_OVERLAPPEDWINDOW, FALSE); 37 | 38 | // Create the window and store a handle to it. 39 | m_hwnd = CreateWindow( 40 | windowClass.lpszClassName, 41 | pSample->GetTitle(), 42 | WS_OVERLAPPEDWINDOW, 43 | CW_USEDEFAULT, 44 | CW_USEDEFAULT, 45 | windowRect.right - windowRect.left, 46 | windowRect.bottom - windowRect.top, 47 | nullptr, // We have no parent window. 48 | nullptr, // We aren't using menus. 49 | hInstance, 50 | pSample); 51 | 52 | // Initialize the sample. OnInit is defined in each child-implementation of DXSample. 53 | pSample->OnInit(); 54 | 55 | ShowWindow(m_hwnd, nCmdShow); 56 | 57 | // Main sample loop. 58 | MSG msg = {}; 59 | while (msg.message != WM_QUIT) 60 | { 61 | // Process any messages in the queue. 62 | if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE)) 63 | { 64 | TranslateMessage(&msg); 65 | DispatchMessage(&msg); 66 | } 67 | } 68 | 69 | pSample->OnDestroy(); 70 | 71 | // Return this part of the WM_QUIT message to Windows. 72 | return static_cast(msg.wParam); 73 | } 74 | 75 | // Main message handler for the sample. 76 | LRESULT CALLBACK Win32Application::WindowProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) 77 | { 78 | DXSample* pSample = reinterpret_cast(GetWindowLongPtr(hWnd, GWLP_USERDATA)); 79 | 80 | switch (message) 81 | { 82 | case WM_CREATE: 83 | { 84 | // Save the DXSample* passed in to CreateWindow. 85 | LPCREATESTRUCT pCreateStruct = reinterpret_cast(lParam); 86 | SetWindowLongPtr(hWnd, GWLP_USERDATA, reinterpret_cast(pCreateStruct->lpCreateParams)); 87 | } 88 | return 0; 89 | 90 | case WM_KEYDOWN: 91 | if (pSample) 92 | { 93 | pSample->OnKeyDown(static_cast(wParam)); 94 | } 95 | return 0; 96 | 97 | case WM_KEYUP: 98 | if (pSample) 99 | { 100 | pSample->OnKeyUp(static_cast(wParam)); 101 | } 102 | return 0; 103 | 104 | case WM_PAINT: 105 | if (pSample) 106 | { 107 | pSample->OnUpdate(); 108 | pSample->OnRender(); 109 | } 110 | return 0; 111 | 112 | case WM_DESTROY: 113 | PostQuitMessage(0); 114 | return 0; 115 | } 116 | 117 | // Handle any messages the switch statement didn't. 118 | return DefWindowProc(hWnd, message, wParam, lParam); 119 | } 120 | -------------------------------------------------------------------------------- /dxil/shadertoy/Win32Application.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #pragma once 13 | 14 | #include "DXSample.h" 15 | 16 | class DXSample; 17 | 18 | class Win32Application 19 | { 20 | public: 21 | static int Run(DXSample* pSample, HINSTANCE hInstance, int nCmdShow); 22 | static HWND GetHwnd() { return m_hwnd; } 23 | 24 | protected: 25 | static LRESULT CALLBACK WindowProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam); 26 | 27 | private: 28 | static HWND m_hwnd; 29 | }; 30 | -------------------------------------------------------------------------------- /dxil/shadertoy/band1.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/band1.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/band2.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/band2.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/bands.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/bands.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/build_shaders.bat: -------------------------------------------------------------------------------- 1 | :: one vertex shader 2 | wsl circle -shader -emit-dxil -c shaders.cxx -E vert -o vert.dxil & dxil-signing vert.dxil 3 | 4 | :: fragment shaders 5 | wsl circle -shader -emit-dxil -c shaders.cxx -E fractal -o fractal.dxil && dxil-signing fractal.dxil 6 | wsl circle -shader -emit-dxil -c shaders.cxx -E clouds -o clouds.dxil && dxil-signing clouds.dxil 7 | wsl circle -shader -emit-dxil -c shaders.cxx -E devil -o devil.dxil && dxil-signing devil.dxil 8 | wsl circle -shader -emit-dxil -c shaders.cxx -E square -o square.dxil && dxil-signing square.dxil 9 | wsl circle -shader -emit-dxil -c shaders.cxx -E modulation -o modulation.dxil && dxil-signing modulation.dxil 10 | wsl circle -shader -emit-dxil -c shaders.cxx -E bands -o bands.dxil && dxil-signing bands.dxil 11 | wsl circle -shader -emit-dxil -c shaders.cxx -E paint -o paint.dxil && dxil-signing paint.dxil 12 | wsl circle -shader -emit-dxil -c shaders.cxx -E triangle_grid -o triangle_grid.dxil && dxil-signing triangle_grid.dxil 13 | wsl circle -shader -emit-dxil -c shaders.cxx -E menger -o menger.dxil && dxil-signing menger.dxil 14 | wsl circle -shader -emit-dxil -c shaders.cxx -E hypercomplex -o hypercomplex.dxil && dxil-signing hypercomplex.dxil 15 | wsl circle -shader -emit-dxil -c shaders.cxx -E band1 -o band1.dxil && dxil-signing band1.dxil 16 | wsl circle -shader -emit-dxil -c shaders.cxx -E band2 -o band2.dxil && dxil-signing band2.dxil 17 | wsl circle -shader -emit-dxil -c shaders.cxx -E sphere -o sphere.dxil && dxil-signing sphere.dxil 18 | wsl circle -shader -emit-dxil -c shaders.cxx -E segment -o segment.dxil && dxil-signing segment.dxil 19 | wsl circle -shader -emit-dxil -c shaders.cxx -E comparison -o comparison.dxil && dxil-signing comparison.dxil 20 | wsl circle -shader -emit-dxil -c shaders.cxx -E raymarch -o raymarch.dxil && dxil-signing raymarch.dxil 21 | wsl circle -shader -emit-dxil -c shaders.cxx -E thumbnails -o thumbnails.dxil && dxil-signing thumbnails.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/clouds.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/clouds.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/comparison.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/comparison.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/devil.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/devil.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/fractal.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/fractal.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/hypercomplex.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/hypercomplex.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/menger.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/menger.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/modulation.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/modulation.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/paint.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/paint.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/raymarch.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/raymarch.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/segment.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/segment.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/sphere.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/sphere.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/square.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/square.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/stdafx.cpp: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | #include "stdafx.h" 13 | -------------------------------------------------------------------------------- /dxil/shadertoy/stdafx.h: -------------------------------------------------------------------------------- 1 | //********************************************************* 2 | // 3 | // Copyright (c) Microsoft. All rights reserved. 4 | // This code is licensed under the MIT License (MIT). 5 | // THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF 6 | // ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY 7 | // IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR 8 | // PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. 9 | // 10 | //********************************************************* 11 | 12 | // stdafx.h : include file for standard system include files, 13 | // or project specific include files that are used frequently, but 14 | // are changed infrequently. 15 | 16 | #pragma once 17 | 18 | #ifndef WIN32_LEAN_AND_MEAN 19 | #define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers. 20 | #endif 21 | 22 | #include 23 | 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include "d3dx12.h" 29 | 30 | #include 31 | #include 32 | #include 33 | -------------------------------------------------------------------------------- /dxil/shadertoy/thumbnails.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/thumbnails.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/triangle_grid.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/triangle_grid.dxil -------------------------------------------------------------------------------- /dxil/shadertoy/vert.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/shadertoy/vert.dxil -------------------------------------------------------------------------------- /dxil/tessellation/Camera.cpp: -------------------------------------------------------------------------------- 1 | //*************************************************************************************** 2 | // Camera.h by Frank Luna (C) 2011 All Rights Reserved. 3 | //*************************************************************************************** 4 | 5 | #include "Camera.h" 6 | 7 | using namespace DirectX; 8 | 9 | Camera::Camera() 10 | { 11 | SetLens(0.25f*MathHelper::Pi, 1.0f, 1.0f, 1000.0f); 12 | } 13 | 14 | Camera::~Camera() 15 | { 16 | } 17 | 18 | XMVECTOR Camera::GetPosition()const 19 | { 20 | return XMLoadFloat3(&mPosition); 21 | } 22 | 23 | XMFLOAT3 Camera::GetPosition3f()const 24 | { 25 | return mPosition; 26 | } 27 | 28 | void Camera::SetPosition(float x, float y, float z) 29 | { 30 | mPosition = XMFLOAT3(x, y, z); 31 | mViewDirty = true; 32 | } 33 | 34 | void Camera::SetPosition(const XMFLOAT3& v) 35 | { 36 | mPosition = v; 37 | mViewDirty = true; 38 | } 39 | 40 | XMVECTOR Camera::GetRight()const 41 | { 42 | return XMLoadFloat3(&mRight); 43 | } 44 | 45 | XMFLOAT3 Camera::GetRight3f()const 46 | { 47 | return mRight; 48 | } 49 | 50 | XMVECTOR Camera::GetUp()const 51 | { 52 | return XMLoadFloat3(&mUp); 53 | } 54 | 55 | XMFLOAT3 Camera::GetUp3f()const 56 | { 57 | return mUp; 58 | } 59 | 60 | XMVECTOR Camera::GetLook()const 61 | { 62 | return XMLoadFloat3(&mLook); 63 | } 64 | 65 | XMFLOAT3 Camera::GetLook3f()const 66 | { 67 | return mLook; 68 | } 69 | 70 | float Camera::GetNearZ()const 71 | { 72 | return mNearZ; 73 | } 74 | 75 | float Camera::GetFarZ()const 76 | { 77 | return mFarZ; 78 | } 79 | 80 | float Camera::GetAspect()const 81 | { 82 | return mAspect; 83 | } 84 | 85 | float Camera::GetFovY()const 86 | { 87 | return mFovY; 88 | } 89 | 90 | float Camera::GetFovX()const 91 | { 92 | float halfWidth = 0.5f*GetNearWindowWidth(); 93 | return 2.0f*atan(halfWidth / mNearZ); 94 | } 95 | 96 | float Camera::GetNearWindowWidth()const 97 | { 98 | return mAspect * mNearWindowHeight; 99 | } 100 | 101 | float Camera::GetNearWindowHeight()const 102 | { 103 | return mNearWindowHeight; 104 | } 105 | 106 | float Camera::GetFarWindowWidth()const 107 | { 108 | return mAspect * mFarWindowHeight; 109 | } 110 | 111 | float Camera::GetFarWindowHeight()const 112 | { 113 | return mFarWindowHeight; 114 | } 115 | 116 | void Camera::SetLens(float fovY, float aspect, float zn, float zf) 117 | { 118 | // cache properties 119 | mFovY = fovY; 120 | mAspect = aspect; 121 | mNearZ = zn; 122 | mFarZ = zf; 123 | 124 | mNearWindowHeight = 2.0f * mNearZ * tanf( 0.5f*mFovY ); 125 | mFarWindowHeight = 2.0f * mFarZ * tanf( 0.5f*mFovY ); 126 | 127 | XMMATRIX P = XMMatrixPerspectiveFovLH(mFovY, mAspect, mNearZ, mFarZ); 128 | XMStoreFloat4x4(&mProj, P); 129 | } 130 | 131 | void Camera::LookAt(FXMVECTOR pos, FXMVECTOR target, FXMVECTOR worldUp) 132 | { 133 | XMVECTOR L = XMVector3Normalize(XMVectorSubtract(target, pos)); 134 | XMVECTOR R = XMVector3Normalize(XMVector3Cross(worldUp, L)); 135 | XMVECTOR U = XMVector3Cross(L, R); 136 | 137 | XMStoreFloat3(&mPosition, pos); 138 | XMStoreFloat3(&mLook, L); 139 | XMStoreFloat3(&mRight, R); 140 | XMStoreFloat3(&mUp, U); 141 | 142 | mViewDirty = true; 143 | } 144 | 145 | void Camera::LookAt(const XMFLOAT3& pos, const XMFLOAT3& target, const XMFLOAT3& up) 146 | { 147 | XMVECTOR P = XMLoadFloat3(&pos); 148 | XMVECTOR T = XMLoadFloat3(&target); 149 | XMVECTOR U = XMLoadFloat3(&up); 150 | 151 | LookAt(P, T, U); 152 | 153 | mViewDirty = true; 154 | } 155 | 156 | XMMATRIX Camera::GetView()const 157 | { 158 | assert(!mViewDirty); 159 | return XMLoadFloat4x4(&mView); 160 | } 161 | 162 | XMMATRIX Camera::GetProj()const 163 | { 164 | return XMLoadFloat4x4(&mProj); 165 | } 166 | 167 | 168 | XMFLOAT4X4 Camera::GetView4x4f()const 169 | { 170 | assert(!mViewDirty); 171 | return mView; 172 | } 173 | 174 | XMFLOAT4X4 Camera::GetProj4x4f()const 175 | { 176 | return mProj; 177 | } 178 | 179 | void Camera::Strafe(float d) 180 | { 181 | // mPosition += d*mRight 182 | XMVECTOR s = XMVectorReplicate(d); 183 | XMVECTOR r = XMLoadFloat3(&mRight); 184 | XMVECTOR p = XMLoadFloat3(&mPosition); 185 | XMStoreFloat3(&mPosition, XMVectorMultiplyAdd(s, r, p)); 186 | 187 | mViewDirty = true; 188 | } 189 | 190 | void Camera::Walk(float d) 191 | { 192 | // mPosition += d*mLook 193 | XMVECTOR s = XMVectorReplicate(d); 194 | XMVECTOR l = XMLoadFloat3(&mLook); 195 | XMVECTOR p = XMLoadFloat3(&mPosition); 196 | XMStoreFloat3(&mPosition, XMVectorMultiplyAdd(s, l, p)); 197 | 198 | mViewDirty = true; 199 | } 200 | 201 | void Camera::Pitch(float angle) 202 | { 203 | // Rotate up and look vector about the right vector. 204 | 205 | XMMATRIX R = XMMatrixRotationAxis(XMLoadFloat3(&mRight), angle); 206 | 207 | XMStoreFloat3(&mUp, XMVector3TransformNormal(XMLoadFloat3(&mUp), R)); 208 | XMStoreFloat3(&mLook, XMVector3TransformNormal(XMLoadFloat3(&mLook), R)); 209 | 210 | mViewDirty = true; 211 | } 212 | 213 | void Camera::RotateY(float angle) 214 | { 215 | // Rotate the basis vectors about the world y-axis. 216 | 217 | XMMATRIX R = XMMatrixRotationY(angle); 218 | 219 | XMStoreFloat3(&mRight, XMVector3TransformNormal(XMLoadFloat3(&mRight), R)); 220 | XMStoreFloat3(&mUp, XMVector3TransformNormal(XMLoadFloat3(&mUp), R)); 221 | XMStoreFloat3(&mLook, XMVector3TransformNormal(XMLoadFloat3(&mLook), R)); 222 | 223 | mViewDirty = true; 224 | } 225 | 226 | void Camera::UpdateViewMatrix() 227 | { 228 | if(mViewDirty) 229 | { 230 | XMVECTOR R = XMLoadFloat3(&mRight); 231 | XMVECTOR U = XMLoadFloat3(&mUp); 232 | XMVECTOR L = XMLoadFloat3(&mLook); 233 | XMVECTOR P = XMLoadFloat3(&mPosition); 234 | 235 | // Keep camera's axes orthogonal to each other and of unit length. 236 | L = XMVector3Normalize(L); 237 | U = XMVector3Normalize(XMVector3Cross(L, R)); 238 | 239 | // U, L already ortho-normal, so no need to normalize cross product. 240 | R = XMVector3Cross(U, L); 241 | 242 | // Fill in the view matrix entries. 243 | float x = -XMVectorGetX(XMVector3Dot(P, R)); 244 | float y = -XMVectorGetX(XMVector3Dot(P, U)); 245 | float z = -XMVectorGetX(XMVector3Dot(P, L)); 246 | 247 | XMStoreFloat3(&mRight, R); 248 | XMStoreFloat3(&mUp, U); 249 | XMStoreFloat3(&mLook, L); 250 | 251 | mView(0, 0) = mRight.x; 252 | mView(1, 0) = mRight.y; 253 | mView(2, 0) = mRight.z; 254 | mView(3, 0) = x; 255 | 256 | mView(0, 1) = mUp.x; 257 | mView(1, 1) = mUp.y; 258 | mView(2, 1) = mUp.z; 259 | mView(3, 1) = y; 260 | 261 | mView(0, 2) = mLook.x; 262 | mView(1, 2) = mLook.y; 263 | mView(2, 2) = mLook.z; 264 | mView(3, 2) = z; 265 | 266 | mView(0, 3) = 0.0f; 267 | mView(1, 3) = 0.0f; 268 | mView(2, 3) = 0.0f; 269 | mView(3, 3) = 1.0f; 270 | 271 | mViewDirty = false; 272 | } 273 | } 274 | 275 | 276 | -------------------------------------------------------------------------------- /dxil/tessellation/Camera.h: -------------------------------------------------------------------------------- 1 | //*************************************************************************************** 2 | // Camera.h by Frank Luna (C) 2011 All Rights Reserved. 3 | // 4 | // Simple first person style camera class that lets the viewer explore the 3D scene. 5 | // -It keeps track of the camera coordinate system relative to the world space 6 | // so that the view matrix can be constructed. 7 | // -It keeps track of the viewing frustum of the camera so that the projection 8 | // matrix can be obtained. 9 | //*************************************************************************************** 10 | 11 | #ifndef CAMERA_H 12 | #define CAMERA_H 13 | 14 | #include "d3dUtil.h" 15 | 16 | class Camera 17 | { 18 | public: 19 | 20 | Camera(); 21 | ~Camera(); 22 | 23 | // Get/Set world camera position. 24 | DirectX::XMVECTOR GetPosition()const; 25 | DirectX::XMFLOAT3 GetPosition3f()const; 26 | void SetPosition(float x, float y, float z); 27 | void SetPosition(const DirectX::XMFLOAT3& v); 28 | 29 | // Get camera basis vectors. 30 | DirectX::XMVECTOR GetRight()const; 31 | DirectX::XMFLOAT3 GetRight3f()const; 32 | DirectX::XMVECTOR GetUp()const; 33 | DirectX::XMFLOAT3 GetUp3f()const; 34 | DirectX::XMVECTOR GetLook()const; 35 | DirectX::XMFLOAT3 GetLook3f()const; 36 | 37 | // Get frustum properties. 38 | float GetNearZ()const; 39 | float GetFarZ()const; 40 | float GetAspect()const; 41 | float GetFovY()const; 42 | float GetFovX()const; 43 | 44 | // Get near and far plane dimensions in view space coordinates. 45 | float GetNearWindowWidth()const; 46 | float GetNearWindowHeight()const; 47 | float GetFarWindowWidth()const; 48 | float GetFarWindowHeight()const; 49 | 50 | // Set frustum. 51 | void SetLens(float fovY, float aspect, float zn, float zf); 52 | 53 | // Define camera space via LookAt parameters. 54 | void LookAt(DirectX::FXMVECTOR pos, DirectX::FXMVECTOR target, DirectX::FXMVECTOR worldUp); 55 | void LookAt(const DirectX::XMFLOAT3& pos, const DirectX::XMFLOAT3& target, const DirectX::XMFLOAT3& up); 56 | 57 | // Get View/Proj matrices. 58 | DirectX::XMMATRIX GetView()const; 59 | DirectX::XMMATRIX GetProj()const; 60 | 61 | DirectX::XMFLOAT4X4 GetView4x4f()const; 62 | DirectX::XMFLOAT4X4 GetProj4x4f()const; 63 | 64 | // Strafe/Walk the camera a distance d. 65 | void Strafe(float d); 66 | void Walk(float d); 67 | 68 | // Rotate the camera. 69 | void Pitch(float angle); 70 | void RotateY(float angle); 71 | 72 | // After modifying camera position/orientation, call to rebuild the view matrix. 73 | void UpdateViewMatrix(); 74 | 75 | private: 76 | 77 | // Camera coordinate system with coordinates relative to world space. 78 | DirectX::XMFLOAT3 mPosition = { 0.0f, 0.0f, 0.0f }; 79 | DirectX::XMFLOAT3 mRight = { 1.0f, 0.0f, 0.0f }; 80 | DirectX::XMFLOAT3 mUp = { 0.0f, 1.0f, 0.0f }; 81 | DirectX::XMFLOAT3 mLook = { 0.0f, 0.0f, 1.0f }; 82 | 83 | // Cache frustum properties. 84 | float mNearZ = 0.0f; 85 | float mFarZ = 0.0f; 86 | float mAspect = 0.0f; 87 | float mFovY = 0.0f; 88 | float mNearWindowHeight = 0.0f; 89 | float mFarWindowHeight = 0.0f; 90 | 91 | bool mViewDirty = true; 92 | 93 | // Cache View/Proj matrices. 94 | DirectX::XMFLOAT4X4 mView = MathHelper::Identity4x4(); 95 | DirectX::XMFLOAT4X4 mProj = MathHelper::Identity4x4(); 96 | }; 97 | 98 | #endif // CAMERA_H -------------------------------------------------------------------------------- /dxil/tessellation/FrameResource.cpp: -------------------------------------------------------------------------------- 1 | #include "FrameResource.h" 2 | 3 | FrameResource::FrameResource(ID3D12Device* device, UINT passCount, UINT objectCount, UINT materialCount) 4 | { 5 | ThrowIfFailed(device->CreateCommandAllocator( 6 | D3D12_COMMAND_LIST_TYPE_DIRECT, 7 | IID_PPV_ARGS(CmdListAlloc.GetAddressOf()))); 8 | 9 | // FrameCB = std::make_unique>(device, 1, true); 10 | PassCB = std::make_unique>(device, passCount, true); 11 | ObjectCB = std::make_unique>(device, objectCount, true); 12 | } 13 | 14 | FrameResource::~FrameResource() 15 | { 16 | 17 | } -------------------------------------------------------------------------------- /dxil/tessellation/FrameResource.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "d3dUtil.h" 4 | #include "MathHelper.h" 5 | #include "UploadBuffer.h" 6 | 7 | struct ObjectConstants 8 | { 9 | DirectX::XMFLOAT4X4 World = MathHelper::Identity4x4(); 10 | }; 11 | 12 | struct PassConstants 13 | { 14 | DirectX::XMFLOAT4X4 ViewProj = MathHelper::Identity4x4(); 15 | DirectX::XMFLOAT3 EyePosW = { 0.0f, 0.0f, 0.0f }; 16 | float padding; 17 | }; 18 | 19 | struct Vertex 20 | { 21 | Vertex() = default; 22 | Vertex(float x, float y, float z, float nx, float ny, float nz, float u, float v) : 23 | Pos(x, y, z), 24 | Normal(nx, ny, nz), 25 | TexC(u, v) {} 26 | 27 | DirectX::XMFLOAT3 Pos; 28 | DirectX::XMFLOAT3 Normal; 29 | DirectX::XMFLOAT2 TexC; 30 | }; 31 | 32 | // Stores the resources needed for the CPU to build the command lists 33 | // for a frame. 34 | struct FrameResource 35 | { 36 | public: 37 | 38 | FrameResource(ID3D12Device* device, UINT passCount, UINT objectCount, UINT materialCount); 39 | FrameResource(const FrameResource& rhs) = delete; 40 | FrameResource& operator=(const FrameResource& rhs) = delete; 41 | ~FrameResource(); 42 | 43 | // We cannot reset the allocator until the GPU is done processing the commands. 44 | // So each frame needs their own allocator. 45 | Microsoft::WRL::ComPtr CmdListAlloc; 46 | 47 | // We cannot update a cbuffer until the GPU is done processing the commands 48 | // that reference it. So each frame needs their own cbuffers. 49 | // std::unique_ptr> FrameCB = nullptr; 50 | std::unique_ptr> PassCB = nullptr; 51 | std::unique_ptr> ObjectCB = nullptr; 52 | 53 | // Fence value to mark commands up to this fence point. This lets us 54 | // check if these frame resources are still in use by the GPU. 55 | UINT64 Fence = 0; 56 | }; -------------------------------------------------------------------------------- /dxil/tessellation/GameTimer.cpp: -------------------------------------------------------------------------------- 1 | //*************************************************************************************** 2 | // GameTimer.cpp by Frank Luna (C) 2011 All Rights Reserved. 3 | //*************************************************************************************** 4 | 5 | #include 6 | #include "GameTimer.h" 7 | 8 | GameTimer::GameTimer() 9 | : mSecondsPerCount(0.0), mDeltaTime(-1.0), mBaseTime(0), 10 | mPausedTime(0), mPrevTime(0), mCurrTime(0), mStopped(false) 11 | { 12 | __int64 countsPerSec; 13 | QueryPerformanceFrequency((LARGE_INTEGER*)&countsPerSec); 14 | mSecondsPerCount = 1.0 / (double)countsPerSec; 15 | } 16 | 17 | // Returns the total time elapsed since Reset() was called, NOT counting any 18 | // time when the clock is stopped. 19 | float GameTimer::TotalTime()const 20 | { 21 | // If we are stopped, do not count the time that has passed since we stopped. 22 | // Moreover, if we previously already had a pause, the distance 23 | // mStopTime - mBaseTime includes paused time, which we do not want to count. 24 | // To correct this, we can subtract the paused time from mStopTime: 25 | // 26 | // |<--paused time-->| 27 | // ----*---------------*-----------------*------------*------------*------> time 28 | // mBaseTime mStopTime startTime mStopTime mCurrTime 29 | 30 | if( mStopped ) 31 | { 32 | return (float)(((mStopTime - mPausedTime)-mBaseTime)*mSecondsPerCount); 33 | } 34 | 35 | // The distance mCurrTime - mBaseTime includes paused time, 36 | // which we do not want to count. To correct this, we can subtract 37 | // the paused time from mCurrTime: 38 | // 39 | // (mCurrTime - mPausedTime) - mBaseTime 40 | // 41 | // |<--paused time-->| 42 | // ----*---------------*-----------------*------------*------> time 43 | // mBaseTime mStopTime startTime mCurrTime 44 | 45 | else 46 | { 47 | return (float)(((mCurrTime-mPausedTime)-mBaseTime)*mSecondsPerCount); 48 | } 49 | } 50 | 51 | float GameTimer::DeltaTime()const 52 | { 53 | return (float)mDeltaTime; 54 | } 55 | 56 | void GameTimer::Reset() 57 | { 58 | __int64 currTime; 59 | QueryPerformanceCounter((LARGE_INTEGER*)&currTime); 60 | 61 | mBaseTime = currTime; 62 | mPrevTime = currTime; 63 | mStopTime = 0; 64 | mStopped = false; 65 | } 66 | 67 | void GameTimer::Start() 68 | { 69 | __int64 startTime; 70 | QueryPerformanceCounter((LARGE_INTEGER*)&startTime); 71 | 72 | 73 | // Accumulate the time elapsed between stop and start pairs. 74 | // 75 | // |<-------d------->| 76 | // ----*---------------*-----------------*------------> time 77 | // mBaseTime mStopTime startTime 78 | 79 | if( mStopped ) 80 | { 81 | mPausedTime += (startTime - mStopTime); 82 | 83 | mPrevTime = startTime; 84 | mStopTime = 0; 85 | mStopped = false; 86 | } 87 | } 88 | 89 | void GameTimer::Stop() 90 | { 91 | if( !mStopped ) 92 | { 93 | __int64 currTime; 94 | QueryPerformanceCounter((LARGE_INTEGER*)&currTime); 95 | 96 | mStopTime = currTime; 97 | mStopped = true; 98 | } 99 | } 100 | 101 | void GameTimer::Tick() 102 | { 103 | if( mStopped ) 104 | { 105 | mDeltaTime = 0.0; 106 | return; 107 | } 108 | 109 | __int64 currTime; 110 | QueryPerformanceCounter((LARGE_INTEGER*)&currTime); 111 | mCurrTime = currTime; 112 | 113 | // Time difference between this frame and the previous. 114 | mDeltaTime = (mCurrTime - mPrevTime)*mSecondsPerCount; 115 | 116 | // Prepare for next frame. 117 | mPrevTime = mCurrTime; 118 | 119 | // Force nonnegative. The DXSDK's CDXUTTimer mentions that if the 120 | // processor goes into a power save mode or we get shuffled to another 121 | // processor, then mDeltaTime can be negative. 122 | if(mDeltaTime < 0.0) 123 | { 124 | mDeltaTime = 0.0; 125 | } 126 | } 127 | 128 | -------------------------------------------------------------------------------- /dxil/tessellation/GameTimer.h: -------------------------------------------------------------------------------- 1 | //*************************************************************************************** 2 | // GameTimer.h by Frank Luna (C) 2011 All Rights Reserved. 3 | //*************************************************************************************** 4 | 5 | #ifndef GAMETIMER_H 6 | #define GAMETIMER_H 7 | 8 | class GameTimer 9 | { 10 | public: 11 | GameTimer(); 12 | 13 | float TotalTime()const; // in seconds 14 | float DeltaTime()const; // in seconds 15 | 16 | void Reset(); // Call before message loop. 17 | void Start(); // Call when unpaused. 18 | void Stop(); // Call when paused. 19 | void Tick(); // Call every frame. 20 | 21 | private: 22 | double mSecondsPerCount; 23 | double mDeltaTime; 24 | 25 | __int64 mBaseTime; 26 | __int64 mPausedTime; 27 | __int64 mStopTime; 28 | __int64 mPrevTime; 29 | __int64 mCurrTime; 30 | 31 | bool mStopped; 32 | }; 33 | 34 | #endif // GAMETIMER_H -------------------------------------------------------------------------------- /dxil/tessellation/GeometryGenerator.h: -------------------------------------------------------------------------------- 1 | //*************************************************************************************** 2 | // GeometryGenerator.h by Frank Luna (C) 2011 All Rights Reserved. 3 | // 4 | // Defines a static class for procedurally generating the geometry of 5 | // common mathematical objects. 6 | // 7 | // All triangles are generated "outward" facing. If you want "inward" 8 | // facing triangles (for example, if you want to place the camera inside 9 | // a sphere to simulate a sky), you will need to: 10 | // 1. Change the Direct3D cull mode or manually reverse the winding order. 11 | // 2. Invert the normal. 12 | // 3. Update the texture coordinates and tangent vectors. 13 | //*************************************************************************************** 14 | 15 | #pragma once 16 | 17 | #include 18 | #include 19 | #include 20 | 21 | class GeometryGenerator 22 | { 23 | public: 24 | 25 | using uint16 = std::uint16_t; 26 | using uint32 = std::uint32_t; 27 | 28 | struct Vertex 29 | { 30 | Vertex(){} 31 | Vertex( 32 | const DirectX::XMFLOAT3& p, 33 | const DirectX::XMFLOAT3& n, 34 | const DirectX::XMFLOAT3& t, 35 | const DirectX::XMFLOAT2& uv) : 36 | Position(p), 37 | Normal(n), 38 | TangentU(t), 39 | TexC(uv){} 40 | Vertex( 41 | float px, float py, float pz, 42 | float nx, float ny, float nz, 43 | float tx, float ty, float tz, 44 | float u, float v) : 45 | Position(px,py,pz), 46 | Normal(nx,ny,nz), 47 | TangentU(tx, ty, tz), 48 | TexC(u,v){} 49 | 50 | DirectX::XMFLOAT3 Position; 51 | DirectX::XMFLOAT3 Normal; 52 | DirectX::XMFLOAT3 TangentU; 53 | DirectX::XMFLOAT2 TexC; 54 | }; 55 | 56 | struct MeshData 57 | { 58 | std::vector Vertices; 59 | std::vector Indices32; 60 | 61 | std::vector& GetIndices16() 62 | { 63 | if(mIndices16.empty()) 64 | { 65 | mIndices16.resize(Indices32.size()); 66 | for(size_t i = 0; i < Indices32.size(); ++i) 67 | mIndices16[i] = static_cast(Indices32[i]); 68 | } 69 | 70 | return mIndices16; 71 | } 72 | 73 | private: 74 | std::vector mIndices16; 75 | }; 76 | 77 | /// 78 | /// Creates a box centered at the origin with the given dimensions, where each 79 | /// face has m rows and n columns of vertices. 80 | /// 81 | MeshData CreateBox(float width, float height, float depth, uint32 numSubdivisions); 82 | 83 | /// 84 | /// Creates a sphere centered at the origin with the given radius. The 85 | /// slices and stacks parameters control the degree of tessellation. 86 | /// 87 | MeshData CreateSphere(float radius, uint32 sliceCount, uint32 stackCount); 88 | 89 | /// 90 | /// Creates a geosphere centered at the origin with the given radius. The 91 | /// depth controls the level of tessellation. 92 | /// 93 | MeshData CreateGeosphere(float radius, uint32 numSubdivisions); 94 | 95 | /// 96 | /// Creates a cylinder parallel to the y-axis, and centered about the origin. 97 | /// The bottom and top radius can vary to form various cone shapes rather than true 98 | // cylinders. The slices and stacks parameters control the degree of tessellation. 99 | /// 100 | MeshData CreateCylinder(float bottomRadius, float topRadius, float height, uint32 sliceCount, uint32 stackCount); 101 | 102 | /// 103 | /// Creates an mxn grid in the xz-plane with m rows and n columns, centered 104 | /// at the origin with the specified width and depth. 105 | /// 106 | MeshData CreateGrid(float width, float depth, uint32 m, uint32 n); 107 | 108 | /// 109 | /// Creates a quad aligned with the screen. This is useful for postprocessing and screen effects. 110 | /// 111 | MeshData CreateQuad(float x, float y, float w, float h, float depth); 112 | 113 | private: 114 | void Subdivide(MeshData& meshData); 115 | Vertex MidPoint(const Vertex& v0, const Vertex& v1); 116 | void BuildCylinderTopCap(float bottomRadius, float topRadius, float height, uint32 sliceCount, uint32 stackCount, MeshData& meshData); 117 | void BuildCylinderBottomCap(float bottomRadius, float topRadius, float height, uint32 sliceCount, uint32 stackCount, MeshData& meshData); 118 | }; 119 | 120 | -------------------------------------------------------------------------------- /dxil/tessellation/MathHelper.cpp: -------------------------------------------------------------------------------- 1 | //*************************************************************************************** 2 | // MathHelper.cpp by Frank Luna (C) 2011 All Rights Reserved. 3 | //*************************************************************************************** 4 | 5 | #include "MathHelper.h" 6 | #include 7 | #include 8 | 9 | using namespace DirectX; 10 | 11 | const float MathHelper::Infinity = FLT_MAX; 12 | const float MathHelper::Pi = 3.1415926535f; 13 | 14 | float MathHelper::AngleFromXY(float x, float y) 15 | { 16 | float theta = 0.0f; 17 | 18 | // Quadrant I or IV 19 | if(x >= 0.0f) 20 | { 21 | // If x = 0, then atanf(y/x) = +pi/2 if y > 0 22 | // atanf(y/x) = -pi/2 if y < 0 23 | theta = atanf(y / x); // in [-pi/2, +pi/2] 24 | 25 | if(theta < 0.0f) 26 | theta += 2.0f*Pi; // in [0, 2*pi). 27 | } 28 | 29 | // Quadrant II or III 30 | else 31 | theta = atanf(y/x) + Pi; // in [0, 2*pi). 32 | 33 | return theta; 34 | } 35 | 36 | XMVECTOR MathHelper::RandUnitVec3() 37 | { 38 | XMVECTOR One = XMVectorSet(1.0f, 1.0f, 1.0f, 1.0f); 39 | XMVECTOR Zero = XMVectorZero(); 40 | 41 | // Keep trying until we get a point on/in the hemisphere. 42 | while(true) 43 | { 44 | // Generate random point in the cube [-1,1]^3. 45 | XMVECTOR v = XMVectorSet(MathHelper::RandF(-1.0f, 1.0f), MathHelper::RandF(-1.0f, 1.0f), MathHelper::RandF(-1.0f, 1.0f), 0.0f); 46 | 47 | // Ignore points outside the unit sphere in order to get an even distribution 48 | // over the unit sphere. Otherwise points will clump more on the sphere near 49 | // the corners of the cube. 50 | 51 | if( XMVector3Greater( XMVector3LengthSq(v), One) ) 52 | continue; 53 | 54 | return XMVector3Normalize(v); 55 | } 56 | } 57 | 58 | XMVECTOR MathHelper::RandHemisphereUnitVec3(XMVECTOR n) 59 | { 60 | XMVECTOR One = XMVectorSet(1.0f, 1.0f, 1.0f, 1.0f); 61 | XMVECTOR Zero = XMVectorZero(); 62 | 63 | // Keep trying until we get a point on/in the hemisphere. 64 | while(true) 65 | { 66 | // Generate random point in the cube [-1,1]^3. 67 | XMVECTOR v = XMVectorSet(MathHelper::RandF(-1.0f, 1.0f), MathHelper::RandF(-1.0f, 1.0f), MathHelper::RandF(-1.0f, 1.0f), 0.0f); 68 | 69 | // Ignore points outside the unit sphere in order to get an even distribution 70 | // over the unit sphere. Otherwise points will clump more on the sphere near 71 | // the corners of the cube. 72 | 73 | if( XMVector3Greater( XMVector3LengthSq(v), One) ) 74 | continue; 75 | 76 | // Ignore points in the bottom hemisphere. 77 | if( XMVector3Less( XMVector3Dot(n, v), Zero ) ) 78 | continue; 79 | 80 | return XMVector3Normalize(v); 81 | } 82 | } -------------------------------------------------------------------------------- /dxil/tessellation/MathHelper.h: -------------------------------------------------------------------------------- 1 | //*************************************************************************************** 2 | // MathHelper.h by Frank Luna (C) 2011 All Rights Reserved. 3 | // 4 | // Helper math class. 5 | //*************************************************************************************** 6 | 7 | #pragma once 8 | 9 | #include 10 | #include 11 | #include 12 | 13 | class MathHelper 14 | { 15 | public: 16 | // Returns random float in [0, 1). 17 | static float RandF() 18 | { 19 | return (float)(rand()) / (float)RAND_MAX; 20 | } 21 | 22 | // Returns random float in [a, b). 23 | static float RandF(float a, float b) 24 | { 25 | return a + RandF()*(b-a); 26 | } 27 | 28 | static int Rand(int a, int b) 29 | { 30 | return a + rand() % ((b - a) + 1); 31 | } 32 | 33 | template 34 | static T Min(const T& a, const T& b) 35 | { 36 | return a < b ? a : b; 37 | } 38 | 39 | template 40 | static T Max(const T& a, const T& b) 41 | { 42 | return a > b ? a : b; 43 | } 44 | 45 | template 46 | static T Lerp(const T& a, const T& b, float t) 47 | { 48 | return a + (b-a)*t; 49 | } 50 | 51 | template 52 | static T Clamp(const T& x, const T& low, const T& high) 53 | { 54 | return x < low ? low : (x > high ? high : x); 55 | } 56 | 57 | // Returns the polar angle of the point (x,y) in [0, 2*PI). 58 | static float AngleFromXY(float x, float y); 59 | 60 | static DirectX::XMVECTOR SphericalToCartesian(float radius, float theta, float phi) 61 | { 62 | return DirectX::XMVectorSet( 63 | radius*sinf(phi)*cosf(theta), 64 | radius*cosf(phi), 65 | radius*sinf(phi)*sinf(theta), 66 | 1.0f); 67 | } 68 | 69 | static DirectX::XMMATRIX InverseTranspose(DirectX::CXMMATRIX M) 70 | { 71 | // Inverse-transpose is just applied to normals. So zero out 72 | // translation row so that it doesn't get into our inverse-transpose 73 | // calculation--we don't want the inverse-transpose of the translation. 74 | DirectX::XMMATRIX A = M; 75 | A.r[3] = DirectX::XMVectorSet(0.0f, 0.0f, 0.0f, 1.0f); 76 | 77 | DirectX::XMVECTOR det = DirectX::XMMatrixDeterminant(A); 78 | return DirectX::XMMatrixTranspose(DirectX::XMMatrixInverse(&det, A)); 79 | } 80 | 81 | static DirectX::XMFLOAT4X4 Identity4x4() 82 | { 83 | static DirectX::XMFLOAT4X4 I( 84 | 1.0f, 0.0f, 0.0f, 0.0f, 85 | 0.0f, 1.0f, 0.0f, 0.0f, 86 | 0.0f, 0.0f, 1.0f, 0.0f, 87 | 0.0f, 0.0f, 0.0f, 1.0f); 88 | 89 | return I; 90 | } 91 | 92 | static DirectX::XMVECTOR RandUnitVec3(); 93 | static DirectX::XMVECTOR RandHemisphereUnitVec3(DirectX::XMVECTOR n); 94 | 95 | static const float Infinity; 96 | static const float Pi; 97 | 98 | 99 | }; 100 | 101 | -------------------------------------------------------------------------------- /dxil/tessellation/Textures/bricks.dds: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/Textures/bricks.dds -------------------------------------------------------------------------------- /dxil/tessellation/Textures/checkboard.dds: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/Textures/checkboard.dds -------------------------------------------------------------------------------- /dxil/tessellation/Textures/ice.dds: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/Textures/ice.dds -------------------------------------------------------------------------------- /dxil/tessellation/Textures/white1x1.dds: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/Textures/white1x1.dds -------------------------------------------------------------------------------- /dxil/tessellation/UploadBuffer.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "d3dUtil.h" 4 | 5 | template 6 | class UploadBuffer 7 | { 8 | public: 9 | UploadBuffer(ID3D12Device* device, UINT elementCount, bool isConstantBuffer) : 10 | mIsConstantBuffer(isConstantBuffer) 11 | { 12 | mElementByteSize = sizeof(T); 13 | 14 | // Constant buffer elements need to be multiples of 256 bytes. 15 | // This is because the hardware can only view constant data 16 | // at m*256 byte offsets and of n*256 byte lengths. 17 | // typedef struct D3D12_CONSTANT_BUFFER_VIEW_DESC { 18 | // UINT64 OffsetInBytes; // multiple of 256 19 | // UINT SizeInBytes; // multiple of 256 20 | // } D3D12_CONSTANT_BUFFER_VIEW_DESC; 21 | if(isConstantBuffer) 22 | mElementByteSize = d3dUtil::CalcConstantBufferByteSize(sizeof(T)); 23 | 24 | ThrowIfFailed(device->CreateCommittedResource( 25 | &CD3DX12_HEAP_PROPERTIES(D3D12_HEAP_TYPE_UPLOAD), 26 | D3D12_HEAP_FLAG_NONE, 27 | &CD3DX12_RESOURCE_DESC::Buffer(mElementByteSize*elementCount), 28 | D3D12_RESOURCE_STATE_GENERIC_READ, 29 | nullptr, 30 | IID_PPV_ARGS(&mUploadBuffer))); 31 | 32 | ThrowIfFailed(mUploadBuffer->Map(0, nullptr, reinterpret_cast(&mMappedData))); 33 | 34 | // We do not need to unmap until we are done with the resource. However, we must not write to 35 | // the resource while it is in use by the GPU (so we must use synchronization techniques). 36 | } 37 | 38 | UploadBuffer(const UploadBuffer& rhs) = delete; 39 | UploadBuffer& operator=(const UploadBuffer& rhs) = delete; 40 | ~UploadBuffer() 41 | { 42 | if(mUploadBuffer != nullptr) 43 | mUploadBuffer->Unmap(0, nullptr); 44 | 45 | mMappedData = nullptr; 46 | } 47 | 48 | ID3D12Resource* Resource()const 49 | { 50 | return mUploadBuffer.Get(); 51 | } 52 | 53 | void CopyData(int elementIndex, const T& data) 54 | { 55 | memcpy(&mMappedData[elementIndex*mElementByteSize], &data, sizeof(T)); 56 | } 57 | 58 | private: 59 | Microsoft::WRL::ComPtr mUploadBuffer; 60 | BYTE* mMappedData = nullptr; 61 | 62 | UINT mElementByteSize = 0; 63 | bool mIsConstantBuffer = false; 64 | }; -------------------------------------------------------------------------------- /dxil/tessellation/build_shaders.bat: -------------------------------------------------------------------------------- 1 | wsl -e circle -shader -emit-dxil -c -E vert shaders.cxx -o vert.dxil 2 | dxil-signing.exe vert.dxil 3 | wsl -e circle -shader -emit-dxil -c -E tesc shaders.cxx -o tesc.dxil 4 | dxil-signing.exe tesc.dxil 5 | wsl -e circle -shader -emit-dxil -c -E tese shaders.cxx -o tese.dxil 6 | dxil-signing.exe tese.dxil 7 | wsl -e circle -shader -emit-dxil -c -E frag shaders.cxx -o frag.dxil 8 | dxil-signing.exe frag.dxil -------------------------------------------------------------------------------- /dxil/tessellation/d3dApp.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/d3dApp.h -------------------------------------------------------------------------------- /dxil/tessellation/d3dUtil.cpp: -------------------------------------------------------------------------------- 1 | 2 | #include "d3dUtil.h" 3 | #include 4 | #include 5 | 6 | using Microsoft::WRL::ComPtr; 7 | 8 | DxException::DxException(HRESULT hr, const std::wstring& functionName, const std::wstring& filename, int lineNumber) : 9 | ErrorCode(hr), 10 | FunctionName(functionName), 11 | Filename(filename), 12 | LineNumber(lineNumber) 13 | { 14 | } 15 | 16 | bool d3dUtil::IsKeyDown(int vkeyCode) 17 | { 18 | return (GetAsyncKeyState(vkeyCode) & 0x8000) != 0; 19 | } 20 | 21 | ComPtr d3dUtil::LoadBinary(const std::wstring& filename) 22 | { 23 | std::ifstream fin(filename, std::ios::binary); 24 | 25 | fin.seekg(0, std::ios_base::end); 26 | std::ifstream::pos_type size = (int)fin.tellg(); 27 | fin.seekg(0, std::ios_base::beg); 28 | 29 | ComPtr blob; 30 | ThrowIfFailed(D3DCreateBlob(size, blob.GetAddressOf())); 31 | 32 | fin.read((char*)blob->GetBufferPointer(), size); 33 | fin.close(); 34 | 35 | return blob; 36 | } 37 | 38 | Microsoft::WRL::ComPtr d3dUtil::CreateDefaultBuffer( 39 | ID3D12Device* device, 40 | ID3D12GraphicsCommandList* cmdList, 41 | const void* initData, 42 | UINT64 byteSize, 43 | Microsoft::WRL::ComPtr& uploadBuffer) 44 | { 45 | ComPtr defaultBuffer; 46 | 47 | // Create the actual default buffer resource. 48 | ThrowIfFailed(device->CreateCommittedResource( 49 | &CD3DX12_HEAP_PROPERTIES(D3D12_HEAP_TYPE_DEFAULT), 50 | D3D12_HEAP_FLAG_NONE, 51 | &CD3DX12_RESOURCE_DESC::Buffer(byteSize), 52 | D3D12_RESOURCE_STATE_COMMON, 53 | nullptr, 54 | IID_PPV_ARGS(defaultBuffer.GetAddressOf()))); 55 | 56 | // In order to copy CPU memory data into our default buffer, we need to create 57 | // an intermediate upload heap. 58 | ThrowIfFailed(device->CreateCommittedResource( 59 | &CD3DX12_HEAP_PROPERTIES(D3D12_HEAP_TYPE_UPLOAD), 60 | D3D12_HEAP_FLAG_NONE, 61 | &CD3DX12_RESOURCE_DESC::Buffer(byteSize), 62 | D3D12_RESOURCE_STATE_GENERIC_READ, 63 | nullptr, 64 | IID_PPV_ARGS(uploadBuffer.GetAddressOf()))); 65 | 66 | 67 | // Describe the data we want to copy into the default buffer. 68 | D3D12_SUBRESOURCE_DATA subResourceData = {}; 69 | subResourceData.pData = initData; 70 | subResourceData.RowPitch = byteSize; 71 | subResourceData.SlicePitch = subResourceData.RowPitch; 72 | 73 | // Schedule to copy the data to the default buffer resource. At a high level, the helper function UpdateSubresources 74 | // will copy the CPU memory into the intermediate upload heap. Then, using ID3D12CommandList::CopySubresourceRegion, 75 | // the intermediate upload heap data will be copied to mBuffer. 76 | cmdList->ResourceBarrier(1, &CD3DX12_RESOURCE_BARRIER::Transition(defaultBuffer.Get(), 77 | D3D12_RESOURCE_STATE_COMMON, D3D12_RESOURCE_STATE_COPY_DEST)); 78 | UpdateSubresources<1>(cmdList, defaultBuffer.Get(), uploadBuffer.Get(), 0, 0, 1, &subResourceData); 79 | cmdList->ResourceBarrier(1, &CD3DX12_RESOURCE_BARRIER::Transition(defaultBuffer.Get(), 80 | D3D12_RESOURCE_STATE_COPY_DEST, D3D12_RESOURCE_STATE_GENERIC_READ)); 81 | 82 | // Note: uploadBuffer has to be kept alive after the above function calls because 83 | // the command list has not been executed yet that performs the actual copy. 84 | // The caller can Release the uploadBuffer after it knows the copy has been executed. 85 | 86 | 87 | return defaultBuffer; 88 | } 89 | 90 | ComPtr d3dUtil::CompileShader( 91 | const std::wstring& filename, 92 | const D3D_SHADER_MACRO* defines, 93 | const std::string& entrypoint, 94 | const std::string& target) 95 | { 96 | UINT compileFlags = 0; 97 | #if defined(DEBUG) || defined(_DEBUG) 98 | compileFlags = D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION; 99 | #endif 100 | 101 | HRESULT hr = S_OK; 102 | 103 | ComPtr byteCode = nullptr; 104 | ComPtr errors; 105 | hr = D3DCompileFromFile(filename.c_str(), defines, D3D_COMPILE_STANDARD_FILE_INCLUDE, 106 | entrypoint.c_str(), target.c_str(), compileFlags, 0, &byteCode, &errors); 107 | 108 | if(errors != nullptr) 109 | OutputDebugStringA((char*)errors->GetBufferPointer()); 110 | 111 | ThrowIfFailed(hr); 112 | 113 | return byteCode; 114 | } 115 | 116 | std::wstring DxException::ToString()const 117 | { 118 | // Get the string description of the error code. 119 | _com_error err(ErrorCode); 120 | std::wstring msg = err.ErrorMessage(); 121 | 122 | return FunctionName + L" failed in " + Filename + L"; line " + std::to_wstring(LineNumber) + L"; error: " + msg; 123 | } 124 | 125 | 126 | -------------------------------------------------------------------------------- /dxil/tessellation/frag.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/frag.dxil -------------------------------------------------------------------------------- /dxil/tessellation/shaders.cxx: -------------------------------------------------------------------------------- 1 | template 2 | [[using spirv: in, location(location)]] 3 | type_t shader_in; 4 | 5 | template 6 | [[using spirv: out, location(location)]] 7 | type_t shader_out; 8 | 9 | struct object_data_t { 10 | mat4 gWorld; 11 | }; 12 | [[using spirv: uniform, binding(0)]] 13 | object_data_t object_data; 14 | 15 | struct pass_data_t { 16 | mat4 gViewProj; 17 | vec3 eyePos; 18 | }; 19 | [[using spirv: uniform, binding(1)]] 20 | pass_data_t pass_data; 21 | 22 | extern "C" [[spirv::vert]] 23 | void vert() { 24 | glvert_Output.Position = vec4(shader_in<0, vec3>, 1); 25 | } 26 | 27 | inline void patch_constant() { 28 | vec3 p0 = gltesc_Input[0].Position.xyz; 29 | vec3 p1 = gltesc_Input[1].Position.xyz; 30 | vec3 p2 = gltesc_Input[2].Position.xyz; 31 | vec3 p3 = gltesc_Input[3].Position.xyz; 32 | 33 | vec3 centerL = .25f * (p0 + p1 + p2 + p3); 34 | vec3 centerW = (object_data.gWorld * vec4(centerL, 1)).xyz; 35 | 36 | float d = distance(centerW, pass_data.eyePos); 37 | float d0 = 20; 38 | float d1 = 100; 39 | float tess = 64 * saturate((d1 - d) / (d1 - d0)); 40 | 41 | // Uniformly tessellate the patch. 42 | gltesc_LevelOuter[0] = tess; 43 | gltesc_LevelOuter[1] = tess; 44 | gltesc_LevelOuter[2] = tess; 45 | gltesc_LevelOuter[3] = tess; 46 | gltesc_LevelInner[0] = tess; 47 | gltesc_LevelInner[1] = tess; 48 | } 49 | 50 | extern "C" 51 | [[using spirv: tesc(quads, 4), output(triangle_cw), spacing(fractional_even)]] 52 | [[dxil::patch_constant(patch_constant)]] 53 | void tesc() { 54 | // Pass the patch positions through. 55 | gltesc_Output.Position = gltesc_Input[gltesc_InvocationID].Position; 56 | } 57 | 58 | extern "C" 59 | [[using spirv: tese(quads, 4)]] 60 | void tese() { 61 | float u = gltese_TessCoord.x; 62 | float v = gltese_TessCoord.y; 63 | 64 | vec3 p0 = gltese_Input[0].Position.xyz; 65 | vec3 p1 = gltese_Input[1].Position.xyz; 66 | vec3 p2 = gltese_Input[2].Position.xyz; 67 | vec3 p3 = gltese_Input[3].Position.xyz; 68 | 69 | vec3 v1 = mix(p0, p1, u); 70 | vec3 v2 = mix(p2, p3, u); 71 | vec3 p = mix(v1, v2, v); 72 | 73 | // Displacement mapping. 74 | p.y = .3f * (p.z * sin(p.x) + p.x * cos(p.z)); 75 | vec4 pos = vec4(p, 1) * object_data.gWorld * pass_data.gViewProj; 76 | 77 | glvert_Output.Position = pos; 78 | } 79 | 80 | extern "C" [[spirv::frag]] 81 | void frag() { 82 | shader_out<0, vec4> = vec4(1); 83 | } 84 | 85 | -------------------------------------------------------------------------------- /dxil/tessellation/tesc.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/tesc.dxil -------------------------------------------------------------------------------- /dxil/tessellation/tese.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/tese.dxil -------------------------------------------------------------------------------- /dxil/tessellation/vert.dxil: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/dxil/tessellation/vert.dxil -------------------------------------------------------------------------------- /geom/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | project(geom) 3 | 4 | include_directories(../include) 5 | 6 | set(SOURCE_FILES 7 | geom.cxx 8 | ) 9 | 10 | set_source_files_properties(geom.cxx PROPERTIES COMPILE_FLAGS -shader) 11 | 12 | add_executable(geom ${SOURCE_FILES}) 13 | 14 | target_link_libraries(geom 15 | glfw 16 | gl3w 17 | GL 18 | ) 19 | -------------------------------------------------------------------------------- /images/bandlimited.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/bandlimited.png -------------------------------------------------------------------------------- /images/bandlimited_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/bandlimited_small.png -------------------------------------------------------------------------------- /images/bands.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/bands.png -------------------------------------------------------------------------------- /images/bands_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/bands_small.png -------------------------------------------------------------------------------- /images/bunny.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/bunny.png -------------------------------------------------------------------------------- /images/cpu_flip.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/cpu_flip.png -------------------------------------------------------------------------------- /images/cpu_flip_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/cpu_flip_small.png -------------------------------------------------------------------------------- /images/cube.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/cube.png -------------------------------------------------------------------------------- /images/cube_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/cube_small.png -------------------------------------------------------------------------------- /images/debug1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/debug1.png -------------------------------------------------------------------------------- /images/debug1_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/debug1_small.png -------------------------------------------------------------------------------- /images/debug2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/debug2.png -------------------------------------------------------------------------------- /images/debug2_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/debug2_small.png -------------------------------------------------------------------------------- /images/dxil_nbody.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/dxil_nbody.png -------------------------------------------------------------------------------- /images/dxil_nbody_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/dxil_nbody_small.png -------------------------------------------------------------------------------- /images/dxil_shadertoy.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/dxil_shadertoy.png -------------------------------------------------------------------------------- /images/dxil_shadertoy_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/dxil_shadertoy_small.png -------------------------------------------------------------------------------- /images/dxil_tessellation.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/dxil_tessellation.png -------------------------------------------------------------------------------- /images/dxil_tessellation_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/dxil_tessellation_small.png -------------------------------------------------------------------------------- /images/dxil_wave.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/dxil_wave.png -------------------------------------------------------------------------------- /images/dxil_wave_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/dxil_wave_small.png -------------------------------------------------------------------------------- /images/egg.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/egg.png -------------------------------------------------------------------------------- /images/egg_cpu.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/egg_cpu.png -------------------------------------------------------------------------------- /images/egg_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/egg_small.png -------------------------------------------------------------------------------- /images/geom.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/geom.png -------------------------------------------------------------------------------- /images/geom_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/geom_small.png -------------------------------------------------------------------------------- /images/hypercomplex.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/hypercomplex.png -------------------------------------------------------------------------------- /images/hypercomplex_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/hypercomplex_small.png -------------------------------------------------------------------------------- /images/menger.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/menger.png -------------------------------------------------------------------------------- /images/menger_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/menger_small.png -------------------------------------------------------------------------------- /images/meshlet1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/meshlet1.png -------------------------------------------------------------------------------- /images/meshlet1_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/meshlet1_small.png -------------------------------------------------------------------------------- /images/meshlet2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/meshlet2.png -------------------------------------------------------------------------------- /images/meshlet2_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/meshlet2_small.png -------------------------------------------------------------------------------- /images/meshlet2_small2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/meshlet2_small2.png -------------------------------------------------------------------------------- /images/mini_path_tracer.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/mini_path_tracer.png -------------------------------------------------------------------------------- /images/mini_path_tracer_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/mini_path_tracer_small.png -------------------------------------------------------------------------------- /images/modulation.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/modulation.png -------------------------------------------------------------------------------- /images/modulation_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/modulation_small.png -------------------------------------------------------------------------------- /images/nbody.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/nbody.png -------------------------------------------------------------------------------- /images/nbody2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/nbody2.png -------------------------------------------------------------------------------- /images/nbody2_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/nbody2_small.png -------------------------------------------------------------------------------- /images/nbody_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/nbody_small.png -------------------------------------------------------------------------------- /images/paint.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/paint.png -------------------------------------------------------------------------------- /images/paint_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/paint_small.png -------------------------------------------------------------------------------- /images/particles.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/particles.png -------------------------------------------------------------------------------- /images/particles_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/particles_small.png -------------------------------------------------------------------------------- /images/ray_tracing1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/ray_tracing1.png -------------------------------------------------------------------------------- /images/ray_tracing1_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/ray_tracing1_small.png -------------------------------------------------------------------------------- /images/ray_tracing2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/ray_tracing2.png -------------------------------------------------------------------------------- /images/ray_tracing2_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/ray_tracing2_small.png -------------------------------------------------------------------------------- /images/ray_tracing_tutorial.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/ray_tracing_tutorial.png -------------------------------------------------------------------------------- /images/ray_tracing_tutorial_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/ray_tracing_tutorial_small.png -------------------------------------------------------------------------------- /images/raymarch_json.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/raymarch_json.png -------------------------------------------------------------------------------- /images/raymarcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/raymarcher.png -------------------------------------------------------------------------------- /images/raymarcher2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/raymarcher2.png -------------------------------------------------------------------------------- /images/raymarcher2_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/raymarcher2_small.png -------------------------------------------------------------------------------- /images/raymarcher_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/raymarcher_small.png -------------------------------------------------------------------------------- /images/segment_tracer.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/segment_tracer.png -------------------------------------------------------------------------------- /images/segment_tracer_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/segment_tracer_small.png -------------------------------------------------------------------------------- /images/shader_flip.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/shader_flip.png -------------------------------------------------------------------------------- /images/shader_flip_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/shader_flip_small.png -------------------------------------------------------------------------------- /images/shader_params.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/shader_params.png -------------------------------------------------------------------------------- /images/spheres_many_sizes.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/spheres_many_sizes.png -------------------------------------------------------------------------------- /images/sprites.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/sprites.png -------------------------------------------------------------------------------- /images/sprites_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/sprites_small.png -------------------------------------------------------------------------------- /images/square.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/square.png -------------------------------------------------------------------------------- /images/square_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/square_small.png -------------------------------------------------------------------------------- /images/teapot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/teapot.png -------------------------------------------------------------------------------- /images/teapot_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/teapot_small.png -------------------------------------------------------------------------------- /images/temple.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/temple.png -------------------------------------------------------------------------------- /images/viewer.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/viewer.png -------------------------------------------------------------------------------- /images/viewer_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/images/viewer_small.png -------------------------------------------------------------------------------- /include/texture.hxx: -------------------------------------------------------------------------------- 1 | #include "appglfw.hxx" 2 | 3 | #define STBI_ONLY_JPEG 4 | #define STBI_ONLY_PNG 5 | #define STBI_NO_SIMD 6 | #include "../thirdparty/stb/stb_image.h" 7 | 8 | GLuint load_texture(const char* path) { 9 | int width, height, comp; 10 | stbi_uc* data = stbi_load(path, &width, &height, &comp, STBI_rgb_alpha); 11 | 12 | GLuint texture; 13 | glCreateTextures(GL_TEXTURE_2D, 1, &texture); 14 | glTextureStorage2D(texture, 1, GL_RGBA8, width, height); 15 | glTextureSubImage2D(texture, 0, 0, 0, width, height, GL_RGBA, 16 | GL_UNSIGNED_BYTE, data); 17 | stbi_image_free(data); 18 | 19 | glGenerateTextureMipmap(texture); 20 | 21 | glTextureParameteri(texture, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); 22 | glTextureParameteri(texture, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 23 | glTextureParameteri(texture, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); 24 | glTextureParameteri(texture, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); 25 | 26 | return texture; 27 | } 28 | 29 | GLuint load_cubemap(const char* (&paths)[6]) { 30 | GLuint cubemap; 31 | glCreateTextures(GL_TEXTURE_CUBE_MAP, 1, &cubemap); 32 | 33 | int width, height, comp; 34 | stbi_uc* data = stbi_load(paths[0], &width, &height, &comp, STBI_rgb_alpha); 35 | 36 | glTextureStorage2D(cubemap, 1, GL_RGBA8, width, height); 37 | 38 | for(int face = 0; face < 6; ++face) { 39 | if(face) 40 | data = stbi_load(paths[face], &width, &height, &comp, STBI_rgb_alpha); 41 | 42 | glTextureSubImage3D(cubemap, 0, 0, 0, face, width, height, 1, GL_RGBA, 43 | GL_UNSIGNED_BYTE, data); 44 | 45 | stbi_image_free(data); 46 | } 47 | glGenerateTextureMipmap(cubemap); 48 | 49 | glTextureParameteri(cubemap, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); 50 | glTextureParameteri(cubemap, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 51 | glTextureParameteri(cubemap, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); 52 | glTextureParameteri(cubemap, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); 53 | 54 | return cubemap; 55 | } 56 | -------------------------------------------------------------------------------- /nbody/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | project(nbody) 3 | 4 | include_directories(../thirdparty/imgui) 5 | include_directories(../include) 6 | 7 | set(SOURCE_FILES 8 | nbody.cxx 9 | 10 | ../thirdparty/imgui/imgui.cpp 11 | ../thirdparty/imgui/imgui_draw.cpp 12 | ../thirdparty/imgui/imgui_widgets.cpp 13 | ../thirdparty/imgui/backends/imgui_impl_glfw.cpp 14 | ../thirdparty/imgui/backends/imgui_impl_opengl3.cpp 15 | ) 16 | 17 | set_source_files_properties(nbody.cxx PROPERTIES COMPILE_FLAGS -shader) 18 | 19 | add_executable(nbody ${SOURCE_FILES}) 20 | 21 | target_link_libraries(nbody 22 | glfw 23 | gl3w 24 | GL 25 | ) 26 | -------------------------------------------------------------------------------- /nbody/galaxy_20K.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/seanbaxter/shaders/185c6e81bfaabd54fde80a0a2318636ae01bfab5/nbody/galaxy_20K.bin -------------------------------------------------------------------------------- /nbody/tipsy.h: -------------------------------------------------------------------------------- 1 | #ifndef __TIPSY_H__ 2 | #define __TIPSY_H__ 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | using namespace std; 10 | 11 | #define MAXDIM 3 12 | 13 | typedef float Real; 14 | 15 | struct gas_particle 16 | { 17 | Real mass; 18 | Real pos[MAXDIM]; 19 | Real vel[MAXDIM]; 20 | Real rho; 21 | Real temp; 22 | Real hsmooth; 23 | Real metals ; 24 | Real phi ; 25 | } ; 26 | 27 | //struct gas_particle *gas_particles; 28 | 29 | struct dark_particle 30 | { 31 | Real mass; 32 | Real pos[MAXDIM]; 33 | Real vel[MAXDIM]; 34 | Real eps; 35 | int phi ; 36 | } ; 37 | 38 | //struct dark_particle *dark_particles; 39 | 40 | struct star_particle 41 | { 42 | Real mass; 43 | Real pos[MAXDIM]; 44 | Real vel[MAXDIM]; 45 | Real metals ; 46 | Real tform ; 47 | Real eps; 48 | int phi ; 49 | } ; 50 | 51 | //struct star_particle *star_particles; 52 | 53 | struct dump 54 | { 55 | double time ; 56 | int nbodies ; 57 | int ndim ; 58 | int nsph ; 59 | int ndark ; 60 | int nstar ; 61 | } ; 62 | 63 | typedef struct dump header ; 64 | 65 | template 66 | void read_tipsy_file(vector &bodyPositions, 67 | vector &bodyVelocities, 68 | vector &bodiesIDs, 69 | const std::string &fileName, 70 | int &NTotal, 71 | int &NFirst, 72 | int &NSecond, 73 | int &NThird) 74 | { 75 | /* 76 | Read in our custom version of the tipsy file format written by 77 | Jeroen Bedorf. Most important change is that we store particle id on the 78 | location where previously the potential was stored. 79 | */ 80 | 81 | char fullFileName[256]; 82 | sprintf(fullFileName, "%s", fileName.c_str()); 83 | 84 | cout << "Trying to read file: " << fullFileName << endl; 85 | 86 | ifstream inputFile(fullFileName, ios::in | ios::binary); 87 | 88 | if (!inputFile.is_open()) 89 | { 90 | cout << "Can't open input file \n"; 91 | exit(EXIT_SUCCESS); 92 | } 93 | 94 | dump h; 95 | inputFile.read((char *)&h, sizeof(h)); 96 | 97 | int idummy; 98 | real4 positions; 99 | real4 velocity; 100 | 101 | 102 | //Read tipsy header 103 | NTotal = h.nbodies; 104 | NFirst = h.ndark; 105 | NSecond = h.nstar; 106 | NThird = h.nsph; 107 | 108 | //Start reading 109 | int particleCount = 0; 110 | 111 | dark_particle d; 112 | star_particle s; 113 | 114 | for (int i=0; i < NTotal; i++) 115 | { 116 | if (i < NFirst) 117 | { 118 | inputFile.read((char *)&d, sizeof(d)); 119 | velocity.w = d.eps; 120 | positions.w = d.mass; 121 | positions.x = d.pos[0]; 122 | positions.y = d.pos[1]; 123 | positions.z = d.pos[2]; 124 | velocity.x = d.vel[0]; 125 | velocity.y = d.vel[1]; 126 | velocity.z = d.vel[2]; 127 | idummy = d.phi; 128 | } 129 | else 130 | { 131 | inputFile.read((char *)&s, sizeof(s)); 132 | velocity.w = s.eps; 133 | positions.w = s.mass; 134 | positions.x = s.pos[0]; 135 | positions.y = s.pos[1]; 136 | positions.z = s.pos[2]; 137 | velocity.x = s.vel[0]; 138 | velocity.y = s.vel[1]; 139 | velocity.z = s.vel[2]; 140 | idummy = s.phi; 141 | } 142 | 143 | bodyPositions.push_back(positions); 144 | bodyVelocities.push_back(velocity); 145 | bodiesIDs.push_back(idummy); 146 | 147 | particleCount++; 148 | }//end for 149 | 150 | // round up to a multiple of 256 bodies since our kernel only supports that... 151 | int newTotal = NTotal; 152 | 153 | if (NTotal % 256) 154 | { 155 | newTotal = ((NTotal / 256) + 1) * 256; 156 | } 157 | 158 | for (int i = NTotal; i < newTotal; i++) 159 | { 160 | positions.w = positions.x = positions.y = positions.z = 0; 161 | velocity.x = velocity.y = velocity.z = 0; 162 | bodyPositions.push_back(positions); 163 | bodyVelocities.push_back(velocity); 164 | bodiesIDs.push_back(i); 165 | NFirst++; 166 | } 167 | 168 | NTotal = newTotal; 169 | 170 | inputFile.close(); 171 | 172 | cerr << "Read " << NTotal << " bodies" << endl; 173 | } 174 | 175 | #endif //__TIPSY_H__ 176 | -------------------------------------------------------------------------------- /particles-cuda/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | project(particles-cuda) 3 | 4 | include_directories(../thirdparty/thrust ../thirdparty/cub ../mgpu-shaders/inc ../thirdparty/imgui) 5 | 6 | set(SOURCE_FILES 7 | particles-cuda.cxx 8 | 9 | ../thirdparty/imgui/imgui.cpp 10 | ../thirdparty/imgui/imgui_draw.cpp 11 | ../thirdparty/imgui/imgui_widgets.cpp 12 | ../thirdparty/imgui/backends/imgui_impl_glfw.cpp 13 | ../thirdparty/imgui/backends/imgui_impl_opengl3.cpp 14 | ) 15 | 16 | set_source_files_properties(particles-cuda.cxx PROPERTIES COMPILE_FLAGS "-shader -cuda-path=/opt/nvidia/hpc_sdk/Linux_x86_64/21.3/cuda/11.2/ -sm_52 -sm_61 -sm_75 -g") 17 | 18 | add_executable(particles-cuda ${SOURCE_FILES}) 19 | 20 | add_link_options("-no-demangle") 21 | target_link_libraries(particles-cuda 22 | glfw 23 | gl3w 24 | GL 25 | /opt/nvidia/hpc_sdk/Linux_x86_64/21.3/cuda/11.2/lib64/libcudart.so 26 | ) 27 | -------------------------------------------------------------------------------- /particles/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | project(particles) 3 | 4 | include_directories(../mgpu-shaders/inc ../thirdparty/imgui) 5 | 6 | set(SOURCE_FILES 7 | particles.cxx 8 | 9 | ../thirdparty/imgui/imgui.cpp 10 | ../thirdparty/imgui/imgui_draw.cpp 11 | ../thirdparty/imgui/imgui_widgets.cpp 12 | ../thirdparty/imgui/backends/imgui_impl_glfw.cpp 13 | ../thirdparty/imgui/backends/imgui_impl_opengl3.cpp 14 | ) 15 | 16 | 17 | add_compile_options( 18 | "$<$:-g>" 19 | ) 20 | 21 | set_source_files_properties(particles.cxx PROPERTIES COMPILE_FLAGS -shader) 22 | 23 | add_executable(particles ${SOURCE_FILES}) 24 | 25 | target_link_libraries(particles 26 | glfw 27 | gl3w 28 | GL 29 | ) 30 | -------------------------------------------------------------------------------- /push/push1.cxx: -------------------------------------------------------------------------------- 1 | #if __circle_build__ < 108 2 | #error "Circle build 108 required" 3 | #endif 4 | 5 | [[using spirv: buffer, binding(0)]] 6 | mat4 x[]; 7 | 8 | [[using spirv: comp, local_size(128), push]] 9 | void comp_main(mat4 matrix1, int count, int index, float scale) { 10 | // These parameters are implicitly packed into a push constant block 11 | // then disaggregated back into Function parameters. They act just like 12 | // normal parameters. 13 | x[count] = matrix1 * scale; 14 | 15 | // You can even modify them because they've been copied to Function storage. 16 | ++index; 17 | } 18 | -------------------------------------------------------------------------------- /push/push2.cxx: -------------------------------------------------------------------------------- 1 | [[using spirv: buffer, binding(0)]] 2 | mat4 x[]; 3 | 4 | [[using spirv: comp, local_size(128), push]] 5 | void comp_main(mat4 matrix1, mat4 matrix2, int count, int index, float scale) { 6 | // These parameters are implicitly packed into a push constant block 7 | // then disaggregated back into Function parameters. They act just like 8 | // normal parameters. 9 | x[count] = matrix1 * scale; 10 | 11 | // You can even modify them because they've been copied to Function storage. 12 | ++index; 13 | } 14 | -------------------------------------------------------------------------------- /push/push3.cxx: -------------------------------------------------------------------------------- 1 | [[using spirv: buffer, binding(0)]] 2 | mat4 x[]; 3 | 4 | [[using spirv: comp, local_size(128), push(256)]] 5 | void comp_main(mat4 matrix1, mat4 matrix2, int count, int index, float scale) { 6 | // These parameters are implicitly packed into a push constant block 7 | // then disaggregated back into Function parameters. They act just like 8 | // normal parameters. 9 | x[count] = matrix1 * scale; 10 | 11 | // You can even modify them because they've been copied to Function storage. 12 | ++index; 13 | } 14 | -------------------------------------------------------------------------------- /push/push4.cxx: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | template 5 | [[using spirv: comp, local_size(128), push]] 6 | void my_kernel(types_t... args) { 7 | // Signature of shader and layout of push constant is inferred from 8 | // template parameters, which are deduced from the call arguments on the 9 | // host side. 10 | @meta printf("%d: %s\n", int..., @type_string(types_t))...; 11 | } 12 | 13 | template 14 | struct tuple_t { 15 | types_t @(int...) ...; 16 | }; 17 | 18 | template 19 | void dispatch(/* vulkan pipeline args */ const types_t&... x) { 20 | // Put the arguments in an aggregate. 21 | tuple_t storage { x... }; 22 | 23 | @meta printf("tuple storage is %zu bytes with %zu elements\n", 24 | sizeof(storage), @member_count(decltype(storage))); 25 | 26 | // Can push from this address. It will have the same layout as the implicit 27 | // PushConstant type created by the shader. 28 | // vkCmdPushConstants(cmd, layout, stage, 0, sizeof(storage), &storage); 29 | } 30 | 31 | int main() { 32 | // Evaluate the shader call in an unevaluated context to infer template 33 | // parameters. 34 | const char* name = 35 | @spirv(my_kernel(std::array { 1, 2, 3 }, 5, 3.14, vec2(), mat3())); 36 | puts(name); 37 | 38 | // Capture parameters into a struct to pass to Vulkan. 39 | dispatch(std::array {1, 2, 3 }, 5, 3.14, vec2(), mat3()); 40 | } -------------------------------------------------------------------------------- /shadertoy-cuda/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | 3 | project(shadertoy-cuda) 4 | 5 | include_directories(../thirdparty/imgui) 6 | 7 | set(SOURCE_FILES 8 | shadertoy.cxx 9 | 10 | ../thirdparty/imgui/imgui.cpp 11 | ../thirdparty/imgui/imgui_draw.cpp 12 | ../thirdparty/imgui/imgui_widgets.cpp 13 | ../thirdparty/imgui/backends/imgui_impl_glfw.cpp 14 | ../thirdparty/imgui/backends/imgui_impl_opengl3.cpp 15 | ) 16 | 17 | set_source_files_properties(shadertoy.cxx PROPERTIES COMPILE_OPTIONS "-g;-shader;--cuda-path=/usr/local/cuda/;-sm_75") 18 | 19 | add_executable(shadertoy-cuda ${SOURCE_FILES}) 20 | 21 | target_link_libraries(shadertoy-cuda 22 | glfw 23 | gl3w 24 | GL 25 | /usr/local/cuda/targets/x86_64-linux/lib/libcudart.so 26 | ) -------------------------------------------------------------------------------- /shadertoy-cuda/adam7.hxx: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | struct adam7_t { 4 | int blocksX, blocksY; 5 | 6 | template 7 | bool process(int tid, int num_threads, int num_levels, bool interlace, 8 | func_t& func); 9 | }; 10 | 11 | template 12 | bool adam7_t::process(int tid, int num_threads, int num_levels, bool interlace, 13 | func_t& func) { 14 | 15 | int num_blocks = blocksX * blocksY; 16 | 17 | assert(0 < num_levels && num_levels <= 7); 18 | 19 | static const char points_per_level[7] { 20 | 1, 1, 2, 4, 8, 16, 32, 21 | }; 22 | static const char scan_points_per_level[8] { 23 | 0, 1, 2, 4, 8, 16, 32, 64, 24 | }; 25 | static const char block_points_x[64] { 26 | 0, 27 | 4, 28 | 0, 4, 29 | 2, 6, 2, 6, 30 | 0, 2, 4, 6, 0, 4, 2, 6, 31 | 1, 3, 5, 7, 1, 3, 5, 7, 1, 3, 5, 7, 1, 3, 5, 7, 32 | 0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7, 33 | 0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7, 34 | }; 35 | static const char block_points_y[64] { 36 | 0, 37 | 0, 38 | 4, 4, 39 | 0, 0, 4, 4, 40 | 2, 2, 2, 2, 6, 6, 6, 6, 41 | 0, 0, 0, 0, 2, 2, 2, 2, 4, 4, 4, 4, 6, 6, 6, 6, 42 | 1, 1, 1, 1, 1, 1, 1, 1, 3, 3, 3, 3, 3, 3, 3, 3, 43 | 5, 5, 5, 5, 5, 5, 5, 5, 7, 7, 7, 7, 7, 7, 7, 7, 44 | }; 45 | static const char section_size_x[7] { 46 | 8, 4, 4, 2, 2, 1, 1, 47 | }; 48 | static const char section_size_y[7] { 49 | 8, 8, 4, 4, 2, 2, 1, 50 | }; 51 | 52 | for(int level = 0; level < num_levels; ++level) { 53 | int count = points_per_level[level]; 54 | const char* lx = block_points_x + scan_points_per_level[level]; 55 | const char* ly = block_points_y + scan_points_per_level[level]; 56 | int sx = section_size_x[interlace ? level : num_levels - 1]; 57 | int sy = section_size_y[interlace ? level : num_levels - 1]; 58 | 59 | for(int block = tid; block < num_blocks; block += num_threads) { 60 | int bx = block % blocksX; 61 | int by = block / blocksX; 62 | 63 | int x0 = 8 * bx; 64 | int y0 = 8 * by; 65 | for(int i = 0; i < count; ++i) { 66 | int x = x0 + lx[i]; 67 | int y = y0 + ly[i]; 68 | 69 | // Invoke the function for point (x, y) to fill a section (sx, sy). 70 | if(!func(x, y, sx, sy)) 71 | return false; 72 | } 73 | } 74 | } 75 | 76 | return true; 77 | } 78 | -------------------------------------------------------------------------------- /shadertoy/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | 3 | project(shadertoy) 4 | 5 | include_directories(../thirdparty/imgui) 6 | 7 | set(SOURCE_FILES 8 | shadertoy.cxx 9 | 10 | ../thirdparty/imgui/imgui.cpp 11 | ../thirdparty/imgui/imgui_draw.cpp 12 | ../thirdparty/imgui/imgui_widgets.cpp 13 | ../thirdparty/imgui/backends/imgui_impl_glfw.cpp 14 | ../thirdparty/imgui/backends/imgui_impl_opengl3.cpp 15 | ) 16 | 17 | add_compile_options( 18 | "$<$:-g>" 19 | ) 20 | 21 | set_source_files_properties(shadertoy.cxx PROPERTIES COMPILE_FLAGS -shader) 22 | 23 | add_executable(shadertoy ${SOURCE_FILES}) 24 | 25 | target_link_libraries(shadertoy 26 | glfw 27 | gl3w 28 | GL 29 | ) -------------------------------------------------------------------------------- /shadertoy/adam7.hxx: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | struct adam7_t { 4 | int blocksX, blocksY; 5 | 6 | template 7 | bool process(int tid, int num_threads, int num_levels, bool interlace, 8 | func_t& func); 9 | }; 10 | 11 | template 12 | bool adam7_t::process(int tid, int num_threads, int num_levels, bool interlace, 13 | func_t& func) { 14 | 15 | int num_blocks = blocksX * blocksY; 16 | 17 | assert(0 < num_levels && num_levels <= 7); 18 | 19 | static const char points_per_level[7] { 20 | 1, 1, 2, 4, 8, 16, 32, 21 | }; 22 | static const char scan_points_per_level[8] { 23 | 0, 1, 2, 4, 8, 16, 32, 64, 24 | }; 25 | static const char block_points_x[64] { 26 | 0, 27 | 4, 28 | 0, 4, 29 | 2, 6, 2, 6, 30 | 0, 2, 4, 6, 0, 4, 2, 6, 31 | 1, 3, 5, 7, 1, 3, 5, 7, 1, 3, 5, 7, 1, 3, 5, 7, 32 | 0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7, 33 | 0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7, 34 | }; 35 | static const char block_points_y[64] { 36 | 0, 37 | 0, 38 | 4, 4, 39 | 0, 0, 4, 4, 40 | 2, 2, 2, 2, 6, 6, 6, 6, 41 | 0, 0, 0, 0, 2, 2, 2, 2, 4, 4, 4, 4, 6, 6, 6, 6, 42 | 1, 1, 1, 1, 1, 1, 1, 1, 3, 3, 3, 3, 3, 3, 3, 3, 43 | 5, 5, 5, 5, 5, 5, 5, 5, 7, 7, 7, 7, 7, 7, 7, 7, 44 | }; 45 | static const char section_size_x[7] { 46 | 8, 4, 4, 2, 2, 1, 1, 47 | }; 48 | static const char section_size_y[7] { 49 | 8, 8, 4, 4, 2, 2, 1, 50 | }; 51 | 52 | for(int level = 0; level < num_levels; ++level) { 53 | int count = points_per_level[level]; 54 | const char* lx = block_points_x + scan_points_per_level[level]; 55 | const char* ly = block_points_y + scan_points_per_level[level]; 56 | int sx = section_size_x[interlace ? level : num_levels - 1]; 57 | int sy = section_size_y[interlace ? level : num_levels - 1]; 58 | 59 | for(int block = tid; block < num_blocks; block += num_threads) { 60 | int bx = block % blocksX; 61 | int by = block / blocksX; 62 | 63 | int x0 = 8 * bx; 64 | int y0 = 8 * by; 65 | for(int i = 0; i < count; ++i) { 66 | int x = x0 + lx[i]; 67 | int y = y0 + ly[i]; 68 | 69 | // Invoke the function for point (x, y) to fill a section (sx, sy). 70 | if(!func(x, y, sx, sy)) 71 | return false; 72 | } 73 | } 74 | } 75 | 76 | return true; 77 | } 78 | -------------------------------------------------------------------------------- /shadertoy2/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | 3 | project(shadertoy2) 4 | 5 | include_directories(../thirdparty/imgui) 6 | 7 | set(SOURCE_FILES 8 | shadertoy2.cxx 9 | 10 | ../thirdparty/imgui/imgui.cpp 11 | ../thirdparty/imgui/imgui_draw.cpp 12 | ../thirdparty/imgui/imgui_widgets.cpp 13 | ../thirdparty/imgui/backends/imgui_impl_glfw.cpp 14 | ../thirdparty/imgui/backends/imgui_impl_opengl3.cpp 15 | ) 16 | 17 | add_compile_options( 18 | "$<$:-g>" 19 | ) 20 | 21 | set_source_files_properties(shadertoy2.cxx PROPERTIES COMPILE_FLAGS -shader) 22 | 23 | add_executable(shadertoy2 ${SOURCE_FILES}) 24 | 25 | target_link_libraries(shadertoy2 26 | glfw 27 | gl3w 28 | GL 29 | ) -------------------------------------------------------------------------------- /shadertoy2/adam7.hxx: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | struct adam7_t { 4 | int blocksX, blocksY; 5 | 6 | template 7 | bool process(int tid, int num_threads, int num_levels, bool interlace, 8 | func_t& func); 9 | }; 10 | 11 | template 12 | bool adam7_t::process(int tid, int num_threads, int num_levels, bool interlace, 13 | func_t& func) { 14 | 15 | int num_blocks = blocksX * blocksY; 16 | 17 | assert(0 < num_levels && num_levels <= 7); 18 | 19 | static const char points_per_level[7] { 20 | 1, 1, 2, 4, 8, 16, 32, 21 | }; 22 | static const char scan_points_per_level[8] { 23 | 0, 1, 2, 4, 8, 16, 32, 64, 24 | }; 25 | static const char block_points_x[64] { 26 | 0, 27 | 4, 28 | 0, 4, 29 | 2, 6, 2, 6, 30 | 0, 2, 4, 6, 0, 4, 2, 6, 31 | 1, 3, 5, 7, 1, 3, 5, 7, 1, 3, 5, 7, 1, 3, 5, 7, 32 | 0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7, 33 | 0, 1, 2, 3, 4, 5, 6, 7, 0, 1, 2, 3, 4, 5, 6, 7, 34 | }; 35 | static const char block_points_y[64] { 36 | 0, 37 | 0, 38 | 4, 4, 39 | 0, 0, 4, 4, 40 | 2, 2, 2, 2, 6, 6, 6, 6, 41 | 0, 0, 0, 0, 2, 2, 2, 2, 4, 4, 4, 4, 6, 6, 6, 6, 42 | 1, 1, 1, 1, 1, 1, 1, 1, 3, 3, 3, 3, 3, 3, 3, 3, 43 | 5, 5, 5, 5, 5, 5, 5, 5, 7, 7, 7, 7, 7, 7, 7, 7, 44 | }; 45 | static const char section_size_x[7] { 46 | 8, 4, 4, 2, 2, 1, 1, 47 | }; 48 | static const char section_size_y[7] { 49 | 8, 8, 4, 4, 2, 2, 1, 50 | }; 51 | 52 | for(int level = 0; level < num_levels; ++level) { 53 | int count = points_per_level[level]; 54 | const char* lx = block_points_x + scan_points_per_level[level]; 55 | const char* ly = block_points_y + scan_points_per_level[level]; 56 | int sx = section_size_x[interlace ? level : num_levels - 1]; 57 | int sy = section_size_y[interlace ? level : num_levels - 1]; 58 | 59 | for(int block = tid; block < num_blocks; block += num_threads) { 60 | int bx = block % blocksX; 61 | int by = block / blocksX; 62 | 63 | int x0 = 8 * bx; 64 | int y0 = 8 * by; 65 | for(int i = 0; i < count; ++i) { 66 | int x = x0 + lx[i]; 67 | int y = y0 + ly[i]; 68 | 69 | // Invoke the function for point (x, y) to fill a section (sx, sy). 70 | if(!func(x, y, sx, sy)) 71 | return false; 72 | } 73 | } 74 | } 75 | 76 | return true; 77 | } 78 | -------------------------------------------------------------------------------- /shadertoy2/scene.json: -------------------------------------------------------------------------------- 1 | { 2 | "scenes": [ 3 | { 4 | "name" : "spheres of many sizes", 5 | "objects" : [ 6 | { 7 | "name" : "tiny", 8 | "type" : "sphere_t", 9 | "pos" : [ -2.5, 0.1, 0.0 ], 10 | "s" : 0.1, 11 | "material" : 0.0 12 | }, { 13 | "name" : "small", 14 | "type" : "sphere_t", 15 | "pos" : [ -2, 0.3, 0.0 ], 16 | "s" : 0.3, 17 | "material" : 1.0 18 | }, { 19 | "name" : "medium", 20 | "type" : "sphere_t", 21 | "pos" : [ -1, 0.5, 0.0 ], 22 | "s" : 0.5, 23 | "material" : 2.0 24 | }, { 25 | "name" : "large", 26 | "type" : "sphere_t", 27 | "pos" : [ 0.5, 0.75, 0.0 ], 28 | "s" : 0.75, 29 | "material" : 3.0 30 | }, { 31 | "name" : "jumbo", 32 | "type" : "sphere_t", 33 | "pos" : [ 2.5, 1.0, 0.0 ], 34 | "s" : 1.0, 35 | "material" : 4.0 36 | } 37 | ] 38 | }, { 39 | "name" : "temple", 40 | "objects" : [ 41 | { 42 | "name" : "center", 43 | "type" : "bounding_box_t", 44 | "pos" : [ 0, 0.3, 0 ], 45 | "b" : [ 0.3, 0.3, 0.3 ], 46 | "e" : 0.05, 47 | "material" : 3.14 48 | }, 49 | { 50 | "name" : "pyramid_0", 51 | "type" : "pyramid_t", 52 | "pos" : [ -1, 0, 1 ], 53 | "h" : 0.6, 54 | "material" : 1.2 55 | }, 56 | { 57 | "name" : "pyramid_1", 58 | "type" : "pyramid_t", 59 | "pos" : [ 1, 0, 1 ], 60 | "h" : 0.6, 61 | "material" : 1.2 62 | }, 63 | { 64 | "name" : "pyramid_2", 65 | "type" : "pyramid_t", 66 | "pos" : [ 1, 0, -1 ], 67 | "h" : 0.6, 68 | "material" : 1.2 69 | }, 70 | { 71 | "name" : "pyramid_3", 72 | "type" : "pyramid_t", 73 | "pos" : [ -1, 0, -1 ], 74 | "h" : 0.6, 75 | "material" : 1.2 76 | } 77 | ] 78 | } 79 | ] 80 | } 81 | -------------------------------------------------------------------------------- /shadertoy3/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | 3 | project(shadertoy3) 4 | 5 | include_directories(../thirdparty/imgui) 6 | 7 | set(SOURCE_FILES 8 | shadertoy3.cxx 9 | 10 | ../thirdparty/imgui/imgui.cpp 11 | ../thirdparty/imgui/imgui_draw.cpp 12 | ../thirdparty/imgui/imgui_widgets.cpp 13 | ../thirdparty/imgui/backends/imgui_impl_glfw.cpp 14 | ../thirdparty/imgui/backends/imgui_impl_opengl3.cpp 15 | ) 16 | 17 | add_compile_options( 18 | "$<$:-g>" 19 | ) 20 | 21 | set_source_files_properties(shadertoy3.cxx PROPERTIES COMPILE_FLAGS -shader) 22 | 23 | add_executable(shadertoy3 ${SOURCE_FILES}) 24 | 25 | target_link_libraries(shadertoy3 26 | glfw 27 | gl3w 28 | GL 29 | ) -------------------------------------------------------------------------------- /sprites/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | project(sprites) 3 | 4 | include_directories(../include) 5 | 6 | set(SOURCE_FILES 7 | sprites.cxx 8 | ) 9 | 10 | set_source_files_properties(sprites.cxx PROPERTIES COMPILE_FLAGS -shader) 11 | 12 | add_executable(sprites ${SOURCE_FILES}) 13 | 14 | target_link_libraries(sprites 15 | glfw 16 | gl3w 17 | GL 18 | ) 19 | -------------------------------------------------------------------------------- /sprites2/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | project(sprites2) 3 | 4 | include_directories(../include) 5 | 6 | set(SOURCE_FILES 7 | sprites2.cxx 8 | ) 9 | 10 | set_source_files_properties(sprites2.cxx PROPERTIES COMPILE_FLAGS "-shader -M ../thirdparty/libstbi.so") 11 | 12 | add_executable(sprites2 ${SOURCE_FILES}) 13 | 14 | target_link_libraries(sprites2 15 | glfw 16 | gl3w 17 | GL 18 | ) 19 | -------------------------------------------------------------------------------- /teapot/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | 3 | project(teapot) 4 | 5 | include_directories(../thirdparty/imgui ../include) 6 | 7 | set(SOURCE_FILES 8 | teapot.cxx 9 | 10 | ../thirdparty/imgui/imgui.cpp 11 | ../thirdparty/imgui/imgui_draw.cpp 12 | ../thirdparty/imgui/imgui_widgets.cpp 13 | ../thirdparty/imgui/backends/imgui_impl_glfw.cpp 14 | ../thirdparty/imgui/backends/imgui_impl_opengl3.cpp 15 | ) 16 | 17 | set_source_files_properties(teapot.cxx PROPERTIES COMPILE_FLAGS "-shader") 18 | 19 | add_executable(teapot ${SOURCE_FILES}) 20 | 21 | target_link_libraries(teapot 22 | glfw 23 | gl3w 24 | GL 25 | ) -------------------------------------------------------------------------------- /thirdparty/stbi.c: -------------------------------------------------------------------------------- 1 | #define STB_IMAGE_IMPLEMENTATION 2 | #include "stb/stb_image.h" -------------------------------------------------------------------------------- /viewer/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.9) 2 | 3 | project(viewer) 4 | 5 | include_directories(../include) 6 | 7 | set(SOURCE_FILES 8 | viewer.cxx 9 | ) 10 | 11 | set_source_files_properties(viewer.cxx PROPERTIES COMPILE_FLAGS -shader) 12 | 13 | add_executable(viewer ${SOURCE_FILES}) 14 | 15 | target_link_libraries(viewer 16 | glfw 17 | gl3w 18 | GL 19 | ) 20 | -------------------------------------------------------------------------------- /viewer/tonemapping.hxx: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | // linear to sRGB approximation 4 | // see http://chilliant.blogspot.com/2012/08/srgb-approximations-for-hlsl.html 5 | inline vec3 linearTosRGB(vec3 color) { 6 | const float GAMMA = 2.2; 7 | const float INV_GAMMA = 1.0 / GAMMA; 8 | 9 | return pow(color, vec3(INV_GAMMA)); 10 | } 11 | 12 | // sRGB to linear approximation 13 | // see http://chilliant.blogspot.com/2012/08/srgb-approximations-for-hlsl.html 14 | inline vec3 sRGBToLinear(vec3 srgbIn) { 15 | const float GAMMA = 2.2; 16 | return vec3(pow(srgbIn.xyz, vec3(GAMMA))); 17 | } 18 | 19 | inline vec4 sRGBToLinear(vec4 srgbIn) { 20 | return vec4(sRGBToLinear(srgbIn.xyz), srgbIn.w); 21 | } 22 | 23 | // Uncharted 2 tone map 24 | // see: http://filmicworlds.com/blog/filmic-tonemapping-operators/ 25 | inline vec3 toneMapUncharted2Impl(vec3 color) { 26 | const float A = 0.15; 27 | const float B = 0.50; 28 | const float C = 0.10; 29 | const float D = 0.20; 30 | const float E = 0.02; 31 | const float F = 0.30; 32 | return ((color*(A*color+C*B)+D*E)/(color*(A*color+B)+D*F))-E/F; 33 | } 34 | 35 | inline vec3 toneMapUncharted(vec3 color) { 36 | const float W = 11.2; 37 | color = toneMapUncharted2Impl(2 * color); 38 | vec3 whiteScale = 1 / toneMapUncharted2Impl(W); 39 | return linearTosRGB(color * whiteScale); 40 | } 41 | 42 | // Hejl Richard tone map 43 | // see: http://filmicworlds.com/blog/filmic-tonemapping-operators/ 44 | inline vec3 toneMapHejlRichard(vec3 color) { 45 | color = max(vec3(0.0), color - vec3(0.004)); 46 | return (color * (6.2f * color + .5f)) / 47 | (color * (6.2f * color + 1.7f) + 0.06f); 48 | } 49 | 50 | // ACES tone map 51 | // see: https://knarkowicz.wordpress.com/2016/01/06/aces-filmic-tone-mapping-curve/ 52 | inline vec3 toneMapACES(vec3 color) { 53 | const float A = 2.51; 54 | const float B = 0.03; 55 | const float C = 2.43; 56 | const float D = 0.59; 57 | const float E = 0.14; 58 | return linearTosRGB(clamp((color * (A * color + B)) / (color * (C * color + D) + E), 0.f, 1.f)); 59 | } 60 | 61 | inline vec3 toneMap(vec3 color, float exposure) { 62 | color *= exposure; 63 | /* 64 | #ifdef TONEMAP_UNCHARTED 65 | return toneMapUncharted(color); 66 | #endif 67 | 68 | #ifdef TONEMAP_HEJLRICHARD 69 | return toneMapHejlRichard(color); 70 | #endif 71 | 72 | #ifdef TONEMAP_ACES 73 | return toneMapACES(color); 74 | #endif 75 | */ 76 | return linearTosRGB(color); 77 | } 78 | --------------------------------------------------------------------------------