Ejemplo n.º 1
0
        private ParametrizedCode FormatJavascript(JsExpression node, bool allowObservableResult = true)
        {
            var expr = new JsParenthesizedExpression(node.Clone());

            expr.AcceptVisitor(new KnockoutObservableHandlingVisitor(allowObservableResult));
            JavascriptNullCheckAdder.AddNullChecks(expr);
            expr = new JsParenthesizedExpression((JsExpression)JsTemporaryVariableResolver.ResolveVariables(expr.Expression.Detach()));
            return((StartsWithStatementLikeExpression(expr.Expression) ? expr : expr.Expression).FormatParametrizedScript(niceMode: configuration.Debug));
        }
Ejemplo n.º 2
0
 public string CompileBinding(Func<Dictionary<string, Expression>, Expression> expr, Type[] contexts)
 {
     var context = DataContextStack.Create(contexts.FirstOrDefault() ?? typeof(object), extensionParameters: new BindingExtensionParameter[]{
         new BindingPageInfoExtensionParameter()
         });
     for (int i = 1; i < contexts.Length; i++)
     {
         context = DataContextStack.Create(contexts[i], context);
     }
     var expressionTree = expr(BindingExpressionBuilder.GetParameters(context).ToDictionary(e => e.Name, e => (Expression)e));
     var configuration = DotvvmTestHelper.CreateConfiguration();
     var jsExpression = new JsParenthesizedExpression(configuration.ServiceProvider.GetRequiredService<JavascriptTranslator>().CompileToJavascript(expressionTree, context));
     jsExpression.AcceptVisitor(new KnockoutObservableHandlingVisitor(true));
     JsTemporaryVariableResolver.ResolveVariables(jsExpression);
     return JavascriptTranslator.FormatKnockoutScript(jsExpression.Expression);
 }
Ejemplo n.º 3
0
        public string CompileBinding(string expression, Type[] contexts, Type expectedType)
        {
            var context = DataContextStack.Create(contexts.FirstOrDefault() ?? typeof(object), extensionParameters: new BindingExtensionParameter[] {
                new BindingPageInfoExtensionParameter(),
            }.Concat(configuration.Markup.DefaultExtensionParameters).ToArray());

            for (int i = 1; i < contexts.Length; i++)
            {
                context = DataContextStack.Create(contexts[i], context);
            }
            var parser         = new BindingExpressionBuilder();
            var expressionTree = TypeConversion.ImplicitConversion(parser.Parse(expression, context, BindingParserOptions.Create <ValueBindingExpression>()), expectedType, true, true);
            var jsExpression   = new JsParenthesizedExpression(configuration.ServiceProvider.GetRequiredService <JavascriptTranslator>().CompileToJavascript(expressionTree, context));

            jsExpression.AcceptVisitor(new KnockoutObservableHandlingVisitor(true));
            JsTemporaryVariableResolver.ResolveVariables(jsExpression);
            return(JavascriptTranslator.FormatKnockoutScript(jsExpression.Expression));
        }
        private JsNode Binary(OperatorResolveResult res)
        {
            if (res.UserDefinedOperatorMethod != null && !Sk.UseNativeOperatorOverloads(res.UserDefinedOperatorMethod.DeclaringTypeDefinition))
            {
                var op2 = res.OperatorType.ExtractCompoundAssignment();
                if (op2 != null)
                {
                    var fakeRight  = new OperatorResolveResult(res.Type, op2.Value, res.UserDefinedOperatorMethod, res.IsLiftedOperator, res.Operands);
                    var fakeAssign = Cs.Assign(res.Operands[0], fakeRight);
                    return(Visit(fakeAssign));
                }

                var fake = Cs.InvokeMethod(res.UserDefinedOperatorMethod, null, res.Operands[0], res.Operands[1]);
                return(Visit(fake));
            }

            if (res.OperatorType == ExpressionType.Coalesce)
            {
                var fake  = Cs.Conditional(res.Operands[0].NotEqual(Cs.Null(), Project), res.Operands[0], res.Operands[1], res.Type);
                var fake2 = Visit(fake);
                fake2 = new JsParenthesizedExpression {
                    Expression = (JsExpression)fake2
                };
                return(fake2);
            }
            var mrr = res.Operands[0] as MemberResolveResult;

            if (mrr != null && mrr.Member.SymbolKind == SymbolKind.Event)
            {
                var pe = (IEvent)mrr.Member;
                if (res.OperatorType.IsAny(ExpressionType.AddAssign, ExpressionType.SubtractAssign))
                {
                    var accessor = res.OperatorType == ExpressionType.AddAssign ? pe.AddAccessor : pe.RemoveAccessor;
                    var fake     = new CSharpInvocationResolveResult(mrr.TargetResult, accessor, new List <ResolveResult>
                    {
                        res.Operands[1]
                    });
                    var node6 = Visit(fake);
                    return(node6);
                }
            }
            if (mrr != null && IsEntityFunctionProperty(mrr.Member, res))
            {
                var simpleOp = res.OperatorType.ExtractCompoundAssignment();

                var pe = (IProperty)mrr.Member;
                if (simpleOp != null)
                {
                    // x.Name += "Hello"    ->  x.Name = x.Name + "Hello"
                    // x.Dic["Hello"] += 7  ->  x.Dic["Hello"] = x.Dic["Hello"] + 7;
                    var fake  = res.Operands[0].Assign(res.Operands[0].Binary(simpleOp.Value, res.Operands[1], res.Type));
                    var node6 = Visit(fake);
                    return(node6);
                }
                else if (res.OperatorType == ExpressionType.Assign)
                {
                    var args = new List <ResolveResult>();
                    if (pe.IsIndexer)
                    {
                        var irrOp0 = (CSharpInvocationResolveResult)res.Operands[0];
                        args.AddRange(irrOp0.Arguments);
                    }
                    args.Add(res.Operands[1]);
                    var fake  = new CSharpInvocationResolveResult(mrr.TargetResult, pe.Setter, args).AssociateWithOriginal(res);
                    var node6 = Visit(fake);
                    node6 = WrapSetterToReturnValueIfNeeded(res, node6);
                    return(node6);
                }
            }
            if (res.Operands[0] is ConversionResolveResult && res.Operands[1] is ConstantResolveResult)
            {
                var leftConv   = (ConversionResolveResult)res.Operands[0];
                var rightConst = (ConstantResolveResult)res.Operands[1];
                if (leftConv.Conversion.IsNumericConversion && leftConv.Input.Type == Cs.CharType(Project))
                {
                    var value = ((char)(int)rightConst.ConstantValue).ToString();
                    var fake  = Cs.Binary(leftConv.Input, res.OperatorType, Cs.Value(value, Project), leftConv.Input.Type);
                    return(Visit(fake));
                }
            }
            if (res.Operands[0].Type.Kind == TypeKind.Delegate && res.Operands[1].Type.Kind == TypeKind.Delegate)
            {
                if (res.OperatorType.IsAny(ExpressionType.AddAssign, ExpressionType.SubtractAssign))
                {
                    var op    = res.OperatorType == ExpressionType.AddAssign ? ExpressionType.Add : ExpressionType.Subtract;
                    var fake  = Cs.Assign(res.Operands[0], Cs.Binary(res.Operands[0], op, res.Operands[1], res.Type));
                    var node6 = Visit(fake);
                    return(node6);
                }
                else if (res.OperatorType.IsAny(ExpressionType.Add, ExpressionType.Subtract))
                {
                    var combineMethod = Project.Compilation.FindType(KnownTypeCode.Delegate).GetMethods(t => t.Name == "Combine").FirstOrDefault();
                    var removeMethod  = Project.Compilation.FindType(KnownTypeCode.Delegate).GetMethods(t => t.Name == "Remove").FirstOrDefault();

                    var meOp = res.OperatorType == ExpressionType.Add ? combineMethod : removeMethod;

                    var fake  = Cs.Member(null, meOp).Invoke(res.Operands[0], res.Operands[1]);
                    var node6 = Visit(fake);
                    return(node6);
                }
            }

            var node5 = new JsBinaryExpression {
                Operator = Visit(res.OperatorType), Left = VisitExpression(res.Operands[0]), Right = VisitExpression(res.Operands[1])
            };

            if (res.OperatorType == ExpressionType.Equal && node5.Operator == "==")
            {
                var att = Compiler.GetJsExportAttribute();
                if (att != null && att.UseExactEquals)
                {
                    node5.Operator = "===";
                }
            }
            if (res.OperatorType == ExpressionType.NotEqual && node5.Operator == "!=")
            {
                var att = Compiler.GetJsExportAttribute();
                if (att != null && att.UseExactEquals)
                {
                    node5.Operator = "!==";
                }
            }

            return(node5);
        }