Esempio n. 1
0
        internal AntlrTokenTagger(ITextBuffer buffer, SVsServiceProvider service_provider)
        {
            _buffer = buffer;

            _antlr_tag_types = new Dictionary <string, AntlrTagTypes>();
            _antlr_tag_types[Constants.ClassificationNameNonterminal] = AntlrTagTypes.Nonterminal;
            _antlr_tag_types[Constants.ClassificationNameTerminal]    = AntlrTagTypes.Terminal;
            _antlr_tag_types[Constants.ClassificationNameComment]     = AntlrTagTypes.Comment;
            _antlr_tag_types[Constants.ClassificationNameKeyword]     = AntlrTagTypes.Keyword;
            _antlr_tag_types[Constants.ClassificationNameLiteral]     = AntlrTagTypes.Literal;
            _antlr_tag_types["other"] = AntlrTagTypes.Other;

            ITextDocument document  = _buffer.GetTextDocument();
            string        file_name = document.FilePath;

            if (file_name.TrimSuffix(".g4") == file_name)
            {
                return;
            }

            if (!ParserDetails._per_file_parser_details.ContainsKey(file_name))
            {
                ParserDetails parser_details = new ParserDetails();
                ParserDetails._per_file_parser_details[file_name] = parser_details;
                string text = _buffer.GetBufferText();
                parser_details.Parse(text, file_name);
            }

            this._buffer.Changed += OnTextBufferChanged;
        }
Esempio n. 2
0
        public void Parse(ParserDetails pd)
        {
            var        code = pd.Code;
            var        ffn  = pd.FullFileName;
            IParseTree pt   = null;

            // Set up Antlr to parse input grammar.
            byte[] byteArray = Encoding.UTF8.GetBytes(code);
            var    ais       = new AntlrInputStream(
                new StreamReader(
                    new MemoryStream(byteArray)).ReadToEnd());

            ais.name = ffn;
            CommonTokenStream cts = new CommonTokenStream(new Python3Lexer(ais));
            var parser            = new Python3Parser(cts);

            try
            {
                pt = parser.file_input();
            }
            catch (Exception)
            {
                // Parsing error.
            }

            //StringBuilder sb = new StringBuilder();
            //TreeSerializer.ParenthesizedAST(pt, sb, "", cts);
            //string fn = System.IO.Path.GetFileName(ffn);
            //fn = "c:\\temp\\" + fn;
            //System.IO.File.WriteAllText(fn, sb.ToString());

            pd.ParseTree = pt;
        }
Esempio n. 3
0
        private Document CheckDoc(System.Uri uri)
        {
            string   decoded   = System.Web.HttpUtility.UrlDecode(uri.AbsoluteUri);
            string   file_name = new Uri(decoded).LocalPath;
            Document document  = _workspace.FindDocument(file_name);

            if (document == null)
            {
                document = new Workspaces.Document(file_name);
                try
                {   // Open the text file using a stream reader.
                    using (StreamReader sr = new StreamReader(file_name))
                    {
                        // Read the stream to a string, and write the string to the console.
                        string str = sr.ReadToEnd();
                        document.Code = str;
                    }
                }
                catch (IOException)
                {
                }
                Project project = _workspace.FindProject("Misc");
                if (project == null)
                {
                    project = new Project("Misc", "Misc", "Misc");
                    _workspace.AddChild(project);
                }
                project.AddDocument(document);
                document.Changed = true;
                ParserDetails        pd    = ParserDetailsFactory.Create(document);
                List <ParserDetails> to_do = LanguageServer.Module.Compile();
            }
            return(document);
        }
Esempio n. 4
0
        public async void TextDocumentDidChangeName(JToken arg)
        {
            if (trace)
            {
                System.Console.Error.WriteLine("<-- TextDocumentDidChange");
                System.Console.Error.WriteLine(arg.ToString());
            }
            DidChangeTextDocumentParams request = arg.ToObject <DidChangeTextDocumentParams>();
            int?     version  = request.TextDocument.Version;
            Document document = CheckDoc(request.TextDocument.Uri);

            lock (_object)
            {
                ParserDetails pd          = ParserDetailsFactory.Create(document);
                string        code        = pd.Code;
                int           start_index = 0;
                int           end_index   = 0;
                foreach (TextDocumentContentChangeEvent change in request.ContentChanges)
                {
                    Microsoft.VisualStudio.LanguageServer.Protocol.Range range = change.Range;
                    int    length = change.RangeLength; // Why? range encodes start and end => length!
                    string text   = change.Text;
                    {
                        int line      = range.Start.Line;
                        int character = range.Start.Character;
                        start_index = LanguageServer.Module.GetIndex(line, character, document);
                    }
                    {
                        int line      = range.End.Line;
                        int character = range.End.Character;
                        end_index = LanguageServer.Module.GetIndex(line, character, document);
                    }
                    (int, int)bs = LanguageServer.Module.GetLineColumn(start_index, document);
                    (int, int)be = LanguageServer.Module.GetLineColumn(end_index, document);
                    string original = code.Substring(start_index, end_index - start_index);
                    string n        = code.Substring(0, start_index)
                                      + text
                                      + code.Substring(0 + start_index + end_index - start_index);
                    code = n;
                }
                document.Code = code;
                List <ParserDetails> to_do = LanguageServer.Module.Compile();
            }
        }
Esempio n. 5
0
        private void BufferChanged(object sender, TextContentChangedEventArgs e)
        {
            // Non-incremental parse. Future work: if performance becomes a problem, it would
            // probably be best to make the lexical analyzer incremental, then
            // do a full parse.
            ITextSnapshot snapshot = _buffer.CurrentSnapshot;

            if (TagsChanged != null)
            {
                ParserDetails foo = new ParserDetails();
                ITextDocument doc = _buffer.GetTextDocument();
                string        f   = doc.FilePath;
                ParserDetails._per_file_parser_details[f] = foo;
                IVsTextView  vstv  = IVsTextViewExtensions.GetIVsTextView(f);
                IWpfTextView wpftv = vstv.GetIWpfTextView();
                if (wpftv == null)
                {
                    return;
                }
                ITextBuffer tb = wpftv.TextBuffer;
                foo.Parse(tb.GetBufferText(), f);
                TagsChanged(this, new SnapshotSpanEventArgs(new SnapshotSpan(snapshot, new Span(0, snapshot.Length))));
            }
        }
Esempio n. 6
0
        // For each span of text given, perform a complete parse, and reclassify and tag new spans.
        public IEnumerable <ITagSpan <AntlrTokenTag> > GetTags(NormalizedSnapshotSpanCollection spans)
        {
            // Nothing graceful here in relating a span to a part in the
            // syntax tree. For now, get the bounds of the span, find tree nodes
            // that overlap the span. Find all nonterminals
            // and terminals to mark the span up. Likewise, for all comments,
            // find all that overlap span. Sort all terminals, nonterminals,
            // and comments into a list, and package it up as new TagSpan.

            foreach (SnapshotSpan curSpan in spans)
            {
                ITextSnapshotLine containingLine = curSpan.Start.GetContainingLine();
                int         curLoc    = containingLine.Start.Position;
                string      text      = curSpan.GetText();
                ITextBuffer buf       = curSpan.Snapshot.TextBuffer;
                var         doc       = buf.GetTextDocument();
                string      file_name = doc.FilePath;

                ParserDetails details = null;
                bool          found   = ParserDetails._per_file_parser_details.TryGetValue(file_name, out details);
                if (!found)
                {
                    continue;
                }

                SnapshotPoint start       = curSpan.Start;
                int           curLocStart = start.Position;
                SnapshotPoint end         = curSpan.End;
                int           curLocEnd   = end.Position;

                // Collect all nonterminals, terminals, ..., in this span.
                IEnumerable <IToken> combined_tokens    = new List <IToken>();
                List <IToken>        all_term_tokens    = new List <IToken>();
                List <IToken>        all_nonterm_tokens = new List <IToken>();
                List <IToken>        all_comment_tokens = new List <IToken>();
                List <IToken>        all_keyword_tokens = new List <IToken>();
                List <IToken>        all_literal_tokens = new List <IToken>();

                all_nonterm_tokens = details._ant_nonterminals.Where((token) =>
                {
                    int start_token_start = token.StartIndex;
                    int end_token_end     = token.StopIndex;
                    if (start_token_start >= curLocEnd)
                    {
                        return(false);
                    }
                    if (end_token_end < curLocStart)
                    {
                        return(false);
                    }
                    return(true);
                }).ToList();
                combined_tokens = combined_tokens.Concat(all_nonterm_tokens);
                all_term_tokens = details._ant_terminals.Where((token) =>
                {
                    int start_token_start = token.StartIndex;
                    int end_token_end     = token.StopIndex;
                    if (start_token_start >= curLocEnd)
                    {
                        return(false);
                    }
                    if (end_token_end < curLocStart)
                    {
                        return(false);
                    }
                    return(true);
                }).ToList();
                combined_tokens    = combined_tokens.Concat(all_term_tokens);
                all_comment_tokens = details._ant_comments.Where((token) =>
                {
                    int start_token_start = token.StartIndex;
                    int end_token_end     = token.StopIndex;
                    if (start_token_start >= curLocEnd)
                    {
                        return(false);
                    }
                    if (end_token_end < curLocStart)
                    {
                        return(false);
                    }
                    return(true);
                }).ToList();
                combined_tokens    = combined_tokens.Concat(all_comment_tokens);
                all_keyword_tokens = details._ant_keywords.Where((token) =>
                {
                    int start_token_start = token.StartIndex;
                    int end_token_end     = token.StopIndex;
                    if (start_token_start >= curLocEnd)
                    {
                        return(false);
                    }
                    if (end_token_end < curLocStart)
                    {
                        return(false);
                    }
                    return(true);
                }).ToList();
                combined_tokens    = combined_tokens.Concat(all_keyword_tokens);
                all_literal_tokens = details._ant_literals.Where((token) =>
                {
                    int start_token_start = token.StartIndex;
                    int end_token_end     = token.StopIndex;
                    if (start_token_start >= curLocEnd)
                    {
                        return(false);
                    }
                    if (end_token_end < curLocStart)
                    {
                        return(false);
                    }
                    return(true);
                }).ToList();
                combined_tokens = combined_tokens.Concat(all_literal_tokens);

                // Sort the list.
                var sorted_combined_tokens = combined_tokens.OrderBy((t) => t.StartIndex).ToList();

                // Assumption: tokens do not overlap.

                foreach (IToken token in sorted_combined_tokens)
                {
                    int start_token_start = token.StartIndex;
                    int end_token_end     = token.StopIndex;
                    int length            = end_token_end - start_token_start + 1;

                    // Make sure the length doesn't go past the end of the current span.
                    if (start_token_start + length > curLocEnd)
                    {
                        length = curLocEnd - start_token_start;
                    }

                    var tokenSpan = new SnapshotSpan(
                        curSpan.Snapshot,
                        new Span(start_token_start, length));

                    AntlrTagTypes type;
                    if (all_term_tokens.Contains(token))
                    {
                        type = AntlrTagTypes.Terminal;
                    }
                    else if (all_nonterm_tokens.Contains(token))
                    {
                        type = AntlrTagTypes.Nonterminal;
                    }
                    else if (all_comment_tokens.Contains(token))
                    {
                        type = AntlrTagTypes.Comment;
                    }
                    else if (all_keyword_tokens.Contains(token))
                    {
                        type = AntlrTagTypes.Keyword;
                    }
                    else if (all_literal_tokens.Contains(token))
                    {
                        type = AntlrTagTypes.Literal;
                    }
                    else
                    {
                        type = AntlrTagTypes.Other;
                    }

                    if (tokenSpan.IntersectsWith(curSpan))
                    {
                        TagSpan <AntlrTokenTag> t = new TagSpan <AntlrTokenTag>(tokenSpan, new AntlrTokenTag(type));
                        yield return(t);
                    }
                }
            }
        }
Esempio n. 7
0
        private void MenuItemCallback(object sender, EventArgs e, bool forward)
        {
            try
            {
                ////////////////////////
                /// Next rule.
                ////////////////////////

                string       classification = AntlrLanguagePackage.Instance.Classification;
                SnapshotSpan span           = AntlrLanguagePackage.Instance.Span;
                ITextView    view           = AntlrLanguagePackage.Instance.View;

                view = AntlrLanguagePackage.Instance.GetActiveView();
                if (view == null)
                {
                    return;
                }

                ITextCaret    car = view.Caret;
                CaretPosition cp  = car.Position;
                SnapshotPoint bp  = cp.BufferPosition;
                int           pos = bp.Position;

                // First, find out what this view is, and what the file is.
                ITextBuffer buffer = view.TextBuffer;
                string      path   = buffer.GetFFN().Result;
                if (path == null)
                {
                    return;
                }

                List <IToken> where = new List <IToken>();
                List <ParserDetails> where_details = new List <ParserDetails>();
                int next_sym = forward ? Int32.MaxValue : -1;
                foreach (var kvp in ParserDetailsFactory.AllParserDetails)
                {
                    string file_name = kvp.Key;
                    if (file_name != path)
                    {
                        continue;
                    }
                    ParserDetails details = kvp.Value;
                    foreach (var p in details.Defs)
                    {
                        if (p.Value != 0)
                        {
                            continue;
                        }
                        var t = p.Key;
                        if (forward)
                        {
                            if (t.Symbol.StartIndex > pos && t.Symbol.StartIndex < next_sym)
                            {
                                next_sym = t.Symbol.StartIndex;
                            }
                        }
                        else
                        {
                            if (t.Symbol.StartIndex < pos && t.Symbol.StartIndex > next_sym)
                            {
                                next_sym = t.Symbol.StartIndex;
                            }
                        }
                    }

                    foreach (var p in details.Defs)
                    {
                        if (p.Value != 1)
                        {
                            continue;
                        }
                        var t = p.Key;
                        if (forward)
                        {
                            if (t.Symbol.StartIndex > pos && t.Symbol.StartIndex < next_sym)
                            {
                                next_sym = t.Symbol.StartIndex;
                            }
                        }
                        else
                        {
                            if (t.Symbol.StartIndex < pos && t.Symbol.StartIndex > next_sym)
                            {
                                next_sym = t.Symbol.StartIndex;
                            }
                        }
                    }

                    break;
                }

                if (next_sym == Int32.MaxValue || next_sym < 0)
                {
                    return;
                }

                string      full_file_name = path;
                IVsTextView vstv           = IVsTextViewExtensions.FindTextViewFor(full_file_name);
                if (vstv == null)
                {
                    IVsTextViewExtensions.ShowFrame(full_file_name);
                    vstv = IVsTextViewExtensions.FindTextViewFor(full_file_name);
                }

                IWpfTextView wpftv = vstv.GetIWpfTextView();
                if (wpftv == null)
                {
                    return;
                }

                int line_number;
                int colum_number;
                vstv.GetLineAndColumn(next_sym, out line_number, out colum_number);

                // Create new span in the appropriate view.
                ITextSnapshot cc = wpftv.TextBuffer.CurrentSnapshot;
                SnapshotSpan  ss = new SnapshotSpan(cc, next_sym, 1);
                SnapshotPoint sp = ss.Start;
                // Put cursor on symbol.
                wpftv.Caret.MoveTo(sp); // This sets cursor, bot does not center.
                                        // Center on cursor.
                if (line_number > 0)
                {
                    vstv.CenterLines(line_number - 1, 2);
                }
                else
                {
                    vstv.CenterLines(line_number, 1);
                }
                AntlrVSIX.Package.Menus.ResetMenus();
            }
            catch (Exception exception)
            {
                Logger.Log.Notify(exception.StackTrace);
            }
        }
        private void UpdateWordAdornments(object threadContext)
        {
            if (!Enabled)
            {
                return;
            }

            Enabled = false;

            SnapshotPoint currentRequest = RequestedPoint;

            List <SnapshotSpan> wordSpans = new List <SnapshotSpan>();

            // Find all words in the buffer like the one the caret is on
            TextExtent word = TextStructureNavigator.GetExtentOfWord(currentRequest);

            bool foundWord = true;

            // If we've selected something not worth highlighting, we might have
            // missed a "word" by a little bit
            if (!WordExtentIsValid(currentRequest, word))
            {
                // Before we retry, make sure it is worthwhile
                if (word.Span.Start != currentRequest ||
                    currentRequest == currentRequest.GetContainingLine().Start ||
                    char.IsWhiteSpace((currentRequest - 1).GetChar()))
                {
                    foundWord = false;
                }
                else
                {
                    // Try again, one character previous.  If the caret is at the end of a word, then
                    // this will pick up the word we are at the end of.
                    word = TextStructureNavigator.GetExtentOfWord(currentRequest - 1);

                    // If we still aren't valid the second time around, we're done
                    if (!WordExtentIsValid(currentRequest, word))
                    {
                        foundWord = false;
                    }
                }
            }

            if (!foundWord)
            {
                // If we couldn't find a word, just clear out the existing markers
                SynchronousUpdate(currentRequest, new NormalizedSnapshotSpanCollection(), null);
                return;
            }

            SnapshotSpan currentWord = word.Span;

            // If this is the same word we currently have, we're done (e.g. caret moved within a word).
            if (CurrentWord.HasValue && currentWord == CurrentWord)
            {
                return;
            }

            /* Find spans using simple text search....
             * FindData findData = new FindData(currentWord.GetText(), currentWord.Snapshot);
             * findData.FindOptions = FindOptions.WholeWord | FindOptions.MatchCase;
             * wordSpans.AddRange(TextSearchService.FindAll(findData));
             */

            // Verify current word is a grammar symbol.
            //  Now, check for valid classification type.
            string classification = null;

            ClassificationSpan[] c1 = _aggregator.GetClassificationSpans(currentWord).ToArray();
            foreach (ClassificationSpan cl in c1)
            {
                classification = cl.ClassificationType.Classification.ToLower();
                if (classification == AntlrVSIX.Constants.ClassificationNameTerminal)
                {
                    break;
                }
                else if (classification == AntlrVSIX.Constants.ClassificationNameNonterminal)
                {
                    break;
                }
            }
            if (classification == null)
            {
                return;
            }

            SnapshotSpan span = currentWord;
            ITextView    view = this.View;

            // First, find out what this view is, and what the file is.
            ITextBuffer   buffer = view.TextBuffer;
            ITextDocument doc    = buffer.GetTextDocument();
            string        path   = doc.FilePath;

            List <IToken> where = new List <IToken>();
            List <ParserDetails> where_details = new List <ParserDetails>();
            IToken token = null;

            foreach (var kvp in ParserDetails._per_file_parser_details)
            {
                string        file_name = kvp.Key;
                ParserDetails details   = kvp.Value;
                if (classification == AntlrVSIX.Constants.ClassificationNameNonterminal)
                {
                    var it = details._ant_nonterminals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
                else if (classification == AntlrVSIX.Constants.ClassificationNameTerminal)
                {
                    var it = details._ant_terminals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
                else if (classification == AntlrVSIX.Constants.ClassificationNameLiteral)
                {
                    var it = details._ant_literals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
            }
            if (!where.Any())
            {
                return;
            }

            // Populate the Antlr find results model/window with file/line/col info
            // for each occurrence.
            var results = new List <Entry>();

            for (int i = 0; i < where.Count; ++i)
            {
                IToken        x = where[i];
                ParserDetails y = where_details[i];
                var           w = new Entry()
                {
                    FileName = y.full_file_name, LineNumber = x.Line, ColumnNumber = x.Column, Token = x
                };
                results.Add(w);
            }

            // Now, for all entries which are in this buffer, highlight.
            //wordSpans.Add(currentWord);
            for (int i = 0; i < results.Count; ++i)
            {
                var w = results[i];
                if (w.FileName == path)
                {
                    // Create new span in the appropriate view.
                    ITextSnapshot cc = buffer.CurrentSnapshot;
                    SnapshotSpan  ss = new SnapshotSpan(cc, w.Token.StartIndex, 1 + w.Token.StopIndex - w.Token.StartIndex);
                    SnapshotPoint sp = ss.Start;
                    wordSpans.Add(ss);
                }
            }

            // If we are still up-to-date (another change hasn't happened yet), do a real update
            if (currentRequest == RequestedPoint)
            {
                SynchronousUpdate(currentRequest, new NormalizedSnapshotSpanCollection(wordSpans), currentWord);
            }

            // Call up the rename dialog box. In another thread because
            // of "The calling thread must be STA, because many UI components require this."
            // error.
            Application.Current.Dispatcher.Invoke((Action) delegate {
                RenameDialogBox inputDialog = new RenameDialogBox(currentWord.GetText());
                if (inputDialog.ShowDialog() == true)
                {
                    results.Reverse();
                    var new_name = inputDialog.Answer;
                    // Replace all occurrences of symbol, working backwards.
                    foreach (Entry e in results)
                    {
                        string file_name   = e.FileName;
                        var pd             = ParserDetails._per_file_parser_details[file_name];
                        IVsTextView vstv   = IVsTextViewExtensions.GetIVsTextView(file_name);
                        IWpfTextView wpftv = vstv.GetIWpfTextView();
                        if (wpftv == null)
                        {
                            // File has not been opened before! Open file in editor.
                            IVsTextViewExtensions.ShowFrame(file_name);
                            vstv  = IVsTextViewExtensions.GetIVsTextView(file_name);
                            wpftv = vstv.GetIWpfTextView();
                        }
                        ITextBuffer tb   = wpftv.TextBuffer;
                        ITextSnapshot cc = tb.CurrentSnapshot;
                        SnapshotSpan ss  = new SnapshotSpan(cc, e.Token.StartIndex, 1 + e.Token.StopIndex - e.Token.StartIndex);
                        SnapshotPoint sp = ss.Start;
                        tb.Replace(ss, new_name);
                    }

                    // Reparse everything.
                    foreach (string f in results.Select((e) => e.FileName).Distinct())
                    {
                        ParserDetails foo = new ParserDetails();
                        ParserDetails._per_file_parser_details[f] = foo;
                        IVsTextView vstv   = IVsTextViewExtensions.GetIVsTextView(f);
                        IWpfTextView wpftv = vstv.GetIWpfTextView();
                        if (wpftv == null)
                        {
                            continue;
                        }
                        ITextBuffer tb = wpftv.TextBuffer;
                        foo.Parse(tb.GetBufferText(), f);
                    }
                }
            });
        }
Esempio n. 9
0
        private void RenameCallback(object sender, EventArgs e)
        {
            // Highlight the symbol, reposition it to the beginning of it.
            // Every character changes all occurrences of the symbol.

            // First, open up every .g4 file in project and parse.
            DTE application = DteExtensions.GetApplication();

            if (application != null)
            {
                IEnumerable <ProjectItem> iterator = DteExtensions.SolutionFiles(application);
                ProjectItem[]             list     = iterator.ToArray();
                foreach (var item in list)
                {
                    //var doc = item.Document; CRASHES!!!! DO NOT USE!
                    //var props = item.Properties;
                    string file_name = item.Name;
                    if (file_name != null)
                    {
                        string prefix = file_name.TrimSuffix(".g4");
                        if (prefix == file_name)
                        {
                            continue;
                        }

                        try
                        {
                            object prop = item.Properties.Item("FullPath").Value;
                            string ffn  = (string)prop;
                            if (!ParserDetails._per_file_parser_details.ContainsKey(ffn))
                            {
                                StreamReader  sr  = new StreamReader(ffn);
                                ParserDetails foo = new ParserDetails();
                                ParserDetails._per_file_parser_details[ffn] = foo;
                                foo.Parse(sr.ReadToEnd(), ffn);
                            }
                        }
                        catch (Exception eeks)
                        { }
                    }
                }
            }

            string       classification = this.Classification;
            SnapshotSpan span           = this.Symbol;
            ITextView    view           = this.View;

            // First, find out what this view is, and what the file is.
            ITextBuffer   buffer = view.TextBuffer;
            ITextDocument doc    = buffer.GetTextDocument();
            string        path   = doc.FilePath;
            IVsTextView   vstv   = IVsTextViewExtensions.GetIVsTextView(path);

            List <IToken> where = new List <IToken>();
            List <ParserDetails> where_details = new List <ParserDetails>();
            IToken token = null;

            foreach (var kvp in ParserDetails._per_file_parser_details)
            {
                string        file_name = kvp.Key;
                ParserDetails details   = kvp.Value;
                if (classification == AntlrVSIX.Constants.ClassificationNameNonterminal)
                {
                    var it = details._ant_nonterminals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
                else if (classification == AntlrVSIX.Constants.ClassificationNameTerminal)
                {
                    var it = details._ant_terminals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
                else if (classification == AntlrVSIX.Constants.ClassificationNameLiteral)
                {
                    var it = details._ant_literals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
            }
            if (!where.Any())
            {
                return;
            }

            IWpfTextView wpftv = vstv.GetIWpfTextView();

            if (wpftv == null)
            {
                return;
            }

            // Create new span in the appropriate view.
            ITextSnapshot cc = wpftv.TextBuffer.CurrentSnapshot;
            SnapshotSpan  ss = new SnapshotSpan(cc, span.Start.Position, 1);
            SnapshotPoint sp = ss.Start;

            // Enable highlighter.
            RenameHighlightTagger.Enabled = true;

            // Put cursor on symbol.
            wpftv.Caret.MoveTo(sp);     // This sets cursor, bot does not center.
        }
Esempio n. 10
0
        private void MenuItemCallback(object sender, EventArgs e, bool visitor)
        {
            try
            {
                // Return if I can't determine what application this is.
                DTE application = Workspaces.Help.GetApplication();
                if (application == null)
                {
                    return;
                }

                // Get active view and determine if it's a grammar file.
                var grammar_view = AntlrLanguagePackage.Instance.GetActiveView();
                if (grammar_view == null)
                {
                    return;
                }
                ITextCaret    car          = grammar_view.Caret;
                CaretPosition cp           = car.Position;
                SnapshotPoint bp           = cp.BufferPosition;
                int           pos          = bp.Position;
                ITextBuffer   buffer       = grammar_view.TextBuffer;
                var           g4_file_path = buffer.GetFFN().Result;
                if (g4_file_path == null)
                {
                    return;
                }
                IGrammarDescription grammar_description = LanguageServer.GrammarDescriptionFactory.Create(g4_file_path);
                if (!grammar_description.IsFileType(g4_file_path))
                {
                    return;
                }

                // Get name of base class for listener and visitor. These are generated by Antlr,
                // constructed from the name of the file.
                var grammar_name = Path.GetFileName(g4_file_path);
                grammar_name = Path.GetFileNameWithoutExtension(grammar_name);
                var listener_baseclass_name = visitor ? (grammar_name + "BaseVisitor") : (grammar_name + "BaseListener");
                var listener_class_name     = visitor ? ("My" + grammar_name + "Visitor") : ("My" + grammar_name + "Listener");

                // In the current view, find the details of the Antlr symbol at the cursor.
                TextExtent extent = AntlrVSIX.Package.AntlrLanguagePackage.Instance.Navigator[grammar_view]
                                    .GetExtentOfWord(bp);
                SnapshotSpan span = extent.Span;
                AntlrLanguagePackage.Instance.Span = span;

                //  Now, check for valid classification type.
                var  cla             = -1;
                bool can_gotovisitor = AntlrVSIX.Package.AntlrLanguagePackage.Instance.Aggregator[grammar_view].GetClassificationSpans(span).Where(
                    classification =>
                {
                    var name = classification.ClassificationType.Classification;
                    if (!grammar_description.InverseMap.TryGetValue(name, out int c))
                    {
                        return(false);
                    }
                    cla = c;
                    return(grammar_description.CanGotovisitor[cla]);
                }).Any();
                if (!can_gotovisitor)
                {
                    return;
                }

                // Find defining occurrence.
                List <Antlr4.Runtime.Tree.TerminalNodeImpl> where = new List <Antlr4.Runtime.Tree.TerminalNodeImpl>();
                List <ParserDetails> where_details         = new List <ParserDetails>();
                Antlr4.Runtime.Tree.TerminalNodeImpl token = null;
                foreach (var kvp in ParserDetailsFactory.AllParserDetails)
                {
                    string        file_name = kvp.Key;
                    ParserDetails details   = kvp.Value;
                    {
                        var it = details.Defs.Where(
                            (t) => t.Value == cla && t.Key.Symbol.Text == span.GetText()).Select(t => t.Key);
                        where.AddRange(it);
                        foreach (var i in it)
                        {
                            where_details.Add(details);
                        }
                    }
                }

                if (where.Any())
                {
                    token = where.First();
                }
                else
                {
                    System.Windows.Forms.MessageBox.Show(
                        "Symbol '" + span.GetText() + "' definer not found.");
                    return;
                }

                // Get the symbol name as a string.
                var symbol_name             = token.Symbol.Text;
                var capitalized_symbol_name = Capitalized(symbol_name);

                // Parse all the C# files in the solution.
                Dictionary <string, SyntaxTree> trees = new Dictionary <string, SyntaxTree>();
                foreach (var item in DteExtensions.SolutionFiles(application))
                {
                    string file_name = item.Name;
                    if (file_name != null)
                    {
                        string prefix = file_name.TrimSuffix(".cs");
                        if (prefix == file_name)
                        {
                            continue;
                        }
                        try
                        {
                            object       prop = item.Properties.Item("FullPath").Value;
                            string       ffn  = (string)prop;
                            StreamReader sr   = new StreamReader(ffn);
                            string       code = sr.ReadToEnd();
                            SyntaxTree   tree = CSharpSyntaxTree.ParseText(code);
                            trees[ffn] = tree;
                        }
                        catch (Exception)
                        {
                        }
                    }
                }

                // Find all occurrences of visitor class.
                List <ClassDeclarationSyntax> found_class = new List <ClassDeclarationSyntax>();
                string class_file_path = null;
                try
                {
                    foreach (var kvp in trees)
                    {
                        var file_name = kvp.Key;
                        var tree      = kvp.Value;

                        // Look for IParseTreeListener or IParseTreeVisitor classes.
                        var root = (CompilationUnitSyntax)tree.GetRoot();
                        if (root == null)
                        {
                            continue;
                        }
                        foreach (var nm in root.Members)
                        {
                            var namespace_member = nm as NamespaceDeclarationSyntax;
                            if (namespace_member == null)
                            {
                                continue;
                            }
                            foreach (var cm in namespace_member.Members)
                            {
                                var class_member = cm as ClassDeclarationSyntax;
                                if (class_member == null)
                                {
                                    continue;
                                }
                                var bls = class_member.BaseList;
                                if (bls == null)
                                {
                                    continue;
                                }
                                var   types = bls.Types;
                                Regex reg   = new Regex("[<].+[>]");
                                foreach (var type in types)
                                {
                                    var s = type.ToString();
                                    s = reg.Replace(s, "");
                                    if (s.ToString() == listener_baseclass_name)
                                    {
                                        // Found the right class.
                                        found_class.Add(class_member);
                                        throw new Exception();
                                    }
                                }
                            }
                        }
                    }
                }
                catch
                {
                }

                if (found_class.Count == 0)
                {
                    if (!global::Options.POptions.GetBoolean("GenerateVisitorListener"))
                    {
                        return;
                    }

                    // Look in grammar directory for any C# files.
                    string name_space = null;
                    string ffn        = Path.GetFullPath(g4_file_path);
                    ffn = Path.GetDirectoryName(ffn);
                    foreach (var i in DteExtensions.SolutionFiles(application))
                    {
                        string file_name = i.Name;
                        if (file_name != null)
                        {
                            string prefix = file_name.TrimSuffix(".cs");
                            if (prefix == file_name)
                            {
                                continue;
                            }
                            try
                            {
                                object prop  = i.Properties.Item("FullPath").Value;
                                string ffncs = (string)prop;
                                // Look for namespace.
                                var t = trees[ffncs];
                                if (t == null)
                                {
                                    continue;
                                }
                                var root = t.GetCompilationUnitRoot();
                                foreach (var nm in root.Members)
                                {
                                    var namespace_member = nm as NamespaceDeclarationSyntax;
                                    if (namespace_member == null)
                                    {
                                        continue;
                                    }
                                    name_space = namespace_member.Name.ToString();
                                    break;
                                }
                            }
                            catch (Exception)
                            {
                            }
                        }
                    }
                    if (name_space == null)
                    {
                        name_space = "Generated";
                    }

                    // Create class.
                    string clazz = visitor ? $@"
using System;
using System.Collections.Generic;
using System.Text;

namespace {name_space}
{{
    class {listener_class_name}<Result> : {listener_baseclass_name}<Result>
    {{
        //public override Result VisitA([NotNull] A3Parser.AContext context)
        //{{
        //  return VisitChildren(context);
        //}}
    }}
}}
"
                    : $@"
using System;
using System.Collections.Generic;
using System.Text;

namespace {name_space}
{{
    class {listener_class_name} : {listener_baseclass_name}
    {{
        //public override void EnterA(A3Parser.AContext context)
        //{{
        //    base.EnterA(context);
        //}}
        //public override void ExitA(A3Parser.AContext context)
        //{{
        //    base.ExitA(context);
        //}}
    }}
}}
";

                    class_file_path = ffn + Path.DirectorySeparatorChar + listener_class_name + ".cs";
                    System.IO.File.WriteAllText(class_file_path, clazz);
                    var    item   = ProjectHelpers.GetSelectedItem();
                    string folder = FindFolder(item);
                    if (string.IsNullOrEmpty(folder) || !Directory.Exists(folder))
                    {
                        return;
                    }
                    var file         = new FileInfo(class_file_path);
                    var selectedItem = Workspaces.Workspace.Instance.FindDocument(class_file_path);
                    if (selectedItem == null)
                    {
                        //var selectedProject = item as Project;
                        //Project project = selectedItem?.ContainingProject ?? selectedProject ?? null;
                        //var projectItem = project.AddFileToProject(file);
                    }
                    // Redo parse.
                    try
                    {
                        StreamReader sr   = new StreamReader(class_file_path);
                        string       code = sr.ReadToEnd();
                        SyntaxTree   tree = CSharpSyntaxTree.ParseText(code);
                        trees[class_file_path] = tree;
                    }
                    catch (Exception)
                    {
                    }
                    // Redo find class.
                    try
                    {
                        var tree = trees[class_file_path];
                        var save = class_file_path;
                        class_file_path = null;
                        // Look for IParseTreeListener or IParseTreeVisitor classes.
                        var root = (CompilationUnitSyntax)tree.GetRoot();
                        foreach (var nm in root.Members)
                        {
                            var namespace_member = nm as NamespaceDeclarationSyntax;
                            if (namespace_member == null)
                            {
                                continue;
                            }
                            foreach (var cm in namespace_member.Members)
                            {
                                var class_member = cm as ClassDeclarationSyntax;
                                if (class_member == null)
                                {
                                    continue;
                                }
                                var bls = class_member.BaseList;
                                if (bls == null)
                                {
                                    continue;
                                }
                                var   types = bls.Types;
                                Regex reg   = new Regex("[<].+[>]");
                                foreach (var type in types)
                                {
                                    var s = type.ToString();
                                    s = reg.Replace(s, "");
                                    if (s.ToString() == listener_baseclass_name)
                                    {
                                        // Found the right class.
                                        found_class.Add(class_member);
                                        throw new Exception();
                                    }
                                }
                            }
                        }
                    }
                    catch
                    {
                    }
                }

                // Look for enter or exit method for symbol.
                MethodDeclarationSyntax found_member = null;
                var ctl = CtrlKeyState.GetStateForView(grammar_view).Enabled;
                var capitalized_member_name = "";
                if (visitor)
                {
                    capitalized_member_name = "Visit" + capitalized_symbol_name;
                }
                else if (ctl)
                {
                    capitalized_member_name = "Exit" + capitalized_symbol_name;
                }
                else
                {
                    capitalized_member_name = "Enter" + capitalized_symbol_name;
                }
                var capitalized_grammar_name = Capitalized(grammar_name);
                try
                {
                    foreach (var fc in found_class)
                    {
                        foreach (var me in fc.Members)
                        {
                            var method_member = me as MethodDeclarationSyntax;
                            if (method_member == null)
                            {
                                continue;
                            }
                            if (method_member.Identifier.ValueText.ToLower() == capitalized_member_name.ToLower())
                            {
                                found_member = method_member;
                                throw new Exception();
                            }
                        }
                    }
                }
                catch
                {
                }
                if (found_member == null)
                {
                    if (!global::Options.POptions.GetBoolean("GenerateVisitorListener"))
                    {
                        return;
                    }

                    // Find point for edit.
                    var fc   = found_class.First();
                    var here = fc.OpenBraceToken;
                    var spn  = here.FullSpan;
                    var end  = spn.End;

                    IVsTextView vstv = IVsTextViewExtensions.FindTextViewFor(class_file_path);
                    if (vstv == null)
                    {
                        IVsTextViewExtensions.ShowFrame(class_file_path);
                        vstv = IVsTextViewExtensions.FindTextViewFor(class_file_path);
                    }
                    IWpfTextView wpftv = vstv.GetIWpfTextView();
                    if (wpftv == null)
                    {
                        return;
                    }
                    ITextSnapshot cc = wpftv.TextBuffer.CurrentSnapshot;

                    var res = vstv.GetBuffer(out IVsTextLines ppBuffer);

                    var nss      = new SnapshotSpan(cc, spn.End + 1, 0);
                    var txt_span = nss.Span;

                    int line_number;
                    int colum_number;
                    vstv.GetLineAndColumn(txt_span.Start, out line_number, out colum_number);
                    res = ppBuffer.CreateEditPoint(line_number, colum_number, out object ppEditPoint);
                    EditPoint editPoint = ppEditPoint as EditPoint;
                    // Create class.
                    string member = visitor ? $@"
public override Result {capitalized_member_name}([NotNull] {capitalized_grammar_name}Parser.{capitalized_symbol_name}Context context)
{{
    return VisitChildren(context);
}}
"
                        : $@"
public override void {capitalized_member_name}({capitalized_grammar_name}Parser.{capitalized_symbol_name}Context context)
{{
    base.{capitalized_member_name}(context);
}}
";
                    editPoint.Insert(member);
                    // Redo parse.
                    try
                    {
                        vstv = IVsTextViewExtensions.FindTextViewFor(class_file_path);
                        if (vstv == null)
                        {
                            IVsTextViewExtensions.ShowFrame(class_file_path);
                            vstv = IVsTextViewExtensions.FindTextViewFor(class_file_path);
                        }
                        var        text_buffer = vstv.GetITextBuffer();
                        var        code        = text_buffer.GetBufferText();
                        SyntaxTree tree        = CSharpSyntaxTree.ParseText(code);
                        trees[class_file_path] = tree;
                    }
                    catch (Exception)
                    {
                    }
                    // Redo find class.
                    try
                    {
                        var tree = trees[class_file_path];
                        var save = class_file_path;
                        class_file_path = null;
                        // Look for IParseTreeListener or IParseTreeVisitor classes.
                        var root = (CompilationUnitSyntax)tree.GetRoot();
                        foreach (var nm in root.Members)
                        {
                            var namespace_member = nm as NamespaceDeclarationSyntax;
                            if (namespace_member == null)
                            {
                                continue;
                            }
                            foreach (var cm in namespace_member.Members)
                            {
                                var class_member = cm as ClassDeclarationSyntax;
                                if (class_member == null)
                                {
                                    continue;
                                }
                                var bls = class_member.BaseList;
                                if (bls == null)
                                {
                                    continue;
                                }
                                var   types = bls.Types;
                                Regex reg   = new Regex("[<].+[>]");
                                foreach (var type in types)
                                {
                                    var s = type.ToString();
                                    s = reg.Replace(s, "");
                                    if (s.ToString() == listener_baseclass_name)
                                    {
                                        // Found the right class.
                                        found_class.Add(class_member);
                                        class_file_path = save;
                                        throw new Exception();
                                    }
                                }
                            }
                        }
                    }
                    catch
                    {
                    }
                    try
                    {
                        foreach (var fcc in found_class)
                        {
                            foreach (var me in fcc.Members)
                            {
                                var method_member = me as MethodDeclarationSyntax;
                                if (method_member == null)
                                {
                                    continue;
                                }
                                if (method_member.Identifier.ValueText.ToLower() == capitalized_member_name.ToLower())
                                {
                                    found_member = method_member;
                                    throw new Exception();
                                }
                            }
                        }
                    }
                    catch
                    {
                    }
                }

                {
                    // Open to this line in editor.
                    IVsTextView vstv = IVsTextViewExtensions.FindTextViewFor(class_file_path);
                    {
                        IVsTextViewExtensions.ShowFrame(class_file_path);
                        vstv = IVsTextViewExtensions.FindTextViewFor(class_file_path);
                    }

                    IWpfTextView wpftv = vstv.GetIWpfTextView();
                    if (wpftv == null)
                    {
                        return;
                    }

                    int line_number;
                    int colum_number;
                    var txt_span = found_member.Identifier.Span;
                    vstv.GetLineAndColumn(txt_span.Start, out line_number, out colum_number);

                    // Create new span in the appropriate view.
                    ITextSnapshot cc = wpftv.TextBuffer.CurrentSnapshot;
                    SnapshotSpan  ss = new SnapshotSpan(cc, txt_span.Start, txt_span.Length);
                    SnapshotPoint sp = ss.Start;
                    // Put cursor on symbol.
                    wpftv.Caret.MoveTo(sp); // This sets cursor, bot does not center.
                                            // Center on cursor.
                                            //wpftv.Caret.EnsureVisible(); // This works, sort of. It moves the scroll bar, but it does not CENTER! Does not really work!
                    if (line_number > 0)
                    {
                        vstv.CenterLines(line_number - 1, 2);
                    }
                    else
                    {
                        vstv.CenterLines(line_number, 1);
                    }
                    return;
                }
            }
            catch (Exception exception)
            {
                Logger.Log.Notify(exception.StackTrace);
            }
        }
Esempio n. 11
0
        private void MenuItemCallback(object sender, EventArgs e)
        {
            ////////////////////////
            // Find all references..
            ////////////////////////

            // First, open up every .g4 file in project and parse.
            DTE application = DteExtensions.GetApplication();

            if (application != null)
            {
                IEnumerable <ProjectItem> iterator = DteExtensions.SolutionFiles(application);
                ProjectItem[]             list     = iterator.ToArray();
                foreach (var item in list)
                {
                    //var doc = item.Document; CRASHES!!!! DO NOT USE!
                    //var props = item.Properties;
                    string file_name = item.Name;
                    if (file_name != null)
                    {
                        string prefix = file_name.TrimSuffix(".g4");
                        if (prefix == file_name)
                        {
                            continue;
                        }

                        try
                        {
                            object prop = item.Properties.Item("FullPath").Value;
                            string ffn  = (string)prop;
                            if (!ParserDetails._per_file_parser_details.ContainsKey(ffn))
                            {
                                StreamReader  sr  = new StreamReader(ffn);
                                ParserDetails foo = new ParserDetails();
                                ParserDetails._per_file_parser_details[ffn] = foo;
                                foo.Parse(sr.ReadToEnd(), ffn);
                            }
                        }
                        catch (Exception eeks)
                        { }
                    }
                }
            }

            string       classification = this.Classification;
            SnapshotSpan span           = this.Symbol;
            ITextView    view           = this.View;

            // First, find out what this view is, and what the file is.
            ITextBuffer   buffer = view.TextBuffer;
            ITextDocument doc    = buffer.GetTextDocument();
            string        path   = doc.FilePath;

            List <IToken> where = new List <IToken>();
            List <ParserDetails> where_details = new List <ParserDetails>();
            IToken token = null;

            foreach (var kvp in ParserDetails._per_file_parser_details)
            {
                string        file_name = kvp.Key;
                ParserDetails details   = kvp.Value;
                if (classification == AntlrVSIX.Constants.ClassificationNameNonterminal)
                {
                    var it = details._ant_nonterminals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
                else if (classification == AntlrVSIX.Constants.ClassificationNameTerminal)
                {
                    var it = details._ant_terminals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
                else if (classification == AntlrVSIX.Constants.ClassificationNameLiteral)
                {
                    var it = details._ant_literals.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
            }
            if (!where.Any())
            {
                return;
            }

            // Populate the Antlr find results model/window with file/line/col info
            // for each occurrence.
            FindAntlrSymbolsModel.Instance.Results.Clear();
            for (int i = 0; i < where.Count; ++i)
            {
                IToken        x = where[i];
                ParserDetails y = where_details[i];
                var           w = new Entry()
                {
                    FileName = y.full_file_name, LineNumber = x.Line, ColumnNumber = x.Column, Token = x
                };
                FindAntlrSymbolsModel.Instance.Results.Add(w);
            }
        }
        private void MenuItemCallback(object sender, EventArgs e)
        {
            ////////////////////////
            // Go to definition....
            ////////////////////////

            // First, open up every .g4 file in project.
            // Get VS solution, if any, and parse all grammars
            DTE application = DteExtensions.GetApplication();

            if (application != null)
            {
                IEnumerable <ProjectItem> iterator = DteExtensions.SolutionFiles(application);
                ProjectItem[]             list     = iterator.ToArray();
                foreach (var item in list)
                {
                    //var doc = item.Document; CRASHES!!!! DO NOT USE!
                    //var props = item.Properties;
                    string file_name = item.Name;
                    if (file_name != null)
                    {
                        string prefix = file_name.TrimSuffix(".g4");
                        if (prefix == file_name)
                        {
                            continue;
                        }

                        try
                        {
                            object prop = item.Properties.Item("FullPath").Value;
                            string ffn  = (string)prop;
                            if (!ParserDetails._per_file_parser_details.ContainsKey(ffn))
                            {
                                StreamReader  sr  = new StreamReader(ffn);
                                ParserDetails foo = new ParserDetails();
                                ParserDetails._per_file_parser_details[ffn] = foo;
                                foo.Parse(sr.ReadToEnd(), ffn);
                            }
                        } catch (Exception eeks)
                        { }
                    }
                }
            }

            string       classification = this.Classification;
            SnapshotSpan span           = this.Symbol;
            ITextView    view           = this.View;

            // First, find out what this view is, and what the file is.
            ITextBuffer   buffer = view.TextBuffer;
            ITextDocument doc    = buffer.GetTextDocument();
            string        path   = doc.FilePath;

            //ParserDetails details = null;
            //bool found = ParserDetails._per_file_parser_details.TryGetValue(path, out details);
            //if (!found) return;

            List <IToken> where = new List <IToken>();
            List <ParserDetails> where_details = new List <ParserDetails>();
            IToken token = null;

            foreach (var kvp in ParserDetails._per_file_parser_details)
            {
                string        file_name = kvp.Key;
                ParserDetails details   = kvp.Value;
                if (classification == AntlrVSIX.Constants.ClassificationNameNonterminal)
                {
                    var it = details._ant_nonterminals_defining.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
                else if (classification == AntlrVSIX.Constants.ClassificationNameTerminal)
                {
                    var it = details._ant_terminals_defining.Where(
                        (t) => t.Text == span.GetText());
                    where.AddRange(it);
                    foreach (var i in it)
                    {
                        where_details.Add(details);
                    }
                }
            }
            if (where.Any())
            {
                token = where.First();
            }
            else
            {
                return;
            }
            ParserDetails where_token = where_details.First();

            string      full_file_name = where_token.full_file_name;
            IVsTextView vstv           = IVsTextViewExtensions.GetIVsTextView(full_file_name);

            IVsTextViewExtensions.ShowFrame(full_file_name);
            vstv = IVsTextViewExtensions.GetIVsTextView(where_token.full_file_name);

            IWpfTextView wpftv = vstv.GetIWpfTextView();

            if (wpftv == null)
            {
                return;
            }

            int line_number;
            int colum_number;

            vstv.GetLineAndColumn(token.StartIndex, out line_number, out colum_number);

            // Create new span in the appropriate view.
            ITextSnapshot cc = wpftv.TextBuffer.CurrentSnapshot;
            SnapshotSpan  ss = new SnapshotSpan(cc, token.StartIndex, 1);
            SnapshotPoint sp = ss.Start;

            // Put cursor on symbol.
            wpftv.Caret.MoveTo(sp);     // This sets cursor, bot does not center.
            // Center on cursor.
            //wpftv.Caret.EnsureVisible(); // This works, sort of. It moves the scroll bar, but it does not CENTER! Does not really work!
            if (line_number > 0)
            {
                vstv.CenterLines(line_number - 1, 2);
            }
            else
            {
                vstv.CenterLines(line_number, 1);
            }
        }