How do I adapt a shader for an Atlas Texture?

Godot Version

v4.2.2.stable.official [15073afe3]

Question

Hi!

I’m dipping my feet into Godot shaders now, but there’s one piece I’m having a bit of trouble wrapping my head around.

I’m working on a simple use case. An item is dropped from an enemy. It has a shine effect.

The item’s image is from a large Atlas texture array with many different items.

How would I adapt the following shader for such a case? I notice many of the shaders on this site seem to only work for simple, single-sprite textures:

My attempt (which is fairly close to getting what I need) is below. (Side note: This is actually quite a cool effect on its own)

shader_type canvas_item;

// --- Includes --- //
//#include "res://shaders/includes/generic_functions.gdshaderinc"

// --- Uniforms --- //
uniform vec4 shine_color: source_color = vec4(1.0, 1.0, 1.0, 0.25);

uniform float line_width: hint_range(0.0, 2.0, 0.01) = 0.1;
uniform float angle: hint_range(0.0, 6.28318530718, 0.1308996939) = 0.785398163397;

uniform float speed: hint_range(0.0, 10.0, 0.1) = 1.0;
uniform float wait_cycles: hint_range(0.0, 10.0, 0.1) = 1.0;

uniform vec2 sprite_size;
uniform vec2 atlas_size;

vec2 getPixelPosInTile(vec2 uv) {
    float exactPosX = floor(uv.x * atlas_size.x * sprite_size.x);
    float exactPosY = floor(uv.y * atlas_size.y * sprite_size.y);
    float relativePosX = mod(exactPosX, sprite_size.x);
    float relativePosY = mod(exactPosY, sprite_size.y);
    return vec2(relativePosX, relativePosY);
}

// --- Functions --- //
vec2 rotate_precalculated(vec2 _pos, float _sine, float _cosine) {
return vec2(_pos.x * _cosine + _pos.y * -_sine, _pos.x * _sine + _pos.y * _cosine);
}

void fragment() {
 vec2 pixel_pos = getPixelPosInTile(UV);
float sine = sin(angle);
float cosine = cos(angle);
float len = 1.5 - max(abs(sine), abs(cosine)) + line_width;
float line = smoothstep(-line_width, line_width, 
rotate_precalculated((pixel_pos - vec2(0.5)), sine, cosine).y - mod(TIME * speed, (len * 2.0) * wait_cycles) + len);
COLOR.rgb += shine_color.rgb * shine_color.a * vec3(line * (1.0 - line) * 4.0);
}