Пример #1
0
        private static SyntaxNode Property(SyntaxNode node, Scope scope)
        {
            var field = node.AncestorsAndSelf()
                        .OfType <MemberDeclarationSyntax>()
                        .FirstOrDefault()
                        as FieldDeclarationSyntax;

            if (field == null)
            {
                //td: error, malformed property
                return(node);
            }

            if (field.Declaration.Variables.Count != 1)
            {
                //td: error, malformed property
                return(node);
            }

            var variable = field
                           .Declaration
                           .Variables[0];

            var initializer = variable.Initializer;
            var type        = field.Declaration.Type;

            if (type == null || type.IsMissing || type.ToString() == "property") //untyped
            {
                if (initializer != null)
                {
                    type = RoslynCompiler.ConstantType(initializer.Value);
                }
            }

            if (type == null)
            {
                type = RoslynCompiler.@object;
            }

            var property = _property
                           .WithIdentifier(variable.Identifier)
                           .WithType(type);

            if (!RoslynCompiler.HasVisibilityModifier(field.Modifiers))
            {
                property = property.AddModifiers(CSharp.Token(SyntaxKind.PublicKeyword));
            }

            var document = scope.GetDocument <SyntaxToken, SyntaxNode, SemanticModel>();

            //schedule the field replacement
            //td: coud be done in this pass with the right info from lexical
            document.change(field, RoslynCompiler.ReplaceNode(property));

            //must be initialized
            if (initializer != null)
            {
                var expr = (AssignmentExpressionSyntax)_assignment.Expression;
                document.change(field.Parent, RoslynCompiler
                                .AddInitializers(_assignment.WithExpression(expr
                                                                            .WithLeft(CSharp.IdentifierName(variable.Identifier))
                                                                            .WithRight(initializer.Value))));
            }

            return(node);
        }
Пример #2
0
        private static SyntaxNode SemanticEventHandler(SyntaxNode oldNode, SyntaxNode node, SemanticModel model, Scope scope)
        {
            var mthd       = (MethodDeclarationSyntax)node;
            var methdArgs  = mthd.ParameterList;
            var methodName = "on_" + mthd.Identifier.ToString();

            ISymbol     self = model.GetDeclaredSymbol(oldNode);
            ITypeSymbol type = (ITypeSymbol)self.ContainingSymbol;

            string evName   = mthd.Identifier.ToString();
            string typeName = type.Name;
            bool   found    = false;

            while (type != null && !found)
            {
                foreach (var ev in type.GetMembers().OfType <IEventSymbol>())
                {
                    if (ev.Name.Equals(evName))
                    {
                        //arguments
                        foreach (var syntax in ev.Type.DeclaringSyntaxReferences)
                        {
                            var refNode = (DelegateDeclarationSyntax)syntax.GetSyntax();

                            int  pCount = methdArgs.Parameters.Count;
                            int  idx    = 0;
                            bool match  = true;
                            methdArgs = refNode.ParameterList.ReplaceNodes(refNode.ParameterList.Parameters, (oldArg, newArg) =>
                            {
                                if (match)
                                {
                                    if (idx >= pCount && match)
                                    {
                                        return(newArg);
                                    }

                                    ParameterSyntax arg = methdArgs.Parameters[idx++];
                                    string argName      = arg.Identifier.ToString();
                                    if (argName == oldArg.Identifier.ToString())
                                    {
                                        //coincident parameters, fix missing type or return same
                                        if (arg.Identifier.IsMissing || arg.Type.ToString() == "void")
                                        {
                                            return(newArg.WithIdentifier(arg.Identifier));
                                        }

                                        return(arg);
                                    }
                                    else
                                    {
                                        match = false;
                                        if (!refNode.ParameterList.Parameters.Any(p => p.Identifier.ToString().Equals(arg.Identifier.ToString())))
                                        {
                                            //name change?
                                            if (oldArg.Identifier.IsMissing)
                                            {
                                                return(newArg.WithIdentifier(CSharp.Identifier(arg.Type.ToString())));
                                            }

                                            return(arg);
                                        }
                                    }
                                }

                                return(newArg);
                            });
                        }

                        //event initialization
                        var document = scope.GetDocument <SyntaxToken, SyntaxNode, SemanticModel>();
                        document.change(mthd.Parent, RoslynCompiler.AddInitializers(EventInitializer(ev.Name, methodName)));
                        found = true;
                        break;
                    }
                }

                type = type.BaseType;
            }

            if (!found)
            {
                //td: error, no such event
            }

            return(mthd.WithIdentifier(CSharp.Identifier(methodName)).
                   WithParameterList(methdArgs));
        }