UnityGame/Library/PackageCache/com.unity.searcher/Editor/Searcher/Searcher.cs

109 lines
3.7 KiB
C#
Raw Permalink Normal View History

2024-10-27 10:53:47 +03:00
using System;
using System.Collections.Generic;
using System.Linq;
using JetBrains.Annotations;
namespace UnityEditor.Searcher
{
[PublicAPI]
public class Searcher
{
public ISearcherAdapter Adapter { get; }
public Comparison<SearcherItem> SortComparison { get; set; }
readonly List<SearcherDatabaseBase> m_Databases;
public Searcher(SearcherDatabaseBase database, string title)
: this(new List<SearcherDatabaseBase> { database }, title, null)
{ }
public Searcher(IEnumerable<SearcherDatabaseBase> databases, string title)
: this(databases, title, null)
{ }
public Searcher(SearcherDatabaseBase database, ISearcherAdapter adapter = null)
: this(new List<SearcherDatabaseBase> { database }, adapter)
{ }
public Searcher(IEnumerable<SearcherDatabaseBase> databases, ISearcherAdapter adapter = null)
: this(databases, string.Empty, adapter)
{ }
Searcher(IEnumerable<SearcherDatabaseBase> databases, string title, ISearcherAdapter adapter)
{
m_Databases = new List<SearcherDatabaseBase>();
var databaseId = 0;
foreach (var database in databases)
{
// This is needed for sorting items between databases.
database.OverwriteId(databaseId);
databaseId++;
m_Databases.Add(database);
}
Adapter = adapter ?? new SearcherAdapter(title);
}
public void BuildIndices()
{
foreach (var database in m_Databases)
{
database.BuildIndex();
}
}
public IEnumerable<SearcherItem> Search(string query)
{
query = query.ToLower();
var results = new List<SearcherItem>();
float maxScore = 0;
foreach (var database in m_Databases)
{
var localResults = database.Search(query, out var localMaxScore);
if (localMaxScore > maxScore)
{
// skip the highest scored item in the local results and
// insert it back as the first item. The first item should always be
// the highest scored item. The order of the other items does not matter
// because they will be reordered to recreate the tree properly.
if (results.Count > 0)
{
// backup previous best result
results.Add(results[0]);
// replace it with the new best result
results[0] = localResults[0];
// add remaining results at the end
results.AddRange(localResults.Skip(1));
}
else // best result will be the first item
results.AddRange(localResults);
maxScore = localMaxScore;
}
else // no new best result just append everything
{
results.AddRange(localResults);
}
}
return results;
}
[PublicAPI]
public class AnalyticsEvent
{
[PublicAPI]
public enum EventType{ Pending, Picked, Cancelled }
public readonly EventType eventType;
public readonly string currentSearchFieldText;
public AnalyticsEvent(EventType eventType, string currentSearchFieldText)
{
this.eventType = eventType;
this.currentSearchFieldText = currentSearchFieldText;
}
}
}
}