internal IEnumerable<ISearchResult> Search(SearchQuery query, int offset, int length) { // Clear previous search results. _searchResults.Clear(); // Determine the start offset. int caretOffset = 0; if (query.IsRelative) { var textEditor = this.GetLastActiveTextEditor(); if (textEditor != null) caretOffset = textEditor.SelectionStart; // SelectionStart returns CaretOffsets if nothing is selected. } if (caretOffset < offset) caretOffset = offset; else if (caretOffset > offset + length) caretOffset = offset + length; // Perform search. var searchResults = GetSearchResults(query, offset, length); if (searchResults == null || searchResults.Count == 0) return Enumerable.Empty<ISearchResult>(); // Save search results in TextSegmentCollection. (The TextSegmentCollection will // automatically update the offsets of the search results when the document changes.) foreach (var searchResult in searchResults) _searchResults.Add(searchResult); // Order search results. (The search query determines the search direction. // The search results should start at the caret position.) if (query.SearchBackwards) { int numberOfSearchResults = searchResults.Count; int movedSearchResults = 0; for (int i = 0; i < numberOfSearchResults; i++) { var searchResult = searchResults[i]; if (searchResult.EndOffset < caretOffset) { searchResults.Add(searchResult); movedSearchResults++; } else { break; } } searchResults.RemoveRange(0, movedSearchResults); searchResults.Reverse(); } else { int numberOfSearchResults = searchResults.Count; int movedSearchResults = 0; for (int i = 0; i < numberOfSearchResults; i++) { var searchResult = searchResults[i]; if (searchResult.StartOffset < caretOffset) { searchResults.Add(searchResult); movedSearchResults++; } else { break; } } searchResults.RemoveRange(0, movedSearchResults); } return searchResults; }
private List<SearchResult> GetSearchResults(SearchQuery query, int offset, int length) { if (length == 0 || AvalonEditDocument.TextLength == 0) return null; // Use regular expression. var regex = query.AsRegex(); if (regex == null) return null; // Match regular expression. var matches = regex.Matches(AvalonEditDocument.Text); // Return the search results within the specified text segment. var searchResults = new List<SearchResult>(matches.Count); int endOffset = offset + length; foreach (Match match in matches) { if (offset <= match.Index && match.Index + match.Length <= endOffset) searchResults.Add(new SearchResult(this, match)); } return searchResults; }
IEnumerable<ISearchResult> ISearchable.Search(SearchQuery query) { return Search(query, 0, AvalonEditDocument.TextLength); }
/// <inheritdoc/> public IEnumerable<ISearchResult> Search(SearchQuery query) { return _document.Search(query, _offset, _length); }