Exemple #1
0
        private void ParseImgCmd(Compiler.Command cmd, Dict classes, CompileException err)
        {
            if (cmd.ArgCount != 1 && cmd.ArgCount != 6)
            {
                err.Add("Arguments of the 'img' command are invalid.", cmd);
                return;
            }
            // specify argument types
            var types = new[] {
                typeof(GLTexture),
                typeof(int),
                typeof(int),
                typeof(int),
                typeof(TextureAccess),
                typeof(GpuFormat),
                typeof(string)
            };
            // specify mandatory arguments
            var mandatory = new[] {
                new[] { true, true, true, true, true, true, false },
                new[] { false, true, false, false, false, false, false },
            };

            // parse command arguments
            (var values, var unused) = cmd.Parse(types, mandatory, classes, err);
            // if there are no errors, add the object to the pass
            if (!err.HasErrors)
            {
                texImages.Add(new ResTexImg(values));
            }
        }
Exemple #2
0
 /// <summary>
 /// Link image or buffer object to the texture.
 /// </summary>
 /// <param name="file"></param>
 /// <param name="line"></param>
 /// <param name="err"></param>
 private void Link(string file, int line, CompileException err)
 {
     // IN CASE THIS IS A TEXTURE OBJECT
     if (glImg != null)
     {
         glname = glImg.glname;
         // get internal format
         GL.GetTextureLevelParameter(glname, 0, GetTextureParameter.TextureInternalFormat, out int f);
         Format = (GpuFormat)f;
     }
     // IN CASE THIS IS A BUFFER OBJECT
     else if (glBuff != null)
     {
         if (Format == 0)
         {
             throw err.Add($"No texture buffer format defined for " +
                           "buffer '{buff}' (e.g. format RGBA8).", file, line);
         }
         // CREATE OPENGL OBJECT
         glname = GL.GenTexture();
         GL.BindTexture(TextureTarget.TextureBuffer, glname);
         GL.TexBuffer(TextureBufferTarget.TextureBuffer, (SizedInternalFormat)Format, glBuff.glname);
         GL.BindTexture(TextureTarget.TextureBuffer, 0);
     }
 }
Exemple #3
0
        /// <summary>
        /// Create OpenGL object. Standard object constructor for ProtoFX.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="debugging"></param>
        public GLSampler(Compiler.Block block, Dict scene, bool debugging)
            : base(block.Name, block.Anno)
        {
            var err = new CompileException($"sampler '{Name}'");

            // PARSE ARGUMENTS
            Cmds2Fields(block, err);

            // CREATE OPENGL OBJECT
            glname = GL.GenSampler();
            int mini  = (int)Minfilter;
            int magi  = (int)Magfilter;
            int wrapi = (int)Wrap;

            GL.SamplerParameterI(glname, SamplerParameterName.TextureMinFilter, ref mini);
            GL.SamplerParameterI(glname, SamplerParameterName.TextureMagFilter, ref magi);
            GL.SamplerParameterI(glname, SamplerParameterName.TextureWrapR, ref wrapi);
            GL.SamplerParameterI(glname, SamplerParameterName.TextureWrapS, ref wrapi);
            GL.SamplerParameterI(glname, SamplerParameterName.TextureWrapT, ref wrapi);

            HasErrorOrGlError(err, block);
            if (err.HasErrors)
            {
                throw err;
            }
        }
Exemple #4
0
        /// <summary>
        /// Create a new external class instance by processing the specified compiler block.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="err"></param>
        /// <returns></returns>
        internal static object CreateInstance(Compiler.Block block, Dict scene, CompileException err)
        {
            // GET CLASS COMMAND
            var cmds = block["class"].ToList();

            if (cmds.Count == 0)
            {
                err.Add("Instance must specify a 'class' command " +
                        "(e.g., class csharp_name class_name).", block);
                return(null);
            }
            var cmd = cmds.First();

            // check command
            if (cmd.ArgCount < 1)
            {
                err.Add("'class' command must specify a csharp object name.", cmd);
                return(null);
            }

            // FIND CSHARP CLASS DEFINITION
            var csharp = scene.GetValueOrDefault <GLCsharp>(cmd[0].Text);

            if (csharp == null)
            {
                err.Add($"Could not find csharp code '{cmd[0].Text}' of command '{cmd.Text}' ", cmd);
                return(null);
            }

            // INSTANTIATE CSHARP CLASS
            return(csharp.CreateInstance(block, cmd, scene, err));
        }
Exemple #5
0
        /// <summary>
        /// Create OpenGL object. Standard object constructor for ProtoFX.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="debugging"></param>
        public GLVertinput(Compiler.Block block, Dict scene, bool debugging)
            : base(block.Name, block.Anno)
        {
            var err = new CompileException($"vertinput '{Name}'");

            // CREATE OPENGL OBJECT
            glname = GL.GenVertexArray();
            GL.BindVertexArray(glname);

            int numAttr = 0;

            foreach (var cmd in block["attr"])
            {
                Attach(numAttr++, cmd, scene, err | $"command '{cmd.Text}'");
            }

            // if errors occurred throw exception
            if (err.HasErrors)
            {
                throw err;
            }

            // unbind object and check for errors
            GL.BindVertexArray(0);
            if (HasErrorOrGlError(err, block))
            {
                throw err;
            }
        }
Exemple #6
0
        /// <summary>
        /// Create OpenGL object. Standard object constructor for ProtoFX.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="debugging"></param>
        public GLVertoutput(Compiler.Block block, Dict scene, bool debugging)
            : base(block.Name, block.Anno)
        {
            var err = new CompileException($"vertoutput '{Name}'");

            // PARSE ARGUMENTS
            Cmds2Fields(block, err);

            // CREATE OPENGL OBJECT
            glname = GL.GenTransformFeedback();
            GL.BindTransformFeedback(TransformFeedbackTarget.TransformFeedback, glname);

            // parse commands
            int numbindings = 0;

            foreach (var cmd in block["buff"])
            {
                Attach(numbindings++, cmd, scene, err | $"command '{cmd.Text}'");
            }

            // if errors occurred throw exception
            if (err.HasErrors)
            {
                throw err;
            }

            // unbind object and check for errors
            GL.BindTransformFeedback(TransformFeedbackTarget.TransformFeedback, 0);
            if (HasErrorOrGlError(err, block))
            {
                throw err;
            }
        }
Exemple #7
0
        /// <summary>
        /// Check for compiler and OpenGL errors.
        /// </summary>
        /// <param name="err"></param>
        /// <param name="file"></param>
        /// <param name="line"></param>
        /// <returns></returns>
        static protected bool HasErrorOrGlError(CompileException err, string file, int line)
        {
            var errcode = GL.GetError();

            if (errcode != ErrorCode.NoError)
            {
                err.Add($"OpenGL error '{errcode}' occurred.", file, line);
                return(true);
            }
            return(err.HasErrors);
        }
Exemple #8
0
        /// <summary>
        /// Check for compiler and OpenGL errors.
        /// </summary>
        /// <param name="err"></param>
        /// <param name="block"></param>
        /// <returns></returns>
        static protected bool HasErrorOrGlError(CompileException err, Compiler.Block block)
        {
            var errcode = GL.GetError();

            if (errcode != ErrorCode.NoError)
            {
                err.Add($"OpenGL error '{errcode}' occurred.", block);
                return(true);
            }
            return(err.HasErrors);
        }
Exemple #9
0
        private GLShader Attach(Compiler.Block block, string shadername, Dict classes,
                                CompileException err)
        {
            GLShader obj = null;

            // get shader from class list
            if (shadername != null && classes.TryGetValue(shadername, out obj, block, err))
            {
                GL.UseProgramStages(glname, ShaderType2ShaderBit(obj.ShaderType), obj.glname);
            }

            return(obj);
        }
Exemple #10
0
            /// <summary>
            /// Parse the command and extract arguments as values.
            /// </summary>
            /// <param name="types">List of argument types.</param>
            /// <param name="mandatory">Specifies which of this arguments are mandatory.</param>
            /// <param name="unusedArgs">List of arguments the where not parsed.</param>
            /// <param name="scene">Dictionary of scene objects.</param>
            /// <param name="err"></param>
            /// <returns>List of objects values. If a value could not be
            /// parsed, the returned value will be null.</returns>
            public (object[], string[]) Parse(Type[] types, bool[][] mandatory, Dict scene,
                                              CompileException err = null)
            {
                var values = new object[types.Length];

                // parse command arguments
                var lastArgUsed = 0;

                for (var a = 0; a < Length; a++)
                {
                    var arg = this[a];
                    var I   = values
                              .Zip(Enumerable.Range(0, types.Length), (x, i) => x == null ? i : -1)
                              .Where(x => x >= 0);
                    foreach (var i in I)
                    {
                        try
                        {
                            values[i] = types[i].IsSubclassOf(typeof(GLObject))
                                ? scene.GetValueOrDefault <GLObject>(arg.Text)
                                : types[i].IsEnum
                                    ? Enum.Parse(types[i], arg.Text, true)
                                    : Convert.ChangeType(arg.Text, types[i],
                                                         CultureInfo.CurrentCulture);
                            if (values[i] != null)
                            {
                                lastArgUsed = a;
                                break;
                            }
                        }
                        catch { }
                    }
                }

                // return list of unused arguments
                var unusedArgs = this.Skip(lastArgUsed + 1).Select(x => x.Text).ToArray();

                // check for errors
                var valid = values.Select(x => x != null);

                for (int i = 0; i < mandatory.Length; i++)
                {
                    if (mandatory[i].Zip(valid, (m, v) => !m | v).All(x => x))
                    {
                        return(values, unusedArgs);
                    }
                }

                err?.Add("Command has one or more invalid arguments.", this);
                return(values, unusedArgs);
            }
Exemple #11
0
        /// <summary>
        /// Get text from scene structure by processing the specified command.
        /// </summary>
        /// <param name="cmd"></param>
        /// <param name="scene"></param>
        /// <param name="err"></param>
        /// <returns></returns>
        private static byte[] LoadText(Compiler.Command cmd, Dict scene, CompileException err)
        {
            // Get text from file or text object
            var str = GetText(scene, cmd);

            if (str == null)
            {
                err.Add("Could not process command. Second argument must "
                        + "be a name to a text object or a filename.", cmd);
                return(null);
            }

            // Convert text to byte array
            return(str.ToCharArray().ToBytes());
        }
Exemple #12
0
        /// <summary>
        /// Construct GLBuffer object.
        /// </summary>
        /// <param name="name">Name of the object.</param>
        /// <param name="anno">Annotation of the object.</param>
        /// <param name="usage">How the buffer should be used by the program.</param>
        /// <param name="size">The memory size to be allocated in bytes.</param>
        /// <param name="data">Optionally initialize the buffer object with the specified data.</param>
        public GLBuffer(string name, string anno, UsageHint usage, int size, byte[] data = null)
            : base(name, anno)
        {
            var err = new CompileException($"buffer '{name}'");

            Size  = size;
            Usage = usage;

            // CREATE OPENGL OBJECT
            CreateBuffer(data);
            if (HasErrorOrGlError(err, "", -1))
            {
                throw err;
            }
        }
Exemple #13
0
        /// <summary>
        /// Create OpenGL object. Standard object constructor for ProtoFX.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="debugging"></param>
        public GLCsharp(Compiler.Block block, Dict scene, bool debugging)
            : base(block.Name, block.Anno)
        {
            var err = new CompileException($"csharp '{Name}'");

            // PARSE ARGUMENTS
            Cmds2Fields(block, err);

            // check for errors
            if (err.HasErrors)
            {
                throw err;
            }
            if (File == null || File.Length == 0)
            {
                return;
            }

            // LOAD ADDITIONAL ASSEMBLIES
            if (Assembly != null)
            {
                foreach (var assemblypath in Assembly)
                {
                    try {
                        System.Reflection.Assembly.LoadFrom(assemblypath);
                    } catch (FileNotFoundException) {
                        err.Add($"Assembly file '{assemblypath}' cound not be found.", block);
                    } catch (FileLoadException) {
                        err.Add($"Assembly '{assemblypath}' cound not be loaded.", block);
                    } catch {
                        err.Add($"Unknown exception when loading assembly '{assemblypath}'.", block);
                    }
                }
            }

            // replace placeholders with actual path
            var dir      = Path.GetDirectoryName(block.Filename) + Path.DirectorySeparatorChar;
            var filepath = ProcessPaths(dir, File);

            // COMPILE FILES
            CompilerResults = CompileFilesOrSource(filepath.ToArray(), Version, block, err);

            // check for errors
            if (err.HasErrors)
            {
                throw err;
            }
        }
Exemple #14
0
        /// <summary>
        /// Create OpenGL object. Standard object constructor for ProtoFX.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="debugging"></param>
        public GLTech(Compiler.Block block, Dict scene, bool debugging)
            : base(block.Name, block.Anno, 309, debugging)
        {
            var err = new CompileException($"tech '{Name}'");

            // PARSE COMMANDS
            ParsePasses(ref init, block, scene, err);
            ParsePasses(ref passes, block, scene, err);
            ParsePasses(ref uninit, block, scene, err);

            // IF THERE ARE ERRORS THROW AND EXCEPTION
            if (err.HasErrors)
            {
                throw err;
            }
        }
Exemple #15
0
        /// <summary>
        /// Parse commands in block.
        /// </summary>
        /// <param name="list"></param>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="err"></param>
        private void ParsePasses(ref List <GLPass> list, Compiler.Block block, Dict scene,
                                 CompileException err)
        {
            var cmdName = ReferenceEquals(list, init)
                ? "init"
                : ReferenceEquals(list, passes) ? "pass" : "uninit";

            foreach (var cmd in block[cmdName])
            {
                if (scene.TryGetValue(cmd[0].Text, out GLPass pass, block,
                                      err | $"command '{cmd.Text}'"))
                {
                    list.Add(pass);
                }
            }
        }
Exemple #16
0
        /// <summary>
        /// Create OpenGL object specifying the texture
        /// format and referenced scene objects directly.
        /// </summary>
        /// <param name="name"></param>
        /// <param name="anno"></param>
        /// <param name="format"></param>
        /// <param name="glbuff"></param>
        /// <param name="glimg"></param>
        public GLTexture(string name, string anno, GpuFormat format, GLBuffer glbuff, GLImage glimg)
            : base(name, anno)
        {
            var err = new CompileException($"texture '{name}'");

            // set name
            Format = format;
            glBuff = glbuff;
            glImg  = glimg;

            // INCASE THIS IS A TEXTURE OBJECT
            Link("", -1, err);
            if (HasErrorOrGlError(err, "", -1))
            {
                throw err;
            }
        }
Exemple #17
0
        /// <summary>
        /// Try to find the value to a key. If the key could not be found add an exception message.
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="key">Key to search for.</param>
        /// <param name="obj">Output object reference.</param>
        /// <param name="file">Specify the file identifying an exception if it occurs.</param>
        /// <param name="line">Specify the file line identifying an exception if it occurs.</param>
        /// <param name="err">Add new exceptions to this existing one.</param>
        /// <returns></returns>
        public bool TryGetValue <T>(string key, out T obj, int line, string file,
                                    CompileException err)
            where T : GLObject
        {
            // try to find the object instance
            if ((obj = GetValueOrDefault <T>(key)) != default(T))
            {
                return(true);
            }

            // get class name of object type
            var classname = typeof(T).Name.Substring(2).ToLower();

            err.Add($"The name '{key}' could not be found or does not "
                    + $"reference an object of type '{classname}'.", file, line);
            return(false);
        }
Exemple #18
0
        /// <summary>
        /// Create OpenGL object. Standard object constructor for ProtoFX.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="debugging"></param>
        public GLBuffer(Compiler.Block block, Dict scene, bool debugging)
            : base(block.Name, block.Anno)
        {
            var err = new CompileException($"buffer '{block.Name}'");

            // PARSE COMMANDS AND CONVERT THEM TO CLASS FIELDS
            Cmds2Fields(block, err);

            // PARSE COMMANDS
            var datalist = new List <byte[]>();

            foreach (var cmd in block["txt"])
            {
                datalist.Add(LoadText(cmd, scene, err | $"command {cmd.Name} 'txt'"));
            }

            foreach (var cmd in block["xml"])
            {
                datalist.Add(LoadXml(cmd, scene, err | $"command {cmd.Name} 'xml'"));
            }

            // merge data into a single array
            var iter = datalist.Cat();
            var data = iter.Take(Size == 0 ? iter.Count() : Size).ToArray();

            if (Size == 0)
            {
                Size = data.Length;
            }

            // CONVERT DATA
            var clazz = block["class"].FirstOrDefault();

            if (clazz != null && Size > 0)
            {
                var converter = GLCsharp.GetMethod(clazz, scene, err);
                data = (byte[])converter?.Invoke(null, new[] { data });
            }

            // CREATE OPENGL OBJECT
            CreateBuffer(data);
            if (HasErrorOrGlError(err, block))
            {
                throw err;
            }
        }
Exemple #19
0
        private void ParseCsharpExec(Compiler.Command cmd, Dict classes, CompileException err)
        {
            // check if command provides the correct amount of parameters
            if (cmd.ArgCount == 0)
            {
                err.Add("Not enough arguments for exec command.", cmd);
                return;
            }

            // get instance
            if (!classes.TryGetValue(cmd[0].Text, out GLInstance instance, cmd, err))
            {
                return;
            }

            csexec.Add(instance);
        }
Exemple #20
0
        /// <summary>
        /// Get xml text from scene structure by processing the specified command.
        /// </summary>
        /// <param name="cmd"></param>
        /// <param name="scene"></param>
        /// <param name="err"></param>
        /// <returns></returns>
        private static byte[] LoadXml(Compiler.Command cmd, Dict scene, CompileException err)
        {
            // Get text from file or text object
            string str = GetText(scene, cmd);

            if (str == null)
            {
                err.Add("Could not process command. Second argument must "
                        + "be a name to a text object or a filename.", cmd);
                return(null);
            }

            try
            {
                // Parse XML string
                var document = new XmlDocument();
                document.LoadXml(str);

                // Load data from XML
                var filedata = new byte[cmd.ArgCount - 1][];
                for (int i = 1; i < cmd.ArgCount; i++)
                {
                    try
                    {
                        filedata[i - 1] = DataXml.Load(document, cmd[i].Text);
                    }
                    catch (XmlException ex)
                    {
                        err.Add(ex.Message, cmd);
                    }
                }

                // Merge data
                if (!err.HasErrors)
                {
                    return(filedata.Cat().ToArray());
                }
            }
            catch (Exception ex)
            {
                err.Add(ex.GetBaseException().Message, cmd);
            }

            return(null);
        }
Exemple #21
0
        private void ParseComputeCall(Compiler.Command cmd, Dict classes, CompileException err)
        {
            // check for errors
            if (cmd.ArgCount < 2 || cmd.ArgCount > 3)
            {
                err.Add("Compute command does not provide enough arguments "
                        + "(e.g., 'compute num_groups_X num_groups_y num_groups_z' or "
                        + "'compute buffer_name indirect_pointer').", cmd);
                return;
            }

            try
            {
                var call = new CompCall();

                // this is an indirect compute call
                if (cmd.ArgCount == 2)
                {
                    // indirect compute call buffer
                    call.numGroupsX = (uint)classes.GetValue <GLBuffer>(cmd[0].Text,
                                                                        "First argument of compute command must be a buffer name").glname;
                    // indirect compute call buffer pointer
                    call.numGroupsY = cmd[1].Text.To <uint>("Argument must be an unsigned integer, "
                                                            + "specifying a pointer into the indirect compute call buffer.");
                }
                // this is a normal compute call
                else
                {
                    // number of compute groups
                    call.numGroupsX = cmd[0].Text.To <uint>("Argument must be an unsigned integer, "
                                                            + "specifying the number of compute groups in X.");
                    call.numGroupsY = cmd[1].Text.To <uint>("Argument must be an unsigned integer, "
                                                            + "specifying the number of compute groups in Y.");
                    call.numGroupsZ = cmd[2].Text.To <uint>("Argument must be an unsigned integer, "
                                                            + "specifying the number of compute groups in Z.");
                }

                compcalls.Add(call);
            }
            catch (CompileException ex)
            {
                err.Add(ex.Message, cmd);
            }
        }
Exemple #22
0
        /// <summary>
        /// Create OpenGL object specifying the referenced scene objects directly.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="scene"></param>
        /// <param name="glbuff"></param>
        /// <param name="glimg"></param>
        public GLTexture(Compiler.Block block, Dict scene, GLBuffer glbuff, GLImage glimg)
            : base(block.Name, block.Anno)
        {
            var err = new CompileException($"texture '{Name}'");

            // PARSE ARGUMENTS
            Cmds2Fields(block, err);

            // set name
            glBuff = glbuff;
            glImg  = glimg;

            // GET REFERENCES
            if (Buff != null)
            {
                scene.TryGetValue(Buff, out glBuff, block, err);
            }
            if (Img != null)
            {
                scene.TryGetValue(Img, out glImg, block, err);
            }
            if (glBuff != null && glImg != null)
            {
                err.Add("Only an image or a buffer can be bound to a texture object.", block);
            }
            if (glBuff == null && glImg == null)
            {
                err.Add("Ether an image or a buffer has to be bound to a texture object.", block);
            }

            // IF THERE ARE ERRORS THROW AND EXCEPTION
            if (err.HasErrors)
            {
                throw err;
            }

            // INCASE THIS IS A TEXTURE OBJECT
            Link(block.Filename, block.LineInFile, err);
            if (HasErrorOrGlError(err, block))
            {
                throw err;
            }
        }
Exemple #23
0
        /// <summary>
        /// Set a field of the specified class to the specified value.
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="clazz"></param>
        /// <param name="field"></param>
        /// <param name="fieldType"></param>
        /// <param name="cmd"></param>
        /// <param name="err"></param>
        static private void SetValue <T>(T clazz, object field, Type fieldType,
                                         Compiler.Command cmd, CompileException err = null)
        {
            // check for errors
            if (cmd.ArgCount == 0)
            {
                err?.Add($"Command '{cmd.Text}' has no arguments (must have at least one).", cmd);
            }
            if (!fieldType.IsArray && cmd.ArgCount > 1)
            {
                err?.Add($"Command '{cmd.Text}' has too many arguments (more than one).", cmd);
            }
            if (err != null && err.HasErrors)
            {
                return;
            }

            object val = null;

            if (fieldType.IsArray)
            {
                var elType = fieldType.GetElementType();
                var array  = Array.CreateInstance(elType, cmd.Length);
                for (int i = 0; i < cmd.Length; i++)
                {
                    array.SetValue(Convert.ChangeType(cmd[i].Text, elType, CultureInfo.CurrentCulture), i);
                }
                val = array;
            }
            else
            {
                val = fieldType.IsEnum
                      // if this is an enum, convert the string to an enum value
                    ? Convert.ChangeType(Enum.Parse(fieldType, cmd[0].Text, true), fieldType)
                      // else try to convert it to the field type
                    : Convert.ChangeType(cmd[0].Text, fieldType, CultureInfo.CurrentCulture);
            }

            // set value of the field
            field.GetType()
            .GetMethod("SetValue", new[] { typeof(object), typeof(object) })
            .Invoke(field, new object[] { clazz, val });
        }
Exemple #24
0
        /// <summary>
        /// Create a new external method-call by processing the specified compiler command.
        /// </summary>
        /// <param name="cmd"></param>
        /// <param name="err"></param>
        /// <returns></returns>
        private MethodInfo GetMethod(Compiler.Command cmd, CompileException err)
        {
            // check if the command is valid
            if (cmd.ArgCount < 2)
            {
                err.Add("'class' command must specify a class name.", cmd);
                return(null);
            }
            if (cmd.ArgCount < 3)
            {
                err.Add("'class' command must specify a method name.", cmd);
                return(null);
            }

            var classname  = cmd[1].Text;
            var methodname = cmd[2].Text;
            var type       = CompilerResults.CompiledAssembly.GetType(classname);

            return(type?.GetMethod(methodname, BindingFlags.Public | BindingFlags.Static));
        }
Exemple #25
0
        private void ParseSampCmd(Compiler.Command cmd, Dict classes, CompileException err)
        {
            if (cmd.ArgCount != 1 && cmd.ArgCount != 2)
            {
                err.Add("Arguments of the 'samp' command are invalid.", cmd);
                return;
            }
            // specify argument types
            var types = new[] { typeof(GLSampler), typeof(int), typeof(string) };
            // specify mandatory arguments
            var mandatory = new[] { new[] { true, true, false }, new[] { false, true, false } };

            // parse command arguments
            (var values, var unused) = cmd.Parse(types, mandatory, classes, err);
            // if there are no errors, add the object to the pass
            if (!err.HasErrors)
            {
                sampler.Add(new Res <GLSampler>(values));
            }
        }
Exemple #26
0
        /// <summary>
        /// Create a new external method-call by processing the specified compiler command.
        /// </summary>
        /// <param name="cmd"></param>
        /// <param name="err"></param>
        /// <returns></returns>
        internal static MethodInfo GetMethod(Compiler.Command cmd, Dict scene, CompileException err)
        {
            // check command
            if (cmd.ArgCount < 1)
            {
                err.Add("'class' command must specify a csharp object name.", cmd);
                return(null);
            }

            // FIND CSHARP CLASS DEFINITION
            var csharp = scene.GetValueOrDefault <GLCsharp>(cmd[0].Text);

            if (csharp == null)
            {
                err.Add($"Could not find csharp code '{cmd[0].Text}' of command '{cmd.Text}' ", cmd);
                return(null);
            }

            // INSTANTIATE CSHARP CLASS
            return(csharp.GetMethod(cmd, err));
        }
Exemple #27
0
        /// <summary>
        /// Create class instance of a C# class compiled through GLCSharp.
        /// </summary>
        /// <param name="params">Input parameters for GLObject creation.</param>
        public GLInstance(Compiler.Block block, Dict scene, bool debugging)
            : base(block.Name, block.Anno)
        {
            var err = new CompileException($"instance '{Name}'");

            // INSTANTIATE CSHARP CLASS FROM CODE BLOCK
            Instance = GLCsharp.CreateInstance(block, scene, err);
            if (err.HasErrors)
            {
                throw err;
            }

            // get Bind method from main class instance
            update = Instance.GetType().GetMethod("Update", new[] {
                typeof(int), typeof(int), typeof(int), typeof(int), typeof(int)
            });

            // get Unbind method from main class instance
            endpass = Instance.GetType().GetMethod("EndPass", new[] { typeof(int) });

            // get Delete method from main class instance
            delete = Instance.GetType().GetMethod("Delete");

            // get all public methods and check whether
            // they can be used as event handlers for glControl
            var reference = scene.GetValueOrDefault <GLReference>(GraphicControl.nullname);
            var glControl = (GraphicControl)reference.Reference;
            var methods   = Instance.GetType().GetMethods(BindingFlags.Public | BindingFlags.Instance);

            foreach (var method in methods)
            {
                var info = glControl.GetType().GetEvent(method.Name);
                if (info != null)
                {
                    var csmethod = Delegate.CreateDelegate(info.EventHandlerType, Instance, method.Name);
                    info.AddEventHandler(glControl, csmethod);
                }
            }
        }
Exemple #28
0
        /// <summary>
        /// Process object block and try to convert commands to class internal fields.
        /// </summary>
        /// <param name="block"></param>
        /// <param name="err"></param>
        protected void Cmds2Fields(Compiler.Block block, CompileException err = null)
        {
            foreach (var cmd in block)
            {
                // check if the name is too short for a field
                if (cmd.Name.Length < 2)
                {
                    continue;
                }

                // get field member info
                var member = GetFxField(cmd.Name);

                if (member != null)
                {
                    // set value of field
                    SetValue(this, member, member is FieldInfo
                        ? (member as FieldInfo).FieldType
                        : (member as PropertyInfo).PropertyType, cmd, err);
                }
            }
        }
Exemple #29
0
        /// <summary>
        /// Parse command line and attach the buffer object
        /// to the specified unit (output stream).
        /// </summary>
        /// <param name="unit">Vertex output stream unit.</param>
        /// <param name="cmd">Command line to process.</param>
        /// <param name="scene">Dictionary of scene objects.</param>
        /// <param name="err">Compiler exception collector.</param>
        private void Attach(int unit, Compiler.Command cmd, Dict scene, CompileException err)
        {
            if (cmd.ArgCount == 0)
            {
                err.Add("Command buff needs at least one attribute (e.g. 'buff buff_name')", cmd);
                return;
            }

            // get buffer
            var buf = scene.GetValueOrDefault <GLBuffer>(cmd[0].Text);

            if (buf == null)
            {
                err.Add($"The name '{cmd[0]}' does not reference an object of type 'buffer'.", cmd);
                return;
            }

            // parse offset
            int offset = 0;

            if (cmd.ArgCount > 1 && int.TryParse(cmd[1].Text, out offset) == false)
            {
                err.Add($"The second parameter (offset) of buff {unit} is invalid.", cmd);
                return;
            }

            // parse size
            int size = buf.Size;

            if (cmd.ArgCount > 2 && int.TryParse(cmd[2].Text, out size) == false)
            {
                err.Add($"The third parameter (size) of buff {unit} is invalid.", cmd);
                return;
            }

            // bind buffer to transform feedback
            GL.BindBufferRange(BufferRangeTarget.TransformFeedbackBuffer,
                               unit, buf.glname, (IntPtr)offset, (IntPtr)size);
        }
Exemple #30
0
        private void ParseOpenGLCall(Compiler.Command cmd, CompileException err)
        {
            // find OpenGL method
            var mname = cmd.Name.StartsWith("gl") ? cmd.Name.Substring(2) : cmd.Name;
            var mtype = FindMethod(mname, cmd.ArgCount);

            if (mtype == null)
            {
                if (GetFxField(mname) == null)
                {
                    err.Add("Unknown command '" + cmd.Text + "'", cmd);
                }
                return;
            }

            // get method parameter types
            var param = mtype.GetParameters();
            var inval = new object[param.Length];

            // convert strings to parameter types
            for (int i = 0; i < param.Length; i++)
            {
                if (param[i].ParameterType.IsEnum)
                {
                    inval[i] = Convert.ChangeType(
                        Enum.Parse(param[i].ParameterType, cmd[i].Text, true),
                        param[i].ParameterType);
                }
                else
                {
                    inval[i] = Convert.ChangeType(cmd[i].Text, param[i].ParameterType, CultureInfo.CurrentCulture);
                }
            }

            glfunc.Add(new GLMethod(mtype, inval));
        }