コード例 #1
0
        public IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            var indexer = context.GetNode <IndexerExpression>();

            if (indexer == null)
            {
                yield break;
            }
            if (!(context.Resolve(indexer).IsError))
            {
                yield break;
            }

            var state = context.GetResolverStateBefore(indexer);

            if (state.CurrentTypeDefinition == null)
            {
                yield break;
            }
            var guessedType = CreateFieldAction.GuessAstType(context, indexer);

            bool          createInOtherType   = false;
            ResolveResult targetResolveResult = null;

            targetResolveResult = context.Resolve(indexer.Target);
            createInOtherType   = !state.CurrentTypeDefinition.Equals(targetResolveResult.Type.GetDefinition());

            bool isStatic;

            if (createInOtherType)
            {
                if (targetResolveResult.Type.GetDefinition() == null || targetResolveResult.Type.GetDefinition().Region.IsEmpty)
                {
                    yield break;
                }
                isStatic = targetResolveResult is TypeResolveResult;
                if (isStatic && targetResolveResult.Type.Kind == TypeKind.Interface || targetResolveResult.Type.Kind == TypeKind.Enum)
                {
                    yield break;
                }
            }
            else
            {
                isStatic = indexer.Target is IdentifierExpression && state.CurrentMember.IsStatic;
            }

            yield return(new CodeAction(context.TranslateString("Create indexer"), script => {
                var decl = new IndexerDeclaration()
                {
                    ReturnType = guessedType,
                    Getter = new Accessor()
                    {
                        Body = new BlockStatement()
                        {
                            new ThrowStatement(new ObjectCreateExpression(context.CreateShortType("System", "NotImplementedException")))
                        }
                    },
                    Setter = new Accessor()
                    {
                        Body = new BlockStatement()
                        {
                            new ThrowStatement(new ObjectCreateExpression(context.CreateShortType("System", "NotImplementedException")))
                        }
                    },
                };
                decl.Parameters.AddRange(CreateMethodDeclarationAction.GenerateParameters(context, indexer.Arguments));
                if (isStatic)
                {
                    decl.Modifiers |= Modifiers.Static;
                }

                if (createInOtherType)
                {
                    if (targetResolveResult.Type.Kind == TypeKind.Interface)
                    {
                        decl.Getter.Body = null;
                        decl.Setter.Body = null;
                        decl.Modifiers = Modifiers.None;
                    }
                    else
                    {
                        decl.Modifiers |= Modifiers.Public;
                    }

                    script.InsertWithCursor(context.TranslateString("Create indexer"), targetResolveResult.Type.GetDefinition(), decl);
                    return;
                }

                script.InsertWithCursor(context.TranslateString("Create indexer"), Script.InsertPosition.Before, decl);
            }, indexer));
        }
コード例 #2
0
        public IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            // NOTE: @, multiple occurance

            var node = context.GetNode();

            while (node != null && !IsStringConcatenation(context, node as BinaryOperatorExpression))
            {
                node = node.Parent;
            }

            if (node == null)
            {
                yield break;
            }

            var expr   = (BinaryOperatorExpression)node;
            var parent = expr.Parent as BinaryOperatorExpression;

            while (parent != null && parent.Operator == BinaryOperatorType.Add)
            {
                expr   = parent;
                parent = expr.Parent as BinaryOperatorExpression;
            }

            yield return(new CodeAction(context.TranslateString("Use string.Format()"),
                                        script =>
            {
                var format = new StringBuilder();
                var stringType = new PrimitiveType("string");
                var formatInvocation = new InvocationExpression(
                    new MemberReferenceExpression(new TypeReferenceExpression(stringType), "Format"));
                var formatLiteral = new PrimitiveExpression("");
                var counter = 0;
                var verbatim = false;
                var arguments = new List <Expression> ();

                format.Append('"');
                formatInvocation.Arguments.Add(formatLiteral);
                foreach (var item in GetConcatItems(context, expr))
                {
                    if (IsStringLiteral(item))
                    {
                        var stringLiteral = (PrimitiveExpression)item;

                        if (stringLiteral.LiteralValue [0] == '@')
                        {
                            verbatim = true;
                            format.Append(stringLiteral.LiteralValue, 2, stringLiteral.LiteralValue.Length - 3);
                        }
                        else
                        {
                            format.Append(stringLiteral.LiteralValue, 1, stringLiteral.LiteralValue.Length - 2);
                        }
                    }
                    else
                    {
                        var index = IndexOf(arguments, item);
                        if (index == -1)
                        {
                            // new item
                            formatInvocation.Arguments.Add(item.Clone());
                            arguments.Add(item);
                            format.Append("{" + counter++ + "}");
                        }
                        else
                        {
                            // existing item
                            format.Append("{" + index + "}");
                        }
                    }
                }
                format.Append('"');
                if (verbatim)
                {
                    format.Insert(0, '@');
                }
                formatLiteral.LiteralValue = format.ToString();
                script.Replace(expr, formatInvocation);
            }));
        }
コード例 #3
0
        public override IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            var switchStatement = context.GetNode <SwitchStatement> ();

            if (switchStatement == null || !switchStatement.SwitchToken.Contains(context.Location))
            {
                yield break;
            }
            var result = context.Resolve(switchStatement.Expression);

            if (result.Type.Kind != TypeKind.Enum)
            {
                yield break;
            }

            if (switchStatement.SwitchSections.Count == 0)
            {
                yield return(new CodeAction(context.TranslateString("Create switch labels"), script => {
                    var type = result.Type;
                    var newSwitch = (SwitchStatement)switchStatement.Clone();

                    var target = context.CreateShortType(result.Type);
                    foreach (var field in type.GetFields())
                    {
                        if (field.IsSynthetic || !field.IsConst)
                        {
                            continue;
                        }
                        newSwitch.SwitchSections.Add(new SwitchSection()
                        {
                            CaseLabels =
                            {
                                new CaseLabel(target.Clone().Member(field.Name))
                            },
                            Statements =
                            {
                                new BreakStatement()
                            }
                        });
                    }

                    newSwitch.SwitchSections.Add(new SwitchSection()
                    {
                        CaseLabels =
                        {
                            new CaseLabel()
                        },
                        Statements =
                        {
                            new ThrowStatement(new ObjectCreateExpression(context.CreateShortType("System", "ArgumentOutOfRangeException")))
                        }
                    });

                    script.Replace(switchStatement, newSwitch);
                }, switchStatement));
            }
            else
            {
                var missingFields = new List <IField>();
                foreach (var field in result.Type.GetFields())
                {
                    if (field.IsSynthetic || !field.IsConst)
                    {
                        continue;
                    }
                    if (!IsHandled(context, switchStatement, field))
                    {
                        missingFields.Add(field);
                    }
                }
                if (missingFields.Count == 0)
                {
                    yield break;
                }
                yield return(new CodeAction(context.TranslateString("Create missing switch labels"), script => {
                    var type = result.Type;
                    //var newSwitch = (SwitchStatement)switchStatement.Clone();
                    var insertNode = (AstNode)switchStatement.SwitchSections.LastOrDefault(s => !s.CaseLabels.Any(label => label.Expression.IsNull)) ?? switchStatement.LBraceToken;

                    var target = context.CreateShortType(result.Type);
                    foreach (var field in missingFields)
                    {
                        script.InsertAfter(insertNode, new SwitchSection()
                        {
                            CaseLabels =
                            {
                                new CaseLabel(target.Clone().Member(field.Name))
                            },
                            Statements =
                            {
                                new BreakStatement()
                            }
                        });
                    }
                }, switchStatement));
            }
        }
コード例 #4
0
        protected override CodeAction GetAction(RefactoringContext context, SwitchStatement node)
        {
            if (!node.SwitchToken.Contains(context.Location))
            {
                return(null);
            }

            // empty switch
            if (node.SwitchSections.Count == 0)
            {
                return(null);
            }

            // switch with default only
            if (node.SwitchSections.First().CaseLabels.Any(label => label.Expression.IsNull))
            {
                return(null);
            }

            // check non-trailing breaks
            foreach (var switchSection in node.SwitchSections)
            {
                var lastStatement = switchSection.Statements.LastOrDefault();
                var finder        = new NonTrailingBreakFinder(lastStatement as BreakStatement);
                if (switchSection.AcceptVisitor(finder))
                {
                    return(null);
                }
            }

            return(new CodeAction(context.TranslateString("Convert to 'if'"),
                                  script =>
            {
                IfElseStatement ifStatement = null;
                IfElseStatement currentStatement = null;
                foreach (var switchSection in node.SwitchSections)
                {
                    var condition = CollectCondition(node.Expression, switchSection.CaseLabels);
                    var bodyStatement = new BlockStatement();
                    var lastStatement = switchSection.Statements.LastOrDefault();
                    foreach (var statement in switchSection.Statements)
                    {
                        // skip trailing break
                        if (statement == lastStatement && statement is BreakStatement)
                        {
                            continue;
                        }
                        bodyStatement.Add(statement.Clone());
                    }

                    // default -> else
                    if (condition == null)
                    {
                        currentStatement.FalseStatement = bodyStatement;
                        break;
                    }
                    var elseIfStatement = new IfElseStatement(condition, bodyStatement);
                    if (ifStatement == null)
                    {
                        ifStatement = elseIfStatement;
                    }
                    else
                    {
                        currentStatement.FalseStatement = elseIfStatement;
                    }
                    currentStatement = elseIfStatement;
                }
                script.Replace(node, ifStatement);
                script.FormatText(ifStatement);
            }, node));
        }
コード例 #5
0
        public override System.Collections.Generic.IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            Expression expr = null;
            AstNode    token;

            if (!NegateRelationalExpressionAction.GetLogicalExpression(context, out expr, out token))
            {
                yield break;
            }

            var uOp = expr as UnaryOperatorExpression;

            if (uOp != null)
            {
                yield return(new CodeAction(
                                 string.Format(context.TranslateString("Invert '{0}'"), expr),
                                 script => {
                    script.Replace(uOp, CSharpUtil.InvertCondition(CSharpUtil.GetInnerMostExpression(uOp.Expression)));
                }, token
                                 ));

                yield break;
            }

            var negativeExpression = CSharpUtil.InvertCondition(expr);

            if (expr.Parent is ParenthesizedExpression && expr.Parent.Parent is UnaryOperatorExpression)
            {
                var unaryOperatorExpression = expr.Parent.Parent as UnaryOperatorExpression;
                if (unaryOperatorExpression.Operator == UnaryOperatorType.Not)
                {
                    yield return(new CodeAction(
                                     string.Format(context.TranslateString("Invert '{0}'"), unaryOperatorExpression),
                                     script => {
                        script.Replace(unaryOperatorExpression, negativeExpression);
                    }, token
                                     ));

                    yield break;
                }
            }
            var newExpression = new UnaryOperatorExpression(UnaryOperatorType.Not, new ParenthesizedExpression(negativeExpression));

            yield return(new CodeAction(
                             string.Format(context.TranslateString("Invert '{0}'"), expr),
                             script => {
                script.Replace(expr, newExpression);
            }, token
                             ));
        }
コード例 #6
0
 /// <summary>
 /// Inserts 'using ns;' in the current scope, and then removes all explicit
 /// usages of ns that were made redundant by the new using.
 /// </summary>
 public static void InsertUsingAndRemoveRedundantNamespaceUsage(RefactoringContext context, Script script, string ns)
 {
     InsertUsing(context, script, new UsingDeclaration(ns));
     // TODO: remove the usages that were made redundant
 }
コード例 #7
0
        /// <summary>
        /// Inserts 'newUsing' in the current scope.
        /// This method will try to insert new usings in the correct position (depending on
        /// where the existing usings are; and maintaining the sort order).
        /// </summary>
        public static void InsertUsing(RefactoringContext context, Script script, AstNode newUsing)
        {
            UsingInfo newUsingInfo       = new UsingInfo(newUsing, context);
            AstNode   enclosingNamespace = context.GetNode <NamespaceDeclaration>() ?? context.RootNode;
            // Find nearest enclosing parent that has usings:
            AstNode usingParent = enclosingNamespace;

            while (usingParent != null && !usingParent.Children.OfType <UsingDeclaration>().Any())
            {
                usingParent = usingParent.Parent;
            }
            if (usingParent == null)
            {
                // No existing usings at all -> use the default location
                if (script.FormattingOptions.UsingPlacement == UsingPlacement.TopOfFile)
                {
                    usingParent = context.RootNode;
                }
                else
                {
                    usingParent = enclosingNamespace;
                }
            }
            // Find the main block of using declarations in the chosen scope:
            AstNode blockStart = usingParent.Children.FirstOrDefault(IsUsingDeclaration);
            AstNode insertionPoint;
            bool    insertAfter = false;

            if (blockStart == null)
            {
                // no using declarations in the file
                Debug.Assert(SyntaxTree.MemberRole == NamespaceDeclaration.MemberRole);
                insertionPoint = usingParent.GetChildrenByRole(SyntaxTree.MemberRole).SkipWhile(CanAppearBeforeUsings).FirstOrDefault();
            }
            else
            {
                insertionPoint = blockStart;
                while (IsUsingFollowing(ref insertionPoint) && newUsingInfo.CompareTo(new UsingInfo(insertionPoint, context)) > 0)
                {
                    insertionPoint = insertionPoint.NextSibling;
                }
                if (!IsUsingDeclaration(insertionPoint))
                {
                    // Insert after last using instead of before next node
                    // This affects where empty lines get placed.
                    insertionPoint = insertionPoint.PrevSibling;
                    insertAfter    = true;
                }
            }
            if (insertionPoint != null)
            {
                if (insertAfter)
                {
                    script.InsertAfter(insertionPoint, newUsing);
                }
                else
                {
                    script.InsertBefore(insertionPoint, newUsing);
                }
            }
        }
コード例 #8
0
        public IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            var identifier = context.GetNode(n => n is IdentifierExpression || n is MemberReferenceExpression) as Expression;

            if (identifier == null)
            {
                yield break;
            }
            if (CreateFieldAction.IsInvocationTarget(identifier))
            {
                yield break;
            }

            var propertyName = GetPropertyName(identifier);

            if (propertyName == null)
            {
                yield break;
            }

            var statement = context.GetNode <Statement>();

            if (statement == null)
            {
                yield break;
            }

            if (!(context.Resolve(identifier).IsError))
            {
                yield break;
            }

            var guessedType = CreateFieldAction.GuessAstType(context, identifier);

            if (guessedType == null)
            {
                yield break;
            }
            var state = context.GetResolverStateBefore(identifier);

            if (state.CurrentTypeDefinition == null)
            {
                yield break;
            }

            bool          createInOtherType   = false;
            ResolveResult targetResolveResult = null;

            if (identifier is MemberReferenceExpression)
            {
                targetResolveResult = context.Resolve(((MemberReferenceExpression)identifier).Target);
                createInOtherType   = !state.CurrentTypeDefinition.Equals(targetResolveResult.Type.GetDefinition());
            }

            bool isStatic = targetResolveResult is TypeResolveResult;

            if (createInOtherType)
            {
                if (isStatic && targetResolveResult.Type.Kind == TypeKind.Interface)
                {
                    yield break;
                }
            }
            else
            {
                if (state.CurrentMember == null)
                {
                    yield break;
                }
                isStatic |= state.CurrentMember.IsStatic || state.CurrentTypeDefinition.IsStatic;
            }

//			var service = (NamingConventionService)context.GetService(typeof(NamingConventionService));
//			if (service != null && !service.IsValidName(propertyName, AffectedEntity.Property, Modifiers.Private, isStatic)) {
//				yield break;
//			}

            yield return(new CodeAction(context.TranslateString("Create property"), script => {
                var decl = new PropertyDeclaration()
                {
                    ReturnType = guessedType,
                    Name = propertyName,
                    Getter = new Accessor(),
                    Setter = new Accessor()
                };
                if (isStatic)
                {
                    decl.Modifiers |= Modifiers.Static;
                }

                if (createInOtherType)
                {
                    if (targetResolveResult.Type.Kind == TypeKind.Interface)
                    {
                        decl.Modifiers = Modifiers.None;
                    }
                    else
                    {
                        decl.Modifiers |= Modifiers.Public;
                    }
                    script.InsertWithCursor(context.TranslateString("Create property"), decl, targetResolveResult.Type.GetDefinition());
                    return;
                }

                script.InsertWithCursor(context.TranslateString("Create property"), decl, Script.InsertPosition.Before);
            }));
        }
コード例 #9
0
        public override IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            if (!context.IsSomethingSelected)
            {
                yield break;
            }
            var selected = new List <AstNode>(context.GetSelectedNodes());

            if (selected.Count != 1 || !(selected [0] is Expression))
            {
                yield break;
            }

            var expr = selected [0] as Expression;

            if (expr is ArrayInitializerExpression)
            {
                var arr = (ArrayInitializerExpression)expr;
                if (arr.IsSingleElement)
                {
                    expr = arr.Elements.First();
                }
                else
                {
                    yield break;
                }
            }

            var visitor = new SearchNodeVisitior(expr);

            var node = context.GetNode <BlockStatement>();

            if (node != null)
            {
                node.AcceptVisitor(visitor);
            }

            yield return(new CodeAction(context.TranslateString("Declare local variable"), script => {
                var resolveResult = context.Resolve(expr);
                var guessedType = resolveResult.Type;
                if (resolveResult is MethodGroupResolveResult)
                {
                    guessedType = GetDelegateType(context, ((MethodGroupResolveResult)resolveResult).Methods.First(), expr);
                }
                var name = CreateMethodDeclarationAction.CreateBaseName(expr, guessedType);
                name = context.GetLocalNameProposal(name, expr.StartLocation);
                var type = context.UseExplicitTypes ? context.CreateShortType(guessedType) : new SimpleType("var");
                var varDecl = new VariableDeclarationStatement(null, type, name, expr.Clone());
                var replaceNode = visitor.Matches.First() as Expression;
                if (replaceNode.Parent is ExpressionStatement)
                {
                    script.Replace(replaceNode.Parent, varDecl);
                    script.Select(varDecl.Variables.First().NameToken);
                }
                else
                {
                    var containing = replaceNode.Parent;
                    while (!(containing.Parent is BlockStatement))
                    {
                        containing = containing.Parent;
                    }

                    script.InsertBefore(containing, varDecl);
                    var identifierExpression = new IdentifierExpression(name);
                    script.Replace(replaceNode, identifierExpression);
                    script.Link(varDecl.Variables.First().NameToken, identifierExpression);
                }
            }, expr));

            if (visitor.Matches.Count > 1)
            {
                yield return(new CodeAction(string.Format(context.TranslateString("Declare local variable (replace '{0}' occurrences)"), visitor.Matches.Count), script => {
                    var resolveResult = context.Resolve(expr);
                    var guessedType = resolveResult.Type;
                    if (resolveResult is MethodGroupResolveResult)
                    {
                        guessedType = GetDelegateType(context, ((MethodGroupResolveResult)resolveResult).Methods.First(), expr);
                    }
                    var linkedNodes = new List <AstNode>();
                    var name = CreateMethodDeclarationAction.CreateBaseName(expr, guessedType);
                    name = context.GetLocalNameProposal(name, expr.StartLocation);
                    var type = context.UseExplicitTypes ? context.CreateShortType(guessedType) : new SimpleType("var");
                    var varDecl = new VariableDeclarationStatement(null, type, name, expr.Clone());
                    linkedNodes.Add(varDecl.Variables.First().NameToken);
                    var first = visitor.Matches [0];
                    if (first.Parent is ExpressionStatement)
                    {
                        script.Replace(first.Parent, varDecl);
                    }
                    else
                    {
                        var containing = first.Parent;
                        while (!(containing.Parent is BlockStatement))
                        {
                            containing = containing.Parent;
                        }

                        script.InsertBefore(containing, varDecl);
                        var identifierExpression = new IdentifierExpression(name);
                        linkedNodes.Add(identifierExpression);
                        script.Replace(first, identifierExpression);
                    }
                    for (int i = 1; i < visitor.Matches.Count; i++)
                    {
                        var identifierExpression = new IdentifierExpression(name);
                        linkedNodes.Add(identifierExpression);
                        script.Replace(visitor.Matches [i], identifierExpression);
                    }
                    script.Link(linkedNodes.ToArray());
                }, expr));
            }
        }
コード例 #10
0
        protected override CodeAction GetAction(RefactoringContext context, Expression expression)
        {
            if (expression == null)
            {
                return(null);
            }
            if (expression.Role != Roles.Argument || expression is NamedArgumentExpression)
            {
                return(null);
            }
            if (context.Location != expression.StartLocation)
            {
                return(null);
            }
            var parent = expression.Parent;

            if (!(parent is CSharp.Attribute) && !(parent is IndexerExpression) && !(parent is InvocationExpression))
            {
                return(null);
            }

            var attribute = parent as CSharp.Attribute;

            if (attribute != null)
            {
                var resolvedResult = context.Resolve(attribute) as CSharpInvocationResolveResult;
                if (resolvedResult == null || resolvedResult.IsError)
                {
                    return(null);
                }
                var     arguments = attribute.Arguments;
                IMember member    = resolvedResult.Member;

                int index = 0;
                int temp  = 0;
                List <Expression> nodes = new List <Expression>();
                foreach (var argument in arguments)
                {
                    if (argument.Equals(expression))
                    {
                        nodes = CollectNodes(parent, expression);
                        break;
                    }
                    temp++;
                }
                index = temp;
                if (!nodes.Any())
                {
                    return(null);
                }
                var method = member as IMethod;
                if (method == null || method.Parameters.Count == 0 || method.Parameters.Last().IsParams)
                {
                    return(null);
                }

                var parameterMap = resolvedResult.GetArgumentToParameterMap();
                var parameters   = method.Parameters;
                if (index >= parameterMap.Count)
                {
                    return(null);
                }
                var name = parameters[parameterMap[index]].Name;
                return(new CodeAction(string.Format(context.TranslateString("Add argument name '{0}'"), name), script => {
                    for (int i = 0; i < nodes.Count; i++)
                    {
                        int p = index + i;
                        if (p >= parameterMap.Count)
                        {
                            break;
                        }
                        name = parameters[parameterMap[p]].Name;
                        var namedArgument = new NamedArgumentExpression(name, arguments.ElementAt(p).Clone());
                        script.Replace(arguments.ElementAt(p), namedArgument);
                    }
                },
                                      expression
                                      ));
            }

            var indexerExpression = parent as IndexerExpression;

            if (indexerExpression != null)
            {
                var resolvedResult = context.Resolve(indexerExpression) as CSharpInvocationResolveResult;
                if (resolvedResult == null || resolvedResult.IsError)
                {
                    return(null);
                }
                var     arguments = indexerExpression.Arguments;
                IMember member    = resolvedResult.Member;

                int index = 0;
                int temp  = 0;
                List <Expression> nodes = new List <Expression>();
                foreach (var argument in arguments)
                {
                    if (argument.Equals(expression))
                    {
                        nodes = CollectNodes(parent, expression);
                        break;
                    }
                    temp++;
                }
                index = temp;
                if (!nodes.Any())
                {
                    return(null);
                }
                var property = member as IProperty;
                if (property == null || property.Parameters.Count == 0 || property.Parameters.Last().IsParams)
                {
                    return(null);
                }
                var parameterMap = resolvedResult.GetArgumentToParameterMap();
                var parameters   = property.Parameters;
                if (index >= parameterMap.Count)
                {
                    return(null);
                }
                var name = parameters[parameterMap[index]].Name;
                return(new CodeAction(string.Format(context.TranslateString("Add argument name '{0}'"), name), script => {
                    for (int i = 0; i < nodes.Count; i++)
                    {
                        int p = index + i;
                        if (p >= parameterMap.Count)
                        {
                            break;
                        }
                        name = parameters[parameterMap[p]].Name;
                        var namedArgument = new NamedArgumentExpression(name, arguments.ElementAt(p).Clone());
                        script.Replace(arguments.ElementAt(p), namedArgument);
                    }
                },
                                      expression
                                      ));
            }

            var invocationExpression = parent as InvocationExpression;

            if (invocationExpression != null)
            {
                var resolvedResult = context.Resolve(invocationExpression) as CSharpInvocationResolveResult;
                if (resolvedResult == null || resolvedResult.IsError)
                {
                    return(null);
                }
                var     arguments = invocationExpression.Arguments;
                IMember member    = resolvedResult.Member;

                int index = 0;
                int temp  = 0;
                List <Expression> nodes = new List <Expression>();
                foreach (var argument in arguments)
                {
                    if (argument.Equals(expression))
                    {
                        nodes = CollectNodes(parent, expression);
                        break;
                    }
                    temp++;
                }
                index = temp;
                if (!nodes.Any())
                {
                    return(null);
                }

                var method = member as IMethod;
                if (method == null || method.Parameters.Count == 0 || method.Parameters.Last().IsParams)
                {
                    return(null);
                }

                var parameterMap = (resolvedResult as CSharpInvocationResolveResult).GetArgumentToParameterMap();
                var parameters   = method.Parameters;
                if (index >= parameterMap.Count)
                {
                    return(null);
                }
                var name = parameters[parameterMap[index]].Name;
                return(new CodeAction(string.Format(context.TranslateString("Add argument name '{0}'"), name), script => {
                    for (int i = 0; i < nodes.Count; i++)
                    {
                        int p = index + i;
                        if (p >= parameterMap.Count)
                        {
                            break;
                        }
                        name = parameters[parameterMap[p]].Name;
                        var namedArgument = new NamedArgumentExpression(name, arguments.ElementAt(p).Clone());
                        script.Replace(arguments.ElementAt(p), namedArgument);
                    }
                },
                                      expression
                                      ));
            }
            return(null);
        }
コード例 #11
0
        public override IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            var invocationExpression = context.GetNode <InvocationExpression>();

            if (invocationExpression == null)
            {
                yield break;
            }

            var resolveResult = context.Resolve(invocationExpression) as InvocationResolveResult;

            if (resolveResult == null)
            {
                yield break;
            }

            var method = (IMethod)resolveResult.Member;

            bool foundOptionalParameter = false;

            foreach (var parameter in method.Parameters)
            {
                if (parameter.IsParams)
                {
                    yield break;
                }

                if (parameter.IsOptional)
                {
                    foundOptionalParameter = true;
                    break;
                }
            }

            if (!foundOptionalParameter)
            {
                yield break;
            }

            //Basic sanity checks done, now see if there are any missing optional arguments
            var missingParameters = new List <IParameter>(method.Parameters);

            if (resolveResult.Arguments.Count != invocationExpression.Arguments.Count)
            {
                //Extension method
                missingParameters.RemoveAt(0);
            }
            foreach (var argument in invocationExpression.Arguments)
            {
                var namedArgument = argument as NamedArgumentExpression;
                if (namedArgument == null)
                {
                    missingParameters.RemoveAt(0);
                }
                else
                {
                    missingParameters.RemoveAll(parameter => parameter.Name == namedArgument.Name);
                }
            }

            foreach (var parameterToAdd in missingParameters)
            {
                //Add specific parameter
                yield return(new CodeAction(string.Format(context.TranslateString("Add optional parameter \"{0}\""),
                                                          parameterToAdd.Name),
                                            script => {
                    var newInvocation = (InvocationExpression)invocationExpression.Clone();
                    AddArgument(newInvocation, parameterToAdd, parameterToAdd == missingParameters.First());
                    script.Replace(invocationExpression, newInvocation);
                }, invocationExpression));
            }

            if (missingParameters.Count > 1)
            {
                //Add all parameters at once
                yield return(new CodeAction(context.TranslateString("Add all optional parameters"),
                                            script => {
                    var newInvocation = (InvocationExpression)invocationExpression.Clone();

                    foreach (var parameterToAdd in missingParameters)
                    {
                        //We'll add the remaining parameters, in the order they were declared in the function
                        AddArgument(newInvocation, parameterToAdd, true);
                    }
                    script.Replace(invocationExpression, newInvocation);
                }, invocationExpression));
            }
        }
コード例 #12
0
        public override System.Collections.Generic.IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            var node = context.GetNode <T>();

            if (node == null)
            {
                yield break;
            }
            var action = GetAction(context, node);

            if (action == null)
            {
                yield break;
            }
            yield return(action);
        }
コード例 #13
0
 /// <summary>
 /// Gets the action for the specified ast node.
 /// </summary>
 /// <returns>
 /// The code action. May return <c>null</c>, if no action can be provided.
 /// </returns>
 /// <param name='context'>
 /// The refactoring conext.
 /// </param>
 /// <param name='node'>
 /// The AstNode it's ensured that the node is always != null, if called.
 /// </param>
 protected abstract CodeAction GetAction(RefactoringContext context, T node);
コード例 #14
0
 VariableInitializer GetVariableInitializer(RefactoringContext context)
 {
     return(context.GetNode <VariableInitializer> ());
 }
コード例 #15
0
        public override IEnumerable <CodeAction> GetActions(RefactoringContext context)
        {
            var expr = GetCreatePropertyOrFieldNode(context);

            if (expr == null)
            {
                yield break;
            }

            if (expr is MemberReferenceExpression && !(((MemberReferenceExpression)expr).Target is ThisReferenceExpression))
            {
                yield break;
            }

            var propertyName = CreatePropertyAction.GetPropertyName(expr);

            if (propertyName == null)
            {
                yield break;
            }

            if (IsInvocationTarget(expr))
            {
                yield break;
            }
            var statement = expr.GetParent <Statement>();

            if (statement == null)
            {
                yield break;
            }
            if (!(context.Resolve(expr).IsError))
            {
                yield break;
            }
            var guessedType = TypeGuessing.GuessAstType(context, expr);

            if (guessedType == null)
            {
                yield break;
            }
            var state = context.GetResolverStateBefore(expr);

            if (state.CurrentMember == null || state.CurrentTypeDefinition == null)
            {
                yield break;
            }
            bool isStatic = !(expr is NamedExpression) && (state.CurrentMember.IsStatic | state.CurrentTypeDefinition.IsStatic);

//			var service = (NamingConventionService)context.GetService(typeof(NamingConventionService));
//			if (service != null && !service.IsValidName(identifier.Identifier, AffectedEntity.Field, Modifiers.Private, isStatic)) {
//				yield break;
//			}

            yield return(new CodeAction(context.TranslateString("Create field"), script => {
                var decl = new FieldDeclaration {
                    ReturnType = guessedType,
                    Variables = { new VariableInitializer(propertyName) }
                };
                if (isStatic)
                {
                    decl.Modifiers |= Modifiers.Static;
                }
                script.InsertWithCursor(context.TranslateString("Create field"), Script.InsertPosition.Before, decl);
            }, expr.GetNodeAt(context.Location) ?? expr)
            {
                Severity = ICSharpCode.NRefactory.Refactoring.Severity.Error
            });
        }
コード例 #16
0
 internal static Expression GetCreatePropertyOrFieldNode(RefactoringContext context)
 {
     return(context.GetNode(n => n is IdentifierExpression || n is MemberReferenceExpression || n is NamedExpression) as Expression);
 }