"Redefinition of _Time" error in Custom Function Node

Hello,
I have been running into trouble getting the new Custom Function Node to do just about anything. I have followed a number of examples online but any time I try use
#include “Packages/com.unity.render-pipelines.lightweight/ShaderLibrary/Lighting.hlsl” the node throws the error “redefinition of _Time” and I can not seem to find anyone who has a solution to this problem. Any help would be appreciated!

The different hlsl files I have tried to use are :

#include "Packages/com.unity.render-pipelines.lightweight/ShaderLibrary/Lighting.hlsl"
void GetMainLightD_float(out float3 Direction, out float3 Color, out float Attenuation)
{
    #ifdef SHADERGRAPH_PREVIEW
        Direction = float3(-0.5, 0.5, -0.5);
        Color = float3(1,1,1);
        Attenuation = 0.4;
    #else
        Light light = GetMainLight();
        Direction = light.direction;
        Attenuation = light.distanceAttenuation;
        Color = light.color;
    #endif
}

and

#include "Packages/com.unity.render-pipelines.lightweight/ShaderLibrary/Lighting.hlsl"
void GetMainLightDir_float(out float3 lightDir)
{
    lightDir = GetMainLight().direction;
}

Instead of the include, try wrapping your function in an ifdef for lighting:

#ifdef LIGHTWEIGHT_LIGHTING_INCLUDED
    //function body
#endif

It’s not the prettiest, but it should work just fine without the redefinition errors.

2 Likes

Thank you so much! This fixes that problem, though now I am dealing with “output Parameter ‘Direction’ not completely initialized”, which is also giving me trouble.

Is there some documentation or information on using the Custom Function node that I am missing? Really appreciate the help and I don’t want to take too much of your time!

Solved it! Simply had to add a little code, final results below, haven’t really tested it yet though its at least nice to not face an error.

void GetLightingInformation_float(out float3 Direction, out float3 Color,out float Attenuation)
{
    Direction = float3 (0,0,0);
        Color = float3 (0,0,0);
        Attenuation = 0;
   
    #ifdef LIGHTWEIGHT_LIGHTING_INCLUDED

    Light mainLight = GetMainLight();
            Color = mainLight.color;
            Direction = mainLight.direction;
            float4 shadowCoord;
            #ifdef _SHADOWS_ENABLED
            #if SHADOWS_SCREEN
                float4 clipPos = TransformWorldToHClip(WorldPos);
                shadowCoord = ComputeShadowCoord(clipPos);
            #else
                shadowCoord = TransformWorldToShadowCoord(WorldPos);
            #endif
            mainLight.attenuation = MainLightRealtimeShadowAttenuation(shadowCoord);
            #endif
            Attenuation = mainLight.attenuation;
#endif
   
}

Thanks again for the help!

1 Like

We’re working on getting our updated docs and a bit of demo content up for the Custom Function Node but it isn’t live yet!

3 Likes

Did you manage to get this code to work?

If so, please let me know how. I only got the default 0 value’s declared at the top returned.

(if not, this should work as a temporary solution)

@alexandral_unity
Since no documentation was written by Unity, and I’ve been frying my brain with trial and error for the last week.
I would like to know how to make this shader code work with the Universal RP.

No matter what #includes I add or remove, how many #ifdefs I tried I keep getting identifier undeclared errors.
The furthest I got is by surrounding only the function bodies with:

#ifdef UNIVERSAL_LIGHTING_INCLUDED
....
#endif

Because doing it globally makes my function names undeclared, and then initialize my out vars before, which is even more stupid.

But then I would get this weird: Shader error in 'Unlit Master': 'GetAdditionalLight': no matching 2 parameter function
And yet one more undeclared identifier 'WorldPos'

Complete code:

half3 Lambert_half(half3 N, half3 color, half3 direction, half distAtten, half shadowAtten) // Could use LightingLambert directly from calling site instead
{
#ifdef UNIVERSAL_LIGHTING_INCLUDED

    half3 attenColor = color * distAtten * shadowAtten;
    half NdotL = saturate(dot(N, direction));

    return NdotL * attenColor;
#endif
}

half3 BlinnPhong_half(half3 N, half3 V, half3 color, half3 direction, half3 specColor, half smoothness)
{
#ifdef UNIVERSAL_LIGHTING_INCLUDED

    smoothness = exp2(10 * smoothness + 1);

    N = normalize(N);
    V = SafeNormalize(V);

    half3 Out = LightingSpecular(color, direction, N, V, half4(specColor, 0), smoothness);
    return Out;
#endif
}

void DiffSpec_half(half3 N, half3 V, half3 WorlPos, half3 SpecColor, half Smoothness,  out half3 Diffuse, out half3 Specular)
{  
    Diffuse = 0;
    Specular = 0;
#ifdef UNIVERSAL_LIGHTING_INCLUDED

    half3 diffuseColor = 0;
    half3 specularColor = 0;
 
    Light l = GetMainLight(); // GET MAIN LIGHT
    int pixelLightCount = GetAdditionalLightsCount();

    diffuseColor += Lambert_half(N, l.color, l.direction, l.distanceAttenuation, l.shadowAttenuation);

    specularColor += BlinnPhong_half(N, V, l.color, l.direction, SpecColor, Smoothness);           

    for (int i = 0; i < pixelLightCount; ++i)
    {
        Light light = GetAdditionalLight(i, WorldPos); // GET ADDT LIGHTS
        diffuseColor += Lambert_half(N, light.color, light.direction, light.distanceAttenuation, light.shadowAttenuation);
        specularColor += BlinnPhong_half(N, V, light.color, light.direction, SpecColor, Smoothness);
    }

    Diffuse = diffuseColor;
    Specular = specularColor;
#endif
}

I also would like to know how to get vertex data and view data and matrices from shader code.
And of cource proper documentation from the responsible team and opening issues section in the GitHur repo.

1 Like

@alexandral_unity Wrapping my for loop in ```
#ifdef _ADDITIONAL_LIGHTS

Stopped the error because it's not defined but I can't sample additional lights.
Is there any improvements on custom shader functions?

#ifdef UNIVERSAL_LIGHTING_INCLUDED”
This does not work. Was the name changed?

2 Likes

WHAT A FUCKING MESS

7 Likes

If anybody is interested I developed a short elegant solution for this:

I’m using Unity 2020.3.7 and URP 10.4.0 and got the same problems of _Time redefinition in lighting.hlsl.

I tried all the solution above and nothing works.

So I ask if there is a way to downgrade the URP version ?

Yes you can downgrade but it won’t solve your problem.
Are defining or referencing a Light struct?

LIGHTWEIGHT_LIGHTING_INCLUDED is defined by Lighting.hlsl in LWRP, it is renamed to
UNIVERSAL_LIGHTING_INCLUDED in URP 。UNIVERSAL_LIGHTING_INCLUDED should work.
the path of Lighting.hlsl is “Library/PackageCache/com.unity.render-pipelines.universal@10.5.1/ShaderLibrary/Lighting.hlsl”

#ifdef UNIVERSAL_LIGHTING_INCLUDED 
    //function body
#endif

Just in case someone stumbled upon this issue:

The bullet-proof way to define your own lighting function in a .hlsl is:

#if !SHADERGRAPH_PREVIEW
#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl"
#endif

#ifndef MY_CUSTOM_LIGHTING
#define MY_CUSTOM_LIGHTING

void MainLight_float(out float3 Direction, out float3 Color)
{
#if SHADERGRAPH_PREVIEW
    Direction = float3(0.5, 0.5, 0);
    Color = float3(1, 1, 1);
#else
    Light light = GetMainLight();
    Direction = light.direction;
    Color = light.color;
#endif
}

#endif

Don’t do anything with UNIVERSAL_LIGHTING_INCLUDED.

The actual culprit is not Lighting.hlsl, but the preview in shader graph. For unknown stupid reasons, the preview seems to be generated by some built-in cg program, which doesn’t work with those URP shaderlibrary files.

12 Likes

How could I include “Packages/com.unity.render-pipelines.universal/ShaderLibrary/Input.hlsl” ?

If I do what you said I’m getting: “unrecognised identifier InputData”, and if I put the include after I get this error: “Redefinition of _Time”.

Hello, you dont need to include “Packages/com.unity.render-pipelines.universal/ShaderLibrary/Input.hlsl”, because it is already included by “Packages/com.unity.render-pipelines.universal/ShaderLibrary/RealtimeLights.hlsl”, wich is itself included by “Packages/com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl”.

So with just “Lighting” you have all you’re looking for.
And if you want to whatever case have “Input.hlsl”, you have to replace this :

  • #if !SHADERGRAPH_PREVIEW
  • #include “Packages/com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl”
  • #endif

With this :

  • #if !SHADERGRAPH_PREVIEW
  • #include “Packages/com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl”
  • #else
  • #include “Packages/com.unity.render-pipelines.universal/ShaderLibrary/Input.hlsl”
  • #endif

Hope this help you ^^

YOU ARE A GOD!!! THIS WORKS!!! And by using this method I can successfully include any hlsl in URP package!!! LEGEND!!!