예제 #1
0
        /// <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);
        }
예제 #2
0
 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");
            }
        }
예제 #4
0
    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);
            }
        }