Пример #1
0
        private void LoadConstantOutputs(ShaderModel shader)
        {
            IList <ConstantDeclaration> constantTable = shader.ParseConstantTable();

            _activeOutputs = new Dictionary <RegisterComponentKey, HlslTreeNode>();
            _samplers      = new Dictionary <RegisterKey, HlslTreeNode>();

            foreach (var constant in constantTable)
            {
                if (constant.RegisterSet == RegisterSet.Sampler)
                {
                    var registerKey    = new RegisterKey(RegisterType.Sampler, constant.RegisterIndex);
                    var destinationKey = new RegisterComponentKey(registerKey, 0);
                    int samplerTextureDimension;
                    switch (constant.ParameterType)
                    {
                    case ParameterType.Sampler1D:
                        samplerTextureDimension = 1;
                        break;

                    case ParameterType.Sampler2D:
                        samplerTextureDimension = 2;
                        break;

                    case ParameterType.Sampler3D:
                    case ParameterType.SamplerCube:
                        samplerTextureDimension = 3;
                        break;

                    default:
                        throw new InvalidOperationException();
                    }
                    var shaderInput = new RegisterInputNode(destinationKey, samplerTextureDimension);
                    _samplers.Add(registerKey, shaderInput);
                }
                else
                {
                    for (int r = 0; r < constant.RegisterCount; r++)
                    {
                        if (constant.ParameterType != ParameterType.Float)
                        {
                            throw new NotImplementedException();
                        }
                        var registerKey = new RegisterKey(RegisterType.Const, constant.RegisterIndex + r);
                        for (int i = 0; i < 4; i++)
                        {
                            var destinationKey = new RegisterComponentKey(registerKey, i);
                            var shaderInput    = new RegisterInputNode(destinationKey);
                            _activeOutputs.Add(destinationKey, shaderInput);
                        }
                    }
                }
            }
        }
Пример #2
0
        private HlslTreeNode CreateInstructionTree(Instruction instruction, RegisterComponentKey destinationKey)
        {
            int componentIndex = destinationKey.ComponentIndex;

            switch (instruction.Opcode)
            {
            case Opcode.Dcl:
            {
                var shaderInput = new RegisterInputNode(destinationKey);
                return(shaderInput);
            }

            case Opcode.Def:
            {
                var constant = new ConstantNode(instruction.GetParamSingle(componentIndex + 1));
                return(constant);
            }

            case Opcode.DefI:
            {
                var constant = new ConstantNode(instruction.GetParamInt(componentIndex + 1));
                return(constant);
            }

            case Opcode.DefB:
            {
                throw new NotImplementedException();
            }

            case Opcode.Abs:
            case Opcode.Add:
            case Opcode.Cmp:
            case Opcode.Frc:
            case Opcode.Lrp:
            case Opcode.Mad:
            case Opcode.Max:
            case Opcode.Min:
            case Opcode.Mov:
            case Opcode.Mul:
            case Opcode.Pow:
            case Opcode.Rcp:
            case Opcode.Rsq:
            case Opcode.SinCos:
            case Opcode.Sge:
            case Opcode.Slt:
            {
                HlslTreeNode[] inputs = GetInputs(instruction, componentIndex);
                switch (instruction.Opcode)
                {
                case Opcode.Abs:
                    return(new AbsoluteOperation(inputs[0]));

                case Opcode.Cmp:
                    return(new CompareOperation(inputs[0], inputs[1], inputs[2]));

                case Opcode.Frc:
                    return(new FractionalOperation(inputs[0]));

                case Opcode.Lrp:
                    return(new LinearInterpolateOperation(inputs[0], inputs[1], inputs[2]));

                case Opcode.Max:
                    return(new MaximumOperation(inputs[0], inputs[1]));

                case Opcode.Min:
                    return(new MinimumOperation(inputs[0], inputs[1]));

                case Opcode.Mov:
                    return(new MoveOperation(inputs[0]));

                case Opcode.Add:
                    return(new AddOperation(inputs[0], inputs[1]));

                case Opcode.Mul:
                    return(new MultiplyOperation(inputs[0], inputs[1]));

                case Opcode.Mad:
                    return(new MultiplyAddOperation(inputs[0], inputs[1], inputs[2]));

                case Opcode.Pow:
                    return(new PowerOperation(inputs[0], inputs[1]));

                case Opcode.Rcp:
                    return(new ReciprocalOperation(inputs[0]));

                case Opcode.Rsq:
                    return(new ReciprocalSquareRootOperation(inputs[0]));

                case Opcode.SinCos:
                    if (componentIndex == 0)
                    {
                        return(new CosineOperation(inputs[0]));
                    }
                    return(new SineOperation(inputs[0]));

                case Opcode.Sge:
                    return(new SignGreaterOrEqualOperation(inputs[0], inputs[1]));

                case Opcode.Slt:
                    return(new SignLessOperation(inputs[0], inputs[1]));

                default:
                    throw new NotImplementedException();
                }
            }

            case Opcode.Tex:
            case Opcode.TexLDL:
                return(CreateTextureLoadOutputNode(instruction, componentIndex));

            case Opcode.DP2Add:
                return(CreateDotProduct2AddNode(instruction));

            case Opcode.Dp3:
            case Opcode.Dp4:
                return(CreateDotProductNode(instruction));

            case Opcode.Nrm:
                return(CreateNormalizeOutputNode(instruction, componentIndex));

            default:
                throw new NotImplementedException($"{instruction.Opcode} not implemented");
            }
        }