public override VisualBasicSyntaxNode VisitAccessorDeclaration(CSS.AccessorDeclarationSyntax node)
            {
                SyntaxKind blockKind;
                AccessorStatementSyntax      stmt;
                EndBlockStatementSyntax      endStmt;
                SyntaxList <StatementSyntax> body = SyntaxFactory.List <StatementSyntax>();

                if (node.Body != null)
                {
                    body = SyntaxFactory.List(node.Body.Statements.SelectMany(s => s.Accept(new MethodBodyVisitor(semanticModel, this))));
                }
                var             attributes = SyntaxFactory.List(node.AttributeLists.Select(a => (AttributeListSyntax)a.Accept(this)));
                var             modifiers  = ConvertModifiers(node.Modifiers, TokenContext.Member);
                var             parent     = (CSS.BasePropertyDeclarationSyntax)node.Parent.Parent;
                ParameterSyntax valueParam;

                switch (CS.CSharpExtensions.Kind(node))
                {
                case CS.SyntaxKind.GetAccessorDeclaration:
                    blockKind = SyntaxKind.GetAccessorBlock;
                    stmt      = SyntaxFactory.GetAccessorStatement(attributes, modifiers, null);
                    endStmt   = SyntaxFactory.EndGetStatement();
                    break;

                case CS.SyntaxKind.SetAccessorDeclaration:
                    blockKind  = SyntaxKind.SetAccessorBlock;
                    valueParam = SyntaxFactory.Parameter(SyntaxFactory.ModifiedIdentifier("value")).WithAsClause(SyntaxFactory.SimpleAsClause((TypeSyntax)parent.Type.Accept(this)));
                    stmt       = SyntaxFactory.SetAccessorStatement(attributes, modifiers, SyntaxFactory.ParameterList(SyntaxFactory.SingletonSeparatedList(valueParam)));
                    endStmt    = SyntaxFactory.EndSetStatement();
                    break;

                case CS.SyntaxKind.AddAccessorDeclaration:
                    blockKind  = SyntaxKind.AddHandlerAccessorBlock;
                    valueParam = SyntaxFactory.Parameter(SyntaxFactory.ModifiedIdentifier("value")).WithAsClause(SyntaxFactory.SimpleAsClause((TypeSyntax)parent.Type.Accept(this)));
                    stmt       = SyntaxFactory.AddHandlerAccessorStatement(attributes, modifiers, SyntaxFactory.ParameterList(SyntaxFactory.SingletonSeparatedList(valueParam)));
                    endStmt    = SyntaxFactory.EndAddHandlerStatement();
                    break;

                case CS.SyntaxKind.RemoveAccessorDeclaration:
                    blockKind  = SyntaxKind.RemoveHandlerAccessorBlock;
                    valueParam = SyntaxFactory.Parameter(SyntaxFactory.ModifiedIdentifier("value")).WithAsClause(SyntaxFactory.SimpleAsClause((TypeSyntax)parent.Type.Accept(this)));
                    stmt       = SyntaxFactory.RemoveHandlerAccessorStatement(attributes, modifiers, SyntaxFactory.ParameterList(SyntaxFactory.SingletonSeparatedList(valueParam)));
                    endStmt    = SyntaxFactory.EndRemoveHandlerStatement();
                    break;

                default:
                    throw new NotSupportedException();
                }
                return(SyntaxFactory.AccessorBlock(blockKind, stmt, body, endStmt));
            }
        public override async Task ComputeRefactoringsAsync(CodeRefactoringContext context)
        {
            var document = context.Document;

            if (document.Project.Solution.Workspace.Kind == WorkspaceKind.MiscellaneousFiles)
            {
                return;
            }
            var span = context.Span;

            if (!span.IsEmpty)
            {
                return;
            }
            var cancellationToken = context.CancellationToken;

            if (cancellationToken.IsCancellationRequested)
            {
                return;
            }
            var model = await document.GetSemanticModelAsync(cancellationToken).ConfigureAwait(false);

            if (model.IsFromGeneratedCode(cancellationToken))
            {
                return;
            }
            var root = await model.SyntaxTree.GetRootAsync(cancellationToken).ConfigureAwait(false);

            var eventStatement = root.FindNode(span) as EventStatementSyntax;

            if (eventStatement == null)
            {
                return;
            }

            // No action on event blocks
            if (eventStatement.Parent is EventBlockSyntax)
            {
                return;
            }

            // Conversion to custom event only possible for delegate-based events
            if (eventStatement.AsClause == null)
            {
                return;
            }

            var delegateType = model.GetTypeInfo(eventStatement.AsClause.Type).Type;

            if (delegateType.IsErrorType() || !delegateType.IsDelegateType())
            {
                return;
            }
            var delegateParameters = delegateType.GetDelegateInvokeMethod().Parameters;

            context.RegisterRefactoring(
                CodeActionFactory.Create(
                    span,
                    DiagnosticSeverity.Info,
                    GettextCatalog.GetString("Convert to custom event"),
                    t2 =>
            {
                var customEventStatement = SyntaxFactory.EventBlock(
                    eventStatement.WithCustomKeyword(SyntaxFactory.Token(SyntaxKind.CustomKeyword)),
                    SyntaxFactory.List(new AccessorBlockSyntax[] {
                    SyntaxFactory.AddHandlerAccessorBlock(
                        SyntaxFactory.AddHandlerAccessorStatement(
                            SyntaxFactory.List <AttributeListSyntax>(),
                            SyntaxFactory.TokenList(),
                            SyntaxFactory.ParameterList(SyntaxFactory.SeparatedList(new[] {
                        SyntaxFactory.Parameter(SyntaxFactory.List <AttributeListSyntax>(), SyntaxFactory.TokenList(SyntaxFactory.Token(SyntaxKind.ByValKeyword)), SyntaxFactory.ModifiedIdentifier("value"), SyntaxFactory.SimpleAsClause(eventStatement.AsClause.Type().WithoutTrailingTrivia()), null)
                    }))),
                        SyntaxFactory.List <StatementSyntax>(new[] { GetNotImplementedThrowStatement() })),
                    SyntaxFactory.RemoveHandlerAccessorBlock(
                        SyntaxFactory.RemoveHandlerAccessorStatement(
                            SyntaxFactory.List <AttributeListSyntax>(),
                            SyntaxFactory.TokenList(),
                            SyntaxFactory.ParameterList(SyntaxFactory.SeparatedList(new[] {
                        SyntaxFactory.Parameter(SyntaxFactory.List <AttributeListSyntax>(), SyntaxFactory.TokenList(SyntaxFactory.Token(SyntaxKind.ByValKeyword)), SyntaxFactory.ModifiedIdentifier("value"), SyntaxFactory.SimpleAsClause(eventStatement.AsClause.Type().WithoutTrailingTrivia()), null)
                    }))),
                        SyntaxFactory.List <StatementSyntax>(new[] { GetNotImplementedThrowStatement() })),
                    SyntaxFactory.RaiseEventAccessorBlock(
                        SyntaxFactory.RaiseEventAccessorStatement(
                            SyntaxFactory.List <AttributeListSyntax>(),
                            SyntaxFactory.TokenList(),
                            SyntaxFactory.ParameterList(SyntaxFactory.SeparatedList(
                                                            delegateParameters.Select(
                                                                p => SyntaxFactory.Parameter(SyntaxFactory.List <AttributeListSyntax>(), SyntaxFactory.TokenList(SyntaxFactory.Token(SyntaxKind.ByValKeyword)), SyntaxFactory.ModifiedIdentifier(p.Name), SyntaxFactory.SimpleAsClause(SyntaxFactory.ParseTypeName(p.Type.GetFullName())), null)
                                                                )))),
                        SyntaxFactory.List <StatementSyntax>(new[] { GetNotImplementedThrowStatement() }))
                })
                    ).WithTrailingTrivia(eventStatement.GetTrailingTrivia());

                return(Task.FromResult(document.WithSyntaxRoot(root.ReplaceNode(eventStatement, customEventStatement.WithAdditionalAnnotations(Formatter.Annotation)))));
            }
                    )
                );
        }