| 1 | using CascadeIDE.Services; |
| 2 | |
| 3 | namespace CascadeIDE.Features.Editor.Application.Monaco; |
| 4 | |
| 5 | public static class CideEditorCompletionMerger |
| 6 | { |
| 7 | public static IReadOnlyList<CideEditorCompletionItem> Merge( |
| 8 | IReadOnlyList<CideEditorCompletionItem> lspItems, |
| 9 | IReadOnlyList<CideEditorCompletionItem> roslynItems, |
| 10 | string prefix) |
| 11 | { |
| 12 | var filteredLsp = string.IsNullOrEmpty(prefix) |
| 13 | ? lspItems.ToList() |
| 14 | : Filter(lspItems, prefix); |
| 15 | if (filteredLsp.Count == 0 && lspItems.Count > 0) |
| 16 | filteredLsp = lspItems.ToList(); |
| 17 | |
| 18 | if (string.IsNullOrEmpty(prefix)) |
| 19 | return filteredLsp.Count > 0 ? filteredLsp : roslynItems; |
| 20 | |
| 21 | var seen = new HashSet<string>(filteredLsp.Select(i => i.Label), StringComparer.OrdinalIgnoreCase); |
| 22 | var merged = new List<CideEditorCompletionItem>(filteredLsp.Count + roslynItems.Count); |
| 23 | merged.AddRange(filteredLsp); |
| 24 | |
| 25 | foreach (var item in roslynItems |
| 26 | .Where(i => CSharpCompletionMatcher.Matches(i.Label, prefix)) |
| 27 | .Where(i => seen.Add(i.Label)) |
| 28 | .OrderBy(i => i.Label, Comparer<string>.Create((a, b) => |
| 29 | CSharpCompletionMatcher.CompareByRelevance(a, b, prefix)))) |
| 30 | { |
| 31 | merged.Add(item); |
| 32 | } |
| 33 | |
| 34 | return merged; |
| 35 | } |
| 36 | |
| 37 | public static IReadOnlyList<CideEditorCompletionItem> Filter( |
| 38 | IReadOnlyList<CideEditorCompletionItem> items, |
| 39 | string prefix) |
| 40 | { |
| 41 | if (string.IsNullOrEmpty(prefix)) |
| 42 | return items.ToList(); |
| 43 | |
| 44 | return items |
| 45 | .Where(i => CSharpCompletionMatcher.Matches(i.Label, prefix)) |
| 46 | .OrderBy(i => i.Label, Comparer<string>.Create((a, b) => |
| 47 | CSharpCompletionMatcher.CompareByRelevance(a, b, prefix))) |
| 48 | .ToList(); |
| 49 | } |
| 50 | } |
| 51 | |