Michael Ludwig avatar Michael Ludwig committed f376cc8

Flesh out shader generation API and start converting simple_grammar package over to the implementation package.

Comments (0)

Files changed (46)

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/ArrayType.java

+package com.ferox.resource.shader;
+
+public interface ArrayType extends Type {
+    public Type getComponentType();
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/DoWhileBuilder.java

+package com.ferox.resource.shader;
+
+public interface DoWhileBuilder {
+    public Statement while_(Expression condition);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/Environment.java

+package com.ferox.resource.shader;
+
+import java.util.HashMap;
+import java.util.Map;
+
+public class Environment {
+    private final Environment parent;
+    private final Map<String, Type> variables;
+
+    public Environment() {
+        this(new HashMap<String, Type>());
+    }
+
+    public Environment(Map<String, Type> initialState) {
+        this.parent = null;
+        variables = new HashMap<String, Type>(initialState);
+    }
+
+    private Environment(Environment parent, Map<String, Type> newState) {
+        this.parent = parent;
+        variables = newState;
+    }
+
+    public Type getVariable(String name) {
+        Type inScope = variables.get(name);
+        if (inScope == null && parent != null) {
+            return parent.getVariable(name);
+        }
+        return inScope;
+    }
+
+    public Environment getParent() {
+        return parent;
+    }
+
+    public Environment declare(Type type, String name) {
+        Map<String, Type> newState = new HashMap<String, Type>(variables);
+        newState.put(name, type);
+        return new Environment(this, newState);
+    }
+
+    public Environment newScope() {
+        Map<String, Type> newState = new HashMap<String, Type>(variables);
+        return new Environment(this, newState);
+    }
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/Expression.java

+package com.ferox.resource.shader;
+
+public interface Expression extends Statement {
+    public Expression mul(Expression right);
+
+    public Expression add(Expression right);
+
+    public Expression sub(Expression right);
+
+    public Expression div(Expression right);
+
+    public Expression lessThan(Expression right);
+
+    public Expression greaterThan(Expression right);
+
+    public Expression le(Expression right);
+
+    public Expression ge(Expression right);
+
+    public Expression equals(Expression right);
+
+    public Expression notEquals(Expression right);
+
+    public Expression logicalAnd(Expression right);
+
+    public Expression logicalOr(Expression right);
+
+    public Expression logicalXor(Expression right);
+
+    public Expression negate();
+
+    public Expression not();
+
+    public Expression increment();
+
+    public Expression decrement();
+
+    public LValue field(String name);
+
+    public LValue array(Expression index);
+
+    public Type getType(Environment env);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/FragmentShader.java

+package com.ferox.resource.shader;
+
+public interface FragmentShader extends GlslElement {
+
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/FragmentShaderBuilder.java

+package com.ferox.resource.shader;
+
+import java.sql.Struct;
+
+public interface FragmentShaderBuilder {
+    public FragmentShaderBuilder uniform(Type type, String name);
+
+    public FragmentShaderBuilder constant(Type type, String name);
+
+    public FragmentShaderBuilder struct(Struct type);
+
+    public FragmentShaderBuilder in(Type type, String name);
+
+    public FragmentShaderBuilder out(Type type, String name);
+
+    public FragmentShader main(Statement... body);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/Function.java

+package com.ferox.resource.shader;
+
+import java.util.Map;
+
+public interface Function {
+    public Expression call(Expression... parameters);
+
+    public String getName();
+
+    public Map<String, Type> getParameters();
+
+    public Type getReturnType();
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/FunctionBuilder.java

+package com.ferox.resource.shader;
+
+public interface FunctionBuilder {
+    public FunctionBuilder in(Type type, String name);
+
+    public FunctionBuilder inOut(Type type, String name);
+
+    public FunctionBuilder out(Type type, String name);
+
+    public Function invoke(Statement statement);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/GlslElement.java

+package com.ferox.resource.shader;
+
+public interface GlslElement {
+    public Environment validate(Environment environment);
+
+    public void emit(ShaderAccumulator accumulator);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/IfBuilder.java

+package com.ferox.resource.shader;
+
+public interface IfBuilder {
+    public IfBuilder then(Statement... body);
+
+    public Statement fi();
+
+    public Statement else_(Statement... body);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/LValue.java

+package com.ferox.resource.shader;
+
+public interface LValue extends Expression {
+    public Statement setTo(Expression value);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/PrimitiveType.java

+package com.ferox.resource.shader;
+
+public enum PrimitiveType implements Type {
+    VOID,
+    FLOAT,
+    INT,
+    BOOL,
+    VEC2,
+    VEC3,
+    VEC4,
+    BVEC2,
+    BVEC3,
+    BVEC4,
+    IVEC2,
+    IVEC3,
+    IVEC4,
+    MAT2,
+    MAT3,
+    MAT4,
+    SAMPLER1D,
+    SAMPLER2D,
+    SAMPLER3D,
+    SAMPLERCUBE,
+    SAMPLER1DSHADOW,
+    SAMPLER2DSHADOW;
+
+    @Override
+    public String getTypeIdentifier() {
+        return name().toLowerCase();
+    }
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/ShaderAccumulator.java

+package com.ferox.resource.shader;
+
+public interface ShaderAccumulator {
+    public void addLine(String code);
+
+    public ShaderAccumulator indent();
+
+    public void accumulateFunction(Function f);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/ShaderBuilder.java

-package com.ferox.resource.shader;
-
-public interface ShaderBuilder {
-    //    Some quick notes about shader generation:
-    //
-    //        An if block is represented as three inputs (comparison + true/false responses) and outputs the selected one
-    //
-    //        this works well for single-statement if's
-    //
-    //        the generation code can perform comparison matching to merge multiple if blocks together in the actual shader code
-    //
-    //        discarding fragments is awkward, but could be represented as a special 'color' sent to the gl_Color output slot
-    //
-    //
-    //        while loops and other iterative control structures, and if statements that are complex still don't work so well with this model.  
-    //
-    //        part of me feels like they're not needed, especially since loops in general are slow, etc.
-    //        if anything loops will only be needed when doing fullscreen passes, or advanced shadow mapping.
-    //
-    //        Still should have a block/node type that allows carefully injected snippets of GLSL that can then use these advanced features. These could be restricted to be function only, so there's no inline support. The shader generator needs a way to keep track of functions in addition to the main one, so that the shadow-map block only inserts the SM code once, but each time it's referenced in the shader program, it uses the proper call site
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/Statement.java

+package com.ferox.resource.shader;
+
+public interface Statement extends GlslElement {
+
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/Struct.java

+package com.ferox.resource.shader;
+
+import java.util.Map;
+
+public interface Struct extends Type, GlslElement {
+    public Map<String, Type> getFields();
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/StructBuilder.java

+package com.ferox.resource.shader;
+
+public interface StructBuilder {
+    public StructBuilder add(Type type, String name);
+
+    public Struct build();
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/Type.java

+package com.ferox.resource.shader;
+
+public interface Type {
+    public String getTypeIdentifier();
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/VertexShader.java

+package com.ferox.resource.shader;
+
+public interface VertexShader extends GlslElement {
+
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/VertexShaderBuilder.java

+package com.ferox.resource.shader;
+
+import java.sql.Struct;
+
+public interface VertexShaderBuilder {
+    public VertexShaderBuilder uniform(Type type, String name);
+
+    public VertexShaderBuilder constant(Type type, String name);
+
+    public VertexShaderBuilder struct(Struct type);
+
+    public VertexShaderBuilder in(Type type, String name);
+
+    public VertexShaderBuilder out(Type type, String name);
+
+    public VertexShader main(Statement... body);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/WhileBuilder.java

+package com.ferox.resource.shader;
+
+public interface WhileBuilder {
+    public Statement do_(Statement... statement);
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/AbstractExpression.java

+package com.ferox.resource.shader.simple_grammar;
+
+import com.ferox.resource.shader.Expression;
+import com.ferox.resource.shader.LValue;
+import com.ferox.resource.shader.simple_grammar.BinaryExpression.BinaryOperator;
+import com.ferox.resource.shader.simple_grammar.UnaryExpression.UnaryOperator;
+
+public abstract class AbstractExpression implements Expression {
+
+    @Override
+    public Expression mul(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.MULTIPLY, right);
+    }
+
+    @Override
+    public Expression add(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.ADD, right);
+    }
+
+    @Override
+    public Expression sub(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.SUBTRACT, right);
+    }
+
+    @Override
+    public Expression div(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.DIVIDE, right);
+    }
+
+    @Override
+    public Expression lessThan(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.LESS_THAN, right);
+    }
+
+    @Override
+    public Expression greaterThan(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.GREATER_THAN, right);
+    }
+
+    @Override
+    public Expression le(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.LESS_THAN_OR_EQUAL, right);
+    }
+
+    @Override
+    public Expression ge(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.GREATER_THAN_OR_EQUAL, right);
+    }
+
+    @Override
+    public Expression equals(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.EQUAL, right);
+    }
+
+    @Override
+    public Expression notEquals(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.NOT_EQUAL, right);
+    }
+
+    @Override
+    public Expression logicalAnd(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.LOGICAL_AND, right);
+    }
+
+    @Override
+    public Expression logicalOr(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.LOGICAL_OR, right);
+    }
+
+    @Override
+    public Expression logicalXor(Expression right) {
+        return new BinaryExpression(this, BinaryOperator.LOGICAL_XOR, right);
+    }
+
+    @Override
+    public Expression negate() {
+        return new UnaryExpression(UnaryOperator.DASH, this);
+    }
+
+    @Override
+    public Expression not() {
+        return new UnaryExpression(UnaryOperator.BANG, this);
+    }
+
+    @Override
+    public Expression increment() {
+        return new UnaryExpression(UnaryOperator.POSTFIX_INCREMENT, this);
+    }
+
+    @Override
+    public Expression decrement() {
+        return new UnaryExpression(UnaryOperator.POSTFIX_DECREMENT, this);
+    }
+
+    @Override
+    public LValue field(String name) {
+        return new FieldSelection(this, name);
+    }
+
+    @Override
+    public LValue array(Expression index) {
+        return new ArrayAccess(this, index);
+    }
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/AbstractLValue.java

+package com.ferox.resource.shader.simple_grammar;
+
+import com.ferox.resource.shader.Expression;
+import com.ferox.resource.shader.LValue;
+import com.ferox.resource.shader.Statement;
+
+public abstract class AbstractLValue extends AbstractExpression implements LValue {
+    @Override
+    public Statement setTo(Expression value) {
+        return new Assignment(this, value);
+    }
+}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/ArrayAccess.java

 package com.ferox.resource.shader.simple_grammar;
 
-public class ArrayAccess implements Expression {
+import com.ferox.resource.shader.ArrayType;
+import com.ferox.resource.shader.Environment;
+import com.ferox.resource.shader.Expression;
+import com.ferox.resource.shader.PrimitiveType;
+import com.ferox.resource.shader.ShaderAccumulator;
+import com.ferox.resource.shader.Type;
+
+public class ArrayAccess extends AbstractLValue {
     private final Expression array;
     private final Expression index; // int_expression
 
         this.array = array;
         this.index = index;
     }
+
+    @Override
+    public Type getType(Environment env) {
+        return ((ArrayType) array.getType(env)).getComponentType();
+    }
+
+    @Override
+    public Environment validate(Environment environment) {
+        environment = array.validate(index.validate(environment));
+        if (!(array.getType(environment) instanceof ArrayType)) {
+            throw new IllegalStateException("Expression does not evaluate to an array type");
+        } else if (!index.getType(environment).equals(PrimitiveType.INT)) {
+            throw new IllegalStateException("Index expression does not evaluate to an integer type");
+        }
+        return environment;
+    }
+
+    @Override
+    public void emit(ShaderAccumulator accumulator) {
+        // TODO Auto-generated method stub
+
+    }
 }

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/ArrayDeclaration.java

-package com.ferox.resource.shader.simple_grammar;
-
-public class ArrayDeclaration implements Declaration {
-    //    private final TypeQualifier qualifier; FIXME
-    private final Type type;
-    private final String identifier;
-    private final Expression bracketExpression; // must nest for >= assignment expression
-
-    public ArrayDeclaration(Type type, String identifier,
-                                      Expression bracketExpression) {
-        this.type = type;
-        this.identifier = identifier;
-        this.bracketExpression = bracketExpression;
-    }
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Assignment.java

 package com.ferox.resource.shader.simple_grammar;
 
-public class Assignment implements Expression, RightAssociative {
-    public static enum AssignmentOperator {
-        EQUAL,
-        MUL_ASSIGN,
-        DIV_ASSIGN,
-        MOD_ASSIGN,
-        ADD_ASSIGN,
-        SUB_ASSIGN
-        // FIXME insert logical and bitwise assignment operators
+import com.ferox.resource.shader.Environment;
+import com.ferox.resource.shader.Expression;
+import com.ferox.resource.shader.LValue;
+import com.ferox.resource.shader.ShaderAccumulator;
+import com.ferox.resource.shader.Statement;
+
+public class Assignment implements Statement, RightAssociative {
+    private final LValue lvalue;
+    private final Expression rvalue;
+
+    public Assignment(LValue lvalue, Expression rvalue) {
+        this.lvalue = lvalue;
+        this.rvalue = rvalue;
     }
 
-    private final Expression lvalue;
-    private final AssignmentOperator operator;
-    private final Expression rvalue;
+    @Override
+    public Environment validate(Environment environment) {
+        environment = lvalue.validate(rvalue.validate(environment));
+        if (!lvalue.getType(environment).equals(rvalue.getType(environment))) {
+            throw new IllegalStateException("Value does not have same type as variable");
+        }
+        return environment;
+    }
 
-    public Assignment(Expression lvalue, AssignmentOperator operator,
-                                        Expression rvalue) {
-        this.lvalue = lvalue;
-        this.rvalue = rvalue;
-        this.operator = operator;
+    @Override
+    public void emit(ShaderAccumulator accumulator) {
+        // TODO Auto-generated method stub
+
     }
 }

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/BinaryExpression.java

 package com.ferox.resource.shader.simple_grammar;
 
-public class BinaryExpression implements Expression, LeftAssociative {
+import com.ferox.resource.shader.Environment;
+import com.ferox.resource.shader.Expression;
+import com.ferox.resource.shader.ShaderAccumulator;
+import com.ferox.resource.shader.Type;
+
+public class BinaryExpression extends AbstractExpression implements LeftAssociative {
     public static enum BinaryOperator {
         MULTIPLY,
         DIVIDE,
         this.right = right;
         this.operator = operator;
     }
+
+    @Override
+    public Type getType(Environment env) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+    @Override
+    public Environment validate(Environment environment) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+    @Override
+    public void emit(ShaderAccumulator accumulator) {
+        // TODO Auto-generated method stub
+
+    }
 }

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/CompoundStatement.java

-package com.ferox.resource.shader.simple_grammar;
-
-public class CompoundStatement implements Statement {
-    private final Statement[] statements;
-
-    public CompoundStatement(Statement... statements) {
-        this.statements = statements;
-    }
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Constant.java

 package com.ferox.resource.shader.simple_grammar;
 
-public class Constant implements Expression {
+import com.ferox.resource.shader.Environment;
+import com.ferox.resource.shader.PrimitiveType;
+import com.ferox.resource.shader.ShaderAccumulator;
+import com.ferox.resource.shader.Type;
+
+public class Constant extends AbstractExpression {
     private final Object value;
+    private final Type type;
 
     public Constant(int value) {
         this.value = Integer.valueOf(value);
+        this.type = PrimitiveType.INT;
     }
 
     public Constant(float value) {
         this.value = Float.valueOf(value);
+        this.type = PrimitiveType.FLOAT;
     }
 
     public Constant(boolean value) {
         this.value = Boolean.valueOf(value);
+        this.type = PrimitiveType.BOOL;
+    }
+
+    @Override
+    public Type getType(Environment env) {
+        return type;
+    }
+
+    @Override
+    public Environment validate(Environment environment) {
+        return environment;
+    }
+
+    @Override
+    public void emit(ShaderAccumulator accumulator) {
+        // TODO Auto-generated method stub
+
     }
 }

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Declaration.java

-package com.ferox.resource.shader.simple_grammar;
-
-public interface Declaration extends ExternalDeclaration, Statement, ForLoopInitializer {
-
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/EmptyExpression.java

-package com.ferox.resource.shader.simple_grammar;
-
-public class EmptyExpression implements Expression {
-
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Expression.java

-package com.ferox.resource.shader.simple_grammar;
-
-public interface Expression extends Statement, WhileLoopCondition, ForLoopInitializer {
-
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/ExternalDeclaration.java

-package com.ferox.resource.shader.simple_grammar;
-
-public interface ExternalDeclaration {
-
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/FieldSelection.java

 package com.ferox.resource.shader.simple_grammar;
 
-public class FieldSelection implements Expression {
+import com.ferox.resource.shader.Environment;
+import com.ferox.resource.shader.Expression;
+import com.ferox.resource.shader.ShaderAccumulator;
+import com.ferox.resource.shader.Struct;
+import com.ferox.resource.shader.Type;
+
+public class FieldSelection extends AbstractLValue {
     private final Expression variable;
     private final String field;
 
         this.variable = variable;
         this.field = field;
     }
+
+    @Override
+    public Type getType(Environment env) {
+        Type base = variable.getType(env);
+        if (base instanceof Struct) {
+            return ((Struct) base).getFields().get(field);
+        } else {
+            // assume that this is a vector type, must return float/int/bool
+            // or the vectorized versions of those based on the length of its
+            // swizzle
+            // FIXME what about matrix components?
+        }
+        return null;
+    }
+
+    @Override
+    public Environment validate(Environment environment) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+    @Override
+    public void emit(ShaderAccumulator accumulator) {
+        // TODO Auto-generated method stub
+
+    }
 }

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/ForLoopInitializer.java

-package com.ferox.resource.shader.simple_grammar;
-
-public interface ForLoopInitializer {
-
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Jump.java

 package com.ferox.resource.shader.simple_grammar;
 
+import com.ferox.resource.shader.Environment;
+import com.ferox.resource.shader.Expression;
+import com.ferox.resource.shader.ShaderAccumulator;
+import com.ferox.resource.shader.Statement;
+
 public class Jump implements Statement {
     public static enum JumpType {
         BREAK,
         type = JumpType.RETURN;
         this.returnExpression = returnExpression;
     }
+
+    @Override
+    public Environment validate(Environment environment) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+    @Override
+    public void emit(ShaderAccumulator accumulator) {
+        // TODO Auto-generated method stub
+
+    }
 }

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/NamedType.java

-package com.ferox.resource.shader.simple_grammar;
-
-public class NamedType implements Type {
-    private final String name;
-
-    public NamedType(String name) {
-        this.name = name;
-    }
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Parameter.java

-package com.ferox.resource.shader.simple_grammar;
-
-public class Parameter {
-    private final Type type;
-    private final String identifier; // nullable for unlabeled parameter
-    private final Expression bracketExpression; // nullable for non-array type, must wrap for > assignmentexpressions
-
-    public Parameter(Type type, String identifier, Expression bracketExpression) {
-        this.type = type;
-        this.identifier = identifier;
-        this.bracketExpression = bracketExpression;
-    }
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/ParameterDeclaration.java

-package com.ferox.resource.shader.simple_grammar;
-
-public class ParameterDeclaration {
-    public static enum ParameterQualifier {
-        IN,
-        OUT,
-        INOUT
-    }
-
-    private final ParameterQualifier paramQualifier;
-
-    private final Parameter parameter;
-
-    public ParameterDeclaration(ParameterQualifier paramQualifier, Parameter parameter) {
-        this.paramQualifier = paramQualifier;
-        this.parameter = parameter;
-    }
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/PrimitiveType.java

-package com.ferox.resource.shader.simple_grammar;
-
-public enum PrimitiveType implements Type {
-    VOID,
-    FLOAT,
-    INT,
-    BOOL,
-    VEC2,
-    VEC3,
-    VEC4,
-    BVEC2,
-    BVEC3,
-    BVEC4,
-    IVEC2,
-    IVEC3,
-    IVEc4,
-    MAT2,
-    MAT3,
-    MAT4,
-    SAMPLER1D,
-    SAMPLER2D,
-    SAMPLER3D,
-    SAMPLERCUBE,
-    SAMPLER1DSHADOW,
-    SAMPLER2DSHADOW
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/QualifiedType.java

-package com.ferox.resource.shader.simple_grammar;
-
-public class QualifiedType implements Type {
-    public static enum TypeQualifier {
-        UNIFORM,
-        IN, // attribute/varying
-        OUT, // varying
-        CONST,
-    }
-
-    private final TypeQualifier qualifier;
-    private final Type type;
-
-    public QualifiedType(TypeQualifier qualifier, Type type) {
-        if (type instanceof QualifiedType) {
-            throw new IllegalArgumentException("Cannot qualify a qualified type");
-        }
-        this.qualifier = qualifier;
-        this.type = type;
-    }
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Statement.java

-package com.ferox.resource.shader.simple_grammar;
-
-public interface Statement {
-
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Type.java

-package com.ferox.resource.shader.simple_grammar;
-
-public interface Type {
-
-}

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/UnaryExpression.java

 package com.ferox.resource.shader.simple_grammar;
 
-public class UnaryExpression implements Expression {
+import com.ferox.resource.shader.Environment;
+import com.ferox.resource.shader.Expression;
+import com.ferox.resource.shader.ShaderAccumulator;
+import com.ferox.resource.shader.Type;
+
+public class UnaryExpression extends AbstractExpression {
     public static enum UnaryOperator {
         // FIXME other expressions are between the postfix and prefix in terms of precedence
         // is that awkward?
         this.operator = operator;
         this.expression = expression;
     }
+
+    @Override
+    public Type getType(Environment env) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+    @Override
+    public Environment validate(Environment environment) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+    @Override
+    public void emit(ShaderAccumulator accumulator) {
+        // TODO Auto-generated method stub
+
+    }
 }

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/Variable.java

 package com.ferox.resource.shader.simple_grammar;
 
-public class Variable implements Expression {
+import com.ferox.resource.shader.Environment;
+import com.ferox.resource.shader.ShaderAccumulator;
+import com.ferox.resource.shader.Type;
+
+public class Variable extends AbstractLValue {
     private final String identifier;
 
     public Variable(String identifier) {
         this.identifier = identifier;
     }
+
+    @Override
+    public Type getType(Environment env) {
+        return env.getVariable(identifier);
+    }
+
+    @Override
+    public Environment validate(Environment environment) {
+        if (environment.getVariable(identifier) == null) {
+            throw new IllegalStateException("No variable with name: " + identifier);
+        }
+        return environment;
+    }
+
+    @Override
+    public void emit(ShaderAccumulator accumulator) {
+        // TODO Auto-generated method stub
+
+    }
 }

ferox-renderer/ferox-renderer-api/src/main/java/com/ferox/resource/shader/simple_grammar/WhileLoopCondition.java

-package com.ferox.resource.shader.simple_grammar;
-
-public interface WhileLoopCondition {
-
-}
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.