public string Visit(FunctionCallExpression call)
        {
            var codeWriter = new XzaarCodeWriter();
            var indent     = isInsideExpression ? 0 : currentIndent;
            var instance   = call.GetInstance();

            if (instance != null)
            {
                codeWriter.Write(Visit(instance));
                codeWriter.Write("." + call.MethodName + "(");
            }
            else
            {
                codeWriter.Write(call.MethodName + "(", indent);
            }

            for (int index = 0; index < call.Arguments.Count; index++)
            {
                var arg = call.Arguments[index];
                codeWriter.Write(Visit(arg));
                if (index + 1 < call.ArgumentCount)
                {
                    codeWriter.Write(", ");
                }
            }

            codeWriter.Write(")");
            if (!isInsideExpression)
            {
                codeWriter.NewLine();
            }
            return(codeWriter.ToString());
        }
        public string Visit(MemberExpression access)
        {
            var codeWriter = new XzaarCodeWriter();

            if (access.Member != null)
            {
                codeWriter.Write(access.Member.Name);
                return(null);
            }

            var paramExpr = access.Expression as ParameterExpression;

            if (paramExpr != null)
            {
                codeWriter.Write(paramExpr.Name);
                if (access.ArrayIndex != null)
                {
                    codeWriter.Write("[");
                    codeWriter.Write(Visit(access.ArrayIndex));
                    codeWriter.Write("]");
                }
            }

            return(codeWriter.ToString());
        }
        public string Visit(ForExpression @for)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("for (", currentIndent);
            insideExpressionCount++;
            codeWriter.Write(Visit(@for.Initiator));
            insideExpressionCount--;
            codeWriter.Write("; ");

            insideExpressionCount++;
            codeWriter.Write(Visit(@for.Test));
            insideExpressionCount--;
            codeWriter.Write("; ");
            insideExpressionCount++;
            codeWriter.Write(Visit(@for.Incrementor));
            insideExpressionCount--;
            codeWriter.Write(") {");
            codeWriter.NewLine();

            currentIndent++;
            codeWriter.Write(Visit(@for.Body));
            currentIndent--;

            codeWriter.Write("}", currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(ConstantExpression value)
        {
            var codeWriter = new XzaarCodeWriter();

            if (value.Type.IsArray)
            {
                if (value.Value == null)
                {
                    codeWriter.Write("[]");
                }
                else
                {
                    codeWriter.Write(value.Value);
                }
            }
            else if (value.Type == XzaarBaseTypes.Number || value.Type == XzaarBaseTypes.Boolean)
            {
                codeWriter.Write(value.Value.ToString());
            }
            else
            {
                codeWriter.Write("\"" + value.Value + "\"");
            }
            return(codeWriter.GetSourceCode());
        }
        public string Visit(UnaryExpression unary)
        {
            var codeWriter = new XzaarCodeWriter();
            var indent     = isInsideExpression ? 0 : currentIndent;

            switch (unary.NodeType)
            {
            case XzaarExpressionType.PostIncrementAssign:
                codeWriter.Write("", indent);
                codeWriter.Write(Visit(unary.Item));
                codeWriter.Write("++");
                break;

            case XzaarExpressionType.PostDecrementAssign:
                codeWriter.Write("", indent);
                codeWriter.Write(Visit(unary.Item));
                codeWriter.Write("--");
                break;

            case XzaarExpressionType.Increment:
                codeWriter.Write("++", indent);
                codeWriter.Write(Visit(unary.Item));
                break;

            case XzaarExpressionType.Decrement:
                codeWriter.Write("--", indent);
                codeWriter.Write(Visit(unary.Item));
                break;
            }
            if (!isInsideExpression)
            {
                codeWriter.NewLine();
            }
            return(codeWriter.ToString());
        }
        public string Visit(FunctionExpression function)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("fn " + function.Name + "(", currentIndent);
            codeWriter.Write(string.Join(", ", function.GetParameters().Select(v => v.Type.Name + " " + v.Name).ToArray()));
            codeWriter.Write(") ");
            if (function.ReturnType.Name != "void")
            {
                codeWriter.Write("-> " + function.ReturnType.Name + " ");
            }
            codeWriter.Write("{");
            codeWriter.NewLine();

            var body = function.GetBody();

            if (body != null)
            {
                currentIndent++;
                codeWriter.Write(Visit(body));
                currentIndent--;
            }

            codeWriter.Write("}", currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(ParameterExpression parameter)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write(parameter.Name);
            return(codeWriter.ToString());
        }
        public string Visit(ConditionalExpression conditional)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("if (", currentIndent);
            insideExpressionCount++;
            codeWriter.Write(Visit(conditional.Test));
            insideExpressionCount--;
            codeWriter.Write(") { ");
            codeWriter.NewLine();
            if (conditional.IfTrue != null)
            {
                currentIndent++;
                codeWriter.Write(Visit(conditional.IfTrue));
                currentIndent--;
            }

            codeWriter.Write("}", currentIndent);
            codeWriter.NewLine();

            if (conditional.IfFalse != null && !conditional.IfFalse.IsEmpty())
            {
                codeWriter.Write("else {", currentIndent);
                codeWriter.NewLine();

                currentIndent++;
                codeWriter.Write(Visit(conditional.IfFalse));
                currentIndent--;

                codeWriter.Write("}", currentIndent);
                codeWriter.NewLine();
            }
            return(codeWriter.ToString());
        }
        private string VisitGoto(GotoExpression @goto)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("goto " + @goto.Target?.Name, currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(FieldExpression node)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write(node.FieldType + " " + node.Name, currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(LabelExpression label)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write(@label.Target?.Name + ":", currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        private string VisitBreak(GotoExpression @goto)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("break", currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(CreateStructExpression node)
        {
            var codeWriter = new XzaarCodeWriter();
            var indent     = isInsideExpression ? 0 : currentIndent;

            codeWriter.Write(node.StructName, indent);
            if (!isInsideExpression)
            {
                codeWriter.NewLine();
            }
            return(codeWriter.ToString());
        }
        private string VisitReturn(GotoExpression @goto)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("return", currentIndent);
            if (@goto.Value != null)
            {
                codeWriter.Write(" ");
                insideExpressionCount++;
                codeWriter.Write(Visit(@goto.Value));
                insideExpressionCount--;
            }
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(LoopExpression loop)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("loop {", currentIndent);
            codeWriter.NewLine();
            if (loop.Body != null)
            {
                currentIndent++;
                codeWriter.Write(Visit(loop.Body));
                currentIndent--;
            }
            codeWriter.Write("}", currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(StructExpression node)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("struct " + node.Name + " {", currentIndent);
            codeWriter.NewLine();
            currentIndent++;
            foreach (var field in node.Fields)
            {
                codeWriter.Write(Visit(field));
            }
            currentIndent--;
            codeWriter.Write("}", currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(DoWhileExpression doWhile)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("do {", currentIndent);
            codeWriter.NewLine();
            currentIndent++;
            codeWriter.Write(Visit(doWhile.Body));
            currentIndent--;
            codeWriter.Write("} while(", currentIndent);
            insideExpressionCount++;
            codeWriter.Write(Visit(doWhile.Test));
            insideExpressionCount--;
            codeWriter.Write(")");
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(VariableDefinitionExpression definedVariable)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("var " + definedVariable.Name, isInsideExpression ? 0 : currentIndent);
            if (definedVariable.AssignmentExpression != null)
            {
                codeWriter.Write(" = ");
                insideExpressionCount++;
                codeWriter.Write(Visit(definedVariable.AssignmentExpression));
                insideExpressionCount--;
            }
            if (!isInsideExpression)
            {
                codeWriter.NewLine();
            }
            return(codeWriter.ToString());
        }
        public string Visit(ForEachExpression @foreach)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("foreach (", currentIndent);
            insideExpressionCount++;
            codeWriter.Write(Visit(@foreach.Variable));
            codeWriter.Write(" in ");
            codeWriter.Write(Visit(@foreach.Collection));
            insideExpressionCount--;
            codeWriter.Write(") {");
            codeWriter.NewLine();

            currentIndent++;
            codeWriter.Write(Visit(@foreach.Body));
            currentIndent--;

            codeWriter.Write("}", currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(SwitchExpression match)
        {
            var codeWriter = new XzaarCodeWriter();

            codeWriter.Write("switch (", currentIndent);
            insideExpressionCount++;
            codeWriter.Write(Visit(match.Value));
            insideExpressionCount--;
            codeWriter.Write(") {");
            codeWriter.NewLine();

            currentIndent++;
            foreach (var c in match.Cases)
            {
                codeWriter.Write(Visit(c));
            }
            currentIndent--;

            codeWriter.Write("}", currentIndent);
            codeWriter.NewLine();
            return(codeWriter.ToString());
        }
        public string Visit(SwitchCaseExpression matchCase)
        {
            var codeWriter = new XzaarCodeWriter();

            if (matchCase.IsDefaultCase)
            {
                codeWriter.Write("default:", currentIndent);
            }
            else
            {
                insideExpressionCount++;
                codeWriter.Write("case ", currentIndent);
                codeWriter.Write(Visit(matchCase.Match));
                codeWriter.Write(":");
                insideExpressionCount--;
            }
            codeWriter.NewLine();

            currentIndent++;
            codeWriter.Write(Visit(matchCase.Body));
            currentIndent--;
            return(codeWriter.ToString());
        }
        public string Visit(BinaryExpression binaryOp)
        {
            var    codeWriter = new XzaarCodeWriter();
            string op         = GetBinaryOperator(binaryOp.NodeType);

            if (!isInsideExpression && noIndent == 0)
            {
                codeWriter.Write("", currentIndent);
            }

            noNewLine = true;
            codeWriter.Write(Visit(binaryOp.Left));
            noNewLine = false;

            codeWriter.Write(" " + op + " ");
            noIndent++;
            codeWriter.Write(Visit(binaryOp.Right));
            noIndent--;
            if (!isInsideExpression && noIndent == 0)
            {
                codeWriter.NewLine();
            }
            return(codeWriter.ToString());
        }
Example #23
0
 public XzaarCodeGeneratorVisitor()
 {
     codeWriter = new XzaarCodeWriter();
 }
        public string Visit(MemberAccessChainExpression node)
        {
            var codeWriter = new XzaarCodeWriter();
            var chain      = new List <string>();
            var left       = node.Left;
            var isLeft     = true;

            while (left != null)
            {
                var leftValue = "";
                var wasChain  = false;
                var chainExpr = left as MemberAccessChainExpression;
                if (chainExpr != null)
                {
                    left     = chainExpr.Right;
                    wasChain = true;
                }

                var mb = left as MemberExpression;
                if (mb != null && mb.Expression != null)
                {
                    string arrayIndexer = "";
                    if (mb.ArrayIndex != null)
                    {
                        arrayIndexer = "[" + Visit(mb.ArrayIndex) + "]";
                    }

                    var added = false;
                    var f     = mb.Expression as FieldExpression;
                    var p     = mb.Expression as ParameterExpression;
                    if (p != null)
                    {
                        if (isLeft)
                        {
                            chain.Insert(0, p.Name + arrayIndexer);
                        }
                        else
                        {
                            chain.Add(p.Name + arrayIndexer);
                        }
                        added = true;
                    }
                    if (f != null)
                    {
                        if (isLeft)
                        {
                            chain.Insert(0, f.Name + arrayIndexer);
                        }
                        else
                        {
                            chain.Add(f.Name + arrayIndexer);
                        }
                        added = true;
                    }

                    if (added)
                    {
                        if (wasChain && chainExpr.Left != null)
                        {
                            left = chainExpr.Left;
                        }
                        else
                        {
                            if (!isLeft)
                            {
                                break;
                            }
                            left   = node.Right;
                            isLeft = false;
                        }
                        continue;
                    }
                }

                var fnc = left as FunctionCallExpression;
                if (fnc == null)
                {
                    break;
                }
                var fValue = Visit(fnc);
                if (isLeft)
                {
                    chain.Insert(0, fValue);
                }
                else
                {
                    chain.Add(fValue);
                }

                // fnc.

                // chain.Insert(0, );
            }
            var indent = isInsideExpression ? 0 : currentIndent;

            codeWriter.Write(string.Join(".", chain.ToArray()), indent);
            if (!isInsideExpression && !noNewLine)
            {
                codeWriter.NewLine();
            }
            return(codeWriter.ToString());
        }