Sign in to follow this  
Axiverse

Constructing HLSL from snippits or nodes.

Recommended Posts

I've seen some engines (e.g. the offset engine) uses a node type architecture to define their shaders. I'm just wondering how would one go about and convert the node tree into a HLSL shader?

Share this post


Link to post
Share on other sites
I haven't implemented a shader graph compiler (yet) but I have done assembly language compiler/decompiler work and it seems similar.

So, each node obviously has its inputs and outputs, and probably defines an HLSL code fragment. You need to:

1. For the 'start' node, replace its input variable names with shader input references.
2. For the 'end' node, replace its output variable names with shader output references.
3. For each node, figure out what outputs are hooked up to other nodes. Make temporary variables for those outputs.
4. Determine an execution order for each node. The simplest way is to start at the start node of the graph and visit all nodes once using a breadth first traversal, assigning an incremented value to each new node you visit. Then sort the nodes by that value for your execution order.
5. Replace input variable names in each node with the appropriate temporary variable you generated in step 3.
6. Write out a bunch of HLSL text using your execution order and temporary variable names.

It will get more complicated if you allow conditional branching in your shaders though. That should get you started.


A breadth first traversal would look something like this:


queue = new Queue();
queue.Enqueue(the starting node);

int counter = 0;

while (queue.Count() > 0)
{
current = queue.Dequeue();

current.ID = counter;
counter++;

foreach (successor in current.successors)
{
if (the successor has never been added to the queue)
{
queue.Enqueue(successor);
}
}
}


[Edited by - Nypyren on August 1, 2007 10:07:00 PM]

Share this post


Link to post
Share on other sites
It is a potentially very powerful architecture to adopt. If you combine fragment linking (note: this does (or did) exist in D3DX9) with a multi-pass/layered approach then you can give your artists a huge amount of flexibility and get a really solid data-driven architecture.

I'm not aware of there being any standard tricks involved in implementing it. Nypyren's suggestions are as good as any to get started from - beyond this it gets as complicated as you want to allow it [smile]

Have a dig around in the DirectXDev mailing list archives as there have been various discussions over the years on exactly this topic. The regulars on that list have implemented these architectures for commercial games, so you'd hope they know what they're talking about [wink]

hth
Jack

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this