DreamShaderLang
HLSL / GLSL Background

Keyword Cheatsheet

Every word DreamShaderLang's grammar treats specially — the 1.x blocks, sections, qualifiers and contextual keywords, the .dss declarations,

A lookup page. The DreamShaderLang tables are exhaustive: the 1.x block keywords, section names, qualifiers and contextual keywords, the .dss declaration forms, #pragmas and /// tags, and the reserved words are the complete sets the grammar recognises. The HLSL and GLSL tables are for reference when arriving from those languages.

Block keywords, section names and type names are not reserved against identifiers. A property, output variable, parameter or function may be named Shader, Graph or Layout; they are recognised only where the grammar expects them. The exception is a small set of reserved words since 2.0.0. The names of math builtins and constructors cannot name a function either — that is DSH6206 at the declaration (through 1.9.x it silently shadowed).

.dss declaration forms

since 2.0.0 A .dss is HLSL with declarations: these are the only forms at file scope. The full grammar is on DreamShaderLang 2.0.

FormMeaning
uniform <Type> Name = <init>;a material parameter. uniform bool is a dynamic scalar by default; /// @static makes it a static switch
static const <Type> Name = <init>;a compile-time constant
<Type> Name(params) { … }a file-local helper; no linkage keyword
export <Type> Name(params) { … }produces an asset: void (inout material) is a material, anything else a material function
extern <Type> Name(params);a prototype bound to an existing asset through /// @asset; no body
struct Name { … };fields may carry their own /// block and array dimensions; no methods, no nesting
#include "path" · import "path";the same thing; the path must be double-quoted
#pragma material(Key = Value, …)file-level material settings; a key set twice is DSH7200
#pragma layout(Node|Comment, Key = Value, …)node coordinates and comment boxes, written by the decompiler
#pragma region Name · #pragma endregionthe 2.0 spelling of the 1.x #Region comment box

The other #pragma names are instance (.dsi) and pipeline (.dsp). Types particular to a .dss: material (a material attribute set; the entry's parameter is inout material m), void, and user structs.

/// tags

The /// lines above a declaration are its doc block: @key value @key value … per line, keys case-insensitive.

TagOnMeaning
@group, @sort, @desca uniformgroup, sort order and description on the parameter panel
@slider min maxa scalar uniformslider range; on a vector or a switch it is the warning DSH7233
@default /Game/…a texture uniformthe default asset
@samplera texture uniformthe sampler type
@statica uniform boola static switch
@namean export function, a @custom functionthe asset name (or object path); the node title
@assetan extern prototypethe existing asset it binds to
@library, @paraman exported material functionthe library category; the description of an input
@layer, @layerblendan exported functionproduces a material layer / layer blend function
@customa functionthe body is captured verbatim, one Custom node per call

1.x top-level block keywords

Case-sensitive, matched as a whole word — ShaderFunction is its own word, never Shader followed by something. A mis-cased one (shader(…)) is no block: DSH2240.

KeywordHeaderRequiredGenerates
ShaderShader(Name = "…"[, Root = "…"])NameUMaterial
ShaderFunctionShaderFunction(Name = "…"[, Root = "…"])NameUMaterialFunction
ShaderLayer since 1.3.0ShaderLayer(Name = "…"[, Root = "…"])NameUMaterialFunctionMaterialLayer
ShaderLayerBlend since 1.3.0ShaderLayerBlend(Name = "…"[, Root = "…"])NameUMaterialFunctionMaterialLayerBlend
MaterialLayer (deprecated in 1.3.0)MaterialLayer(Name = "…"[, Root = "…"])Nameas ShaderLayer
MaterialLayerBlend (deprecated in 1.3.0)MaterialLayerBlend(Name = "…"[, Root = "…"])Nameas ShaderLayerBlend
VirtualFunction since 1.2.0VirtualFunction(Name = "…"[, Asset = "…"])Name, and an asset from Asset = or Options.Assetnothing — declares an existing asset
NamespaceNamespace(Name = "…")Namenothing — a scope for helpers
FunctionFunction [SelfContained | Inline] [<ret>] <Name>( … ) { <HLSL> }a name, at least one outputan HLSL helper — one Custom node per call
GraphFunction since 1.3.1GraphFunction [<ret>] <Name>( … ) { <HLSL> }a name, at least one outputan HLSL helper with node inputs

Shader is limited to one per file (DSH2250), and a .dsh header holds no asset block at all (DSH2249), so an import cannot add a second one. Every other block may repeat. Function and GraphFunction may also appear nested inside Namespace, where their names become <Namespace>::<Name>.

Deprecated since 1.3.0

Use ShaderLayer instead.

MaterialLayer and MaterialLayerBlend still parse and generate identical assets, with the warning DSH2251. Later diagnostics and generated metadata report the modern spelling.

1.x section names

Case-insensitive. The = before the block is optional since 1.5.0, as is the ; after it. Sections may appear in any order and repeat: Properties, Inputs and Outputs append, Settings merges key by key, and a second Graph or Layout replaces the first with the warning DSH2258. A name the block does not take is DSH2245.

NameAccepted inMeaning
PropertiesShader, ShaderFunction, ShaderLayer, ShaderLayerBlendparameter, const and UE.* node declarations
PropertiesVirtualFunctionalias for Inputs — typed parameters, not parameter nodes
InputsShaderFunction, ShaderLayer, ShaderLayerBlend, VirtualFunctiontyped input parameters
OutputsShaderFunction, ShaderLayer, ShaderLayerBlend, VirtualFunctiontyped output parameters
OutputsShaderoutput declarations and bindings — a different grammar
ResultsShaderFunction, ShaderLayer, ShaderLayerBlend, VirtualFunctionalias for Outputs
SettingsShadermaterial settings — special keys plus reflected UMaterial properties
SettingsShaderFunction, ShaderLayer, ShaderLayerBlendthe material-function keys
SettingsVirtualFunctionalias for Options
OptionsVirtualFunctionthe declared asset and other stored keys
GraphShader, ShaderFunction, ShaderLayer, ShaderLayerBlendthe node-graph body
Code—rejected everywhere (DSH2246; in a VirtualFunction both Graph and Code are DSH2247); use Graph
LayoutShader, ShaderFunction, ShaderLayer, ShaderLayerBlendNode / Comment placement

Function and GraphFunction have no sections at all — their { … } is raw HLSL.

1.x declaration qualifiers

QualifierPositionEffect
const since 1.2.6before the type in a Properties declarationemits a constant node instead of a parameter; refused on most parameter-node tokens (DSH3253)
opt since 1.2.3before the type in an Inputs declarationmarks the function input optional in Unreal; recognised when a type and a name follow it
inbefore a Function / GraphFunction parameter typeinput parameter; the default when a parameter has only two words
outbefore a Function / GraphFunction parameter typeoutput parameter; at least one is required unless a return type is declared, and none may stand beside one (DSH6305, DSH6304)
SelfContainedafter Functionread and ignored: every Function node already embeds what its body calls since 2.0.0; not accepted on GraphFunction (DSH6307)
Inlineafter Functionthe old spelling of SelfContained, with the warning DSH6306

in and out are the only qualifiers accepted on a function parameter, in any case; anything else, inout included, is DSH6302.

1.x contextual keywords

Recognised only in the position listed, and case-insensitively unless the row says otherwise.

KeywordPositionMeaning
importtop level, between blocksdeclares the names of a .dsh header into this file since 2.0.0 (1.x pasted the file in); lower case — another case reads the same, with the warning DSH2253
Group("…") { … } since 1.5.0statement position inside Propertiesscopes a parameter group onto every declaration inside; nests, composing with |
Slider(min, max) since 1.5.0entry inside a [ … ] metadata blocksets a scalar parameter's UI range
Path( … )default value of a texture or asset-valued declarationasset reference with a root spelling
Base.start of an Outputs binding targetbinds to a material property
Expression( … )start of an Outputs binding targetbinds to a pin on a reflected node; Class="…" is mandatory
.Pin[<index>]after an Expression( … ) targetselects the pin to bind
Node( … )statement inside Layoutpins a variable's node position
Comment( … )statement inside Layoutplaces a comment box
#Region / #EndRegionown line inside a Graph bodynames a region of the graph; nests
#if / #elif / #else / #endif since 1.9.0own line, anywhere except a Function / GraphFunction HLSL bodycuts the untaken branch out of the text before parsing; lowercase only
#ifdef / #ifndef since 1.9.0own line, same positionssugar for #if defined(NAME) and #if !defined(NAME)
#define / #undef since 1.9.0own line, same positionsdefines or removes a name, for that file only
defined since 1.9.0inside a #if / #elif expression1 when the name is defined, 0 otherwise
UE.type position in Properties, call position in Graphbuiltin material-node namespace; in a Graph call written exactly UE since 2.0.0
Substrate.call position in Graphthe Substrate node namespace, since UE 5.4
true / falsedefault values, Graph expressionsboolean literal; converts to 1.0 / 0.0 where a scalar is expected
default since 1.2.3call argument in Graphleaves that input unconnected, so the function's own default applies; lower case only since 2.0.0

The preprocessor works in a .dss too; see Lexical rules ▸ Preprocessor.

Reserved words

since 2.0.0 One lexer reads every file, and its keywords are reserved in a 1.x file too, in lower case: uniform static const extern export in out inout struct if else for while do return break continue discard true false import. None of them can name a property, an output, an input or a Graph variable. Another case is an ordinary word: Const and IN are read as const and in where the 1.x grammar expects those, and True as true. See Lexical rules ▸ Reserved words.

Reserved names

NameWhereRule
__returnFunction / GraphFunction parameter namesreserved in any case; a parameter of that name is DSH6303
returneverywherea reserved word: it cannot name an output variable, and is no binding source since 2.0.0
DS_… since 1.9.0preprocessor define namesthe whole DS_ prefix is DreamShader's: #define or #undef of such a name is DSH1039, and the other define tiers drop it with a warning

return inside a Function body is HLSL, kept as written since 2.0.0; a bare return; in a function that declares a return type is DSH6308.

Type tokens

The complete set is 52 tokens. Per-context validity is on Types and Values.

FamilyTokensCount
Scalar (1 component)float half double int uint bool, and each with a 1 suffix (float1 …)12
Vector (2 / 3 / 4 components)float2..4 half2..4 double2..4 int2..4 uint2..4 bool2..4 vec2..4 ivec2..4 uvec2..4 bvec2..430
TextureTexture2D TextureCube Texture2DArray Texture3D VolumeTexture5
Opaque / otherSamplerState MaterialAttributes Substrate StaticBool StaticBoolParameter5

vec* / ivec* / uvec* / bvec* are types in a 1.x source only; a .dss writes the HLSL spelling, and adds material, void and user structs. A graph has no matrix values: mat2 / mat3 / mat4 and float2x2 / float3x3 / float4x4 are DSH3252 in Properties and DSH4361 where they would become a node or a pin. Three tokens have been removed:

Removed tokenReplacement
Scalarfloat
Colorfloat4 / vec4
Vectorfloat2 … float4 / vec2 … vec4

1.x Properties declarations can also use the explicit *Parameter node tokens (ScalarParameter, TextureSampleParameter2D, ChannelMaskParameter, …), catalogued on Property types.

Identifier rewrites

Applied only inside 1.x Function and GraphFunction declarations, before HLSL is emitted. Matching is case-insensitive and whole-identifier; strings and comments are skipped, and a ::-qualified name bypasses the table — it is flattened to <Namespace>_<Name>. A .dss /// @custom body is not rewritten.

WrittenRewritten toApplies to
vec2 vec3 vec4float2 float3 float4parameter and return types, body text
ivec2 ivec3 ivec4int2 int3 int4parameter and return types, body text
uvec2 uvec3 uvec4uint2 uint3 uint4parameter and return types, body text
bvec2 bvec3 bvec4bool2 bool3 bool4parameter and return types, body text
mat2 mat3 mat4float2x2 float3x3 float4x4parameter and return types, body text
mixlerpbody text only
fractfracbody text only
modfmodbody text only

HLSL keywords

For reference — HLSL's own vocabulary, valid inside a /// @custom or Function body; .dss graph code understands most of it, see HLSL Overview.

CategoryKeywords
Typesvoid, bool, int, uint, half, float, double
Control flowif, else, for, while, do, switch, case, default
Jumpsreturn, break, continue, discard
Parametersin, out, inout
Modifiersconst, static, uniform, groupshared
TexturesTexture2D, TextureCube, SamplerState, SamplerComparisonState
Aggregatesstruct

GLSL keywords

For reference — nothing here is part of the DreamShaderLang grammar except the vec* / ivec* / uvec* / bvec* type aliases of a 1.x source, which are first-class tokens.

CategoryKeywords
Typesvoid, bool, int, uint, float, double, vec2, vec3, vec4, mat2, mat3, mat4
Control flowif, else, for, while, do, switch, case, default
Jumpsreturn, break, continue, discard
Parametersin, out, inout
Modifiersconst, uniform, layout, centroid, flat, smooth, attribute, varying
Precisionlowp, mediump, highp

Migration reminders

HabitIn DreamShaderLang
vec3write float3 in a .dss; in 1.x vec3 is a real token, read as float3
mix(a, b, t), fract(x), mod(a, b)write lerp, frac, fmod. In a 1.x Graph the GLSL spellings still compile, with the warning DSH5277; in a .dss they are the error DSH4250; in a 1.x Function body they are rewritten
length(v), distance, exp, logall builtins — spelled the same in both languages
main()a .dss entry, export void M(inout material m); in 1.x a Shader block with Outputs bindings
uniformin a .dss it is uniform, with /// tags; in 1.x a Properties declaration
sampler2D + texture(s, uv).dss: Tex.Sample(uv); 1.x: SampleTexture2D(tex, uv) for a texture object, Tex(Coordinates = uv) for a TextureSampleParameter*
HLSL Custom node bodiesa /// @custom function in a .dss; in 1.x a Function, or a GraphFunction when the body needs UE.* values
Visual material nodesthe specific UE.* builtin, or UE.Expression(Class = "…")
Shared include filesa .dsh header with #include (.dss) or import (1.x)

Where to next

On this page