Last active
May 4, 2020 17:52
-
-
Save t-mw/0b78167372ed97e7c78e3f3844f3ae75 to your computer and use it in GitHub Desktop.
Godot Engine AtlasTexture billboard shader
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# NB: assumes an orthogonal camera and quad mesh geometry | |
fn _process(_delta) { | |
# set this to an instance of AtlasTexture | |
var atlas_tex = ... | |
# set this to an instance of Material | |
var material = ... | |
# optionally center the sprite around a point relative to the top-left corner | |
var center = Vector2(0, 0) | |
# hook this up to the camera size | |
var camera_size = 30 | |
var atlas_size = atlas_tex.get_atlas().get_size() | |
var margin = atlas_tex.get_margin() | |
var margin_origin = margin.position | |
var region = atlas_tex.get_region() | |
var region_origin = region.position | |
var region_size = region.size | |
material.set_shader_param("camera_size", camera_size) | |
material.set_shader_param("inv_atlas_size", Vector2(1.0, 1.0) / atlas_size) | |
material.set_shader_param("offset", Vector2(margin_origin.x - center.x, -(margin_origin.y - center.y))) | |
material.set_shader_param("region_origin", region_origin) | |
material.set_shader_param("region_size", region_size) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
shader_type spatial; | |
render_mode blend_mix,depth_draw_opaque,cull_back,diffuse_burley,specular_schlick_ggx,unshaded,skip_vertex_transform; | |
uniform vec4 albedo : hint_color; | |
uniform sampler2D texture_albedo : hint_albedo; | |
uniform float specular; | |
uniform float metallic; | |
uniform float roughness : hint_range(0,1); | |
uniform float camera_size; | |
uniform vec2 inv_atlas_size; | |
uniform vec2 offset; | |
uniform vec2 region_origin; | |
uniform vec2 region_size; | |
void vertex() { | |
// NB: assumes camera keep_aspect == height. | |
// assign a constant to world_units_per_px to keep the sprite size | |
// fixed relative to the 3D world, rather than fixed 1:1 with the viewport. | |
float world_units_per_px = camera_size / VIEWPORT_SIZE.y; | |
// billboard quad | |
MODELVIEW_MATRIX = INV_CAMERA_MATRIX * mat4(CAMERA_MATRIX[0],CAMERA_MATRIX[1],CAMERA_MATRIX[2],WORLD_MATRIX[3]); | |
// scale quad to region size | |
MODELVIEW_MATRIX[0][0] *= region_size.x * world_units_per_px; | |
MODELVIEW_MATRIX[1][1] *= region_size.y * world_units_per_px; | |
VERTEX = (MODELVIEW_MATRIX * vec4(VERTEX, 1.0)).xyz; | |
NORMAL = (MODELVIEW_MATRIX * vec4(NORMAL, 0.0)).xyz; | |
// anchor top-left of quad to node origin | |
VERTEX.xy += vec2(region_size.x / 2.0, -region_size.y / 2.0) * world_units_per_px; | |
// offset by margin | |
VERTEX.xy += offset * world_units_per_px; | |
// adjust uvs for atlas region | |
vec2 uv_offset = region_origin * inv_atlas_size; | |
vec2 uv_scale = region_size * inv_atlas_size; | |
UV = UV * uv_scale + uv_offset; | |
} | |
void fragment() { | |
vec2 base_uv = UV; | |
vec4 albedo_tex = texture(texture_albedo,base_uv); | |
ALBEDO = albedo.rgb * albedo_tex.rgb; | |
METALLIC = metallic; | |
ROUGHNESS = roughness; | |
SPECULAR = specular; | |
ALPHA = albedo.a * albedo_tex.a; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment