/// <summary> /// Execute a search request that will fetch search results asynchronously. /// </summary> /// <param name="context">Search context used to track asynchronous request.</param> /// <param name="options">Options defining how the query will be performed</param> /// <returns>Asynchronous list of search items.</returns> public static ISearchList Request(SearchContext context, SearchFlags options = SearchFlags.None) { ISearchList results = null; if (!InternalEditorUtility.CurrentThreadIsMainThread()) { results = new ConcurrentSearchList(context); Dispatcher.Enqueue(() => { results.AddItems(GetItems(context, options)); (results as ConcurrentSearchList)?.GetItemsDone(); }); return(results); } if (options.HasAny(SearchFlags.Sorted)) { results = new SortedSearchList(context); } else { results = new AsyncSearchList(context); } results.AddItems(GetItems(context, options)); return(results); }
protected void CheckGetMainThreadContextCalledOnMainThread() { if (!InternalEditorUtility.CurrentThreadIsMainThread()) { throw new NotSupportedException("Deployment targets main thread context can only be retrieved from the main thread."); } }
public UnitySourceFileUpdatersResultHandler() : base(captureSynchronizationContext: true) { ConstentAPI = new UnityScriptUpdaterConsentAPI(); if (!InternalEditorUtility.CurrentThreadIsMainThread()) { throw new Exception($"{nameof(UnitySourceFileUpdatersResultHandler)} can only be created on the main thread"); } }
public static DebuggerTracer.EntityFrameTrace GetRecorder(int graphId, int targetIndex) { Assert.IsTrue(InternalEditorUtility.CurrentThreadIsMainThread()); // TODO cache graphdata/frametrace var frame = Time.frameCount; DebuggerTracer.GraphTrace graphTrace = DebuggerTracer.GetGraphData(graphId, true); var frameData = graphTrace.GetFrameData(frame, createIfAbsent: true); var entityData = frameData.GetEntityFrameTrace(targetIndex, createIfAbsent: true); return(entityData); }
public static IEnumerable <T> EvaluateMainThread <T>(Action <Action <T> > callback) { var concurrentList = new ConcurrentBag <T>(); var yielderHandle = new EventWaitHandle(false, EventResetMode.AutoReset); void ItemReceived(T item) { concurrentList.Add(item); yielderHandle.Set(); } if (!InternalEditorUtility.CurrentThreadIsMainThread()) { var finishedHandle = new EventWaitHandle(false, EventResetMode.AutoReset); Dispatcher.Enqueue(() => { callback(ItemReceived); finishedHandle.Set(); }); while (!finishedHandle.WaitOne(0)) { if (yielderHandle.WaitOne(0)) { while (concurrentList.TryTake(out var item)) { yield return(item); } } } finishedHandle.Dispose(); finishedHandle = null; } else { callback(ItemReceived); } yielderHandle.Dispose(); yielderHandle = null; while (concurrentList.Count > 0) { if (concurrentList.TryTake(out var item)) { yield return(item); } } }
public static T EvaluateMainThread <T>(Func <T> callback) { if (InternalEditorUtility.CurrentThreadIsMainThread()) { return(callback()); } using (var waitHandle = new EventWaitHandle(false, EventResetMode.AutoReset)) { T result = default; Dispatcher.Enqueue(() => { result = callback(); waitHandle.Set(); }); waitHandle.WaitOne(); return(result); } }
public static IEnumerable <T> EvaluateMainThreadUnroll <T>(Func <IEnumerable <T> > callback) { if (InternalEditorUtility.CurrentThreadIsMainThread()) { return(callback()); } MainThreadIEnumerableHandler <T> enumerableHandler = new MainThreadIEnumerableHandler <T>(); Dispatcher.Enqueue(() => { var enumerable = callback(); enumerableHandler.Reset(enumerable); enumerableHandler.Start(); }); enumerableHandler.startEvent.WaitOne(); enumerableHandler.stopEvent.WaitOne(); return(enumerableHandler.results); }
public static IEnumerable <T> EvaluateMainThread <T>(IEnumerable <T> set, Func <T, T> callback, int minBatchSize = 50) where T : class { if (InternalEditorUtility.CurrentThreadIsMainThread()) { foreach (var r in set) { if (r == null) { yield return(null); continue; } yield return(callback(r)); } yield break; } var items = new ConcurrentBag <T>(); var results = new ConcurrentBag <T>(); var resultSignal = new EventWaitHandle(false, EventResetMode.AutoReset); void ProcessBatch(int batchCount, EventWaitHandle finishedSignal) { var processedItemCount = 0; while (items.TryTake(out var item)) { var result = callback(item); if (result != null) { results.Add(result); resultSignal.Set(); } if (batchCount != -1 && processedItemCount++ >= batchCount) { break; } } finishedSignal.Set(); } EventWaitHandle batchFinishedSignal = null; foreach (var r in set) { if (r == null) { yield return(null); continue; } items.Add(r); if (batchFinishedSignal == null || batchFinishedSignal.WaitOne(0)) { if (batchFinishedSignal == null) { batchFinishedSignal = new EventWaitHandle(false, EventResetMode.AutoReset); } Dispatcher.Enqueue(() => ProcessBatch(minBatchSize, batchFinishedSignal)); } if (resultSignal.WaitOne(0)) { while (results.TryTake(out var item)) { yield return(item); } } } var finalBatch = new EventWaitHandle(false, EventResetMode.ManualReset); Dispatcher.Enqueue(() => ProcessBatch(-1, finalBatch)); while (!finalBatch.WaitOne(1) || results.Count > 0) { while (results.TryTake(out var item)) { yield return(item); } } batchFinishedSignal?.Dispose(); batchFinishedSignal = null; finalBatch.Dispose(); finalBatch = null; resultSignal.Dispose(); resultSignal = null; }
public static IEnumerable <T> EvaluateMainThread <T>(IEnumerable <T> set, Func <T, T> callback, int minBatchSize = 10) where T : class { if (InternalEditorUtility.CurrentThreadIsMainThread()) { foreach (var r in set) { if (r == null) { yield return(null); continue; } yield return(callback(r)); } yield break; } var items = new ConcurrentBag <T>(); var results = new ConcurrentBag <T>(); var resultSignal = new EventWaitHandle(false, EventResetMode.AutoReset); var batchFinishedSignal = new EventWaitHandle(true, EventResetMode.AutoReset); void ProcessBatch() { while (!items.IsEmpty) { if (!items.TryTake(out var item)) { break; } var result = callback(item); if (result != null) { results.Add(result); resultSignal.Set(); } } batchFinishedSignal.Set(); } int initialBatchSize = minBatchSize; foreach (var r in set) { if (r == null) { yield return(null); continue; } items.Add(r); if (--initialBatchSize < 0 && batchFinishedSignal.WaitOne(0)) { Dispatcher.Enqueue(ProcessBatch); initialBatchSize = minBatchSize; } if (resultSignal.WaitOne(0)) { while (results.TryTake(out var item)) { yield return(item); } } } batchFinishedSignal.Reset(); Dispatcher.Enqueue(ProcessBatch); while (!batchFinishedSignal.WaitOne(0)) { if (resultSignal.WaitOne(0)) { while (results.TryTake(out var item)) { yield return(item); } } } while (results.TryTake(out var item)) { yield return(item); } }