您最多选择25个主题 主题必须以中文或者字母或数字开头,可以包含连字符 (-),并且长度不得超过35个字符
 
 
 
 
 
 

148 行
5.3 KiB

using System;
using System.Runtime.InteropServices;
using AOT;
using Unity.UIWidgets.ui;
using UnityEngine;
namespace Unity.UIWidgets.async {
class _AsyncCallbackEntry {
public readonly ZoneCallback callback;
public _AsyncCallbackEntry next;
internal _AsyncCallbackEntry(ZoneCallback callback) {
this.callback = callback;
}
}
class _AsyncCallbackState {
internal _AsyncCallbackEntry _nextCallback;
internal _AsyncCallbackEntry _lastCallback;
internal _AsyncCallbackEntry _lastPriorityCallback;
internal bool _isInCallbackLoop;
}
public static partial class async_ {
static _AsyncCallbackState _getState()
{
return Window.instance._asyncCallbackState ??
(Window.instance._asyncCallbackState = new _AsyncCallbackState());
}
static void _microtaskLoop() {
var state = _getState();
while (state._nextCallback != null) {
state._lastPriorityCallback = null;
_AsyncCallbackEntry entry = state._nextCallback;
state._nextCallback = entry.next;
if (state._nextCallback == null) state._lastCallback = null;
entry.callback();
}
}
static object _startMicrotaskLoop() {
var state = _getState();
state._isInCallbackLoop = true;
try {
// Moved to separate function because try-finally prevents
// good optimization.
_microtaskLoop();
}
finally {
state._lastPriorityCallback = null;
state._isInCallbackLoop = false;
if (state._nextCallback != null) {
_AsyncRun._scheduleImmediate(_startMicrotaskLoop);
}
}
return null;
}
static void _scheduleAsyncCallback(ZoneCallback callback) {
var state = _getState();
_AsyncCallbackEntry newEntry = new _AsyncCallbackEntry(callback);
if (state._nextCallback == null) {
state._nextCallback = state._lastCallback = newEntry;
if (!state._isInCallbackLoop) {
_AsyncRun._scheduleImmediate(_startMicrotaskLoop);
}
}
else {
state._lastCallback.next = newEntry;
state._lastCallback = newEntry;
}
}
static void _schedulePriorityAsyncCallback(ZoneCallback callback) {
var state = _getState();
if (state._nextCallback == null) {
_scheduleAsyncCallback(callback);
state._lastPriorityCallback = state._lastCallback;
return;
}
_AsyncCallbackEntry entry = new _AsyncCallbackEntry(callback);
if (state._lastPriorityCallback == null) {
entry.next = state._nextCallback;
state._nextCallback = state._lastPriorityCallback = entry;
}
else {
entry.next = state._lastPriorityCallback.next;
state._lastPriorityCallback.next = entry;
state._lastPriorityCallback = entry;
if (entry.next == null) {
state._lastCallback = entry;
}
}
}
public static void scheduleMicrotask(ZoneCallback callback) {
_Zone currentZone = (_Zone) Zone.current;
if (ReferenceEquals(_rootZone, currentZone)) {
// No need to bind the callback. We know that the root's scheduleMicrotask
// will be invoked in the root zone.
_rootScheduleMicrotask(null, null, _rootZone, callback);
return;
}
_ZoneFunction<ScheduleMicrotaskHandler> implementation = currentZone._scheduleMicrotask;
if (ReferenceEquals(_rootZone, implementation.zone) &&
_rootZone.inSameErrorZone(currentZone)) {
_rootScheduleMicrotask(
null, null, currentZone, currentZone.registerCallback(callback));
return;
}
Zone.current.scheduleMicrotask(Zone.current.bindCallbackGuarded(callback));
}
}
class _AsyncRun {
internal static void _scheduleImmediate(ZoneCallback callback) {
Isolate.ensureExists();
GCHandle callabackHandle = GCHandle.Alloc(callback);
UIMonoState_scheduleMicrotask(_scheduleMicrotask, (IntPtr) callabackHandle);
}
[MonoPInvokeCallback(typeof(UIMonoState_scheduleMicrotaskCallback))]
static void _scheduleMicrotask(IntPtr callbackHandle) {
GCHandle handle = (GCHandle) callbackHandle;
var callback = (ZoneCallback) handle.Target;
handle.Free();
try {
callback();
}
catch (Exception ex) {
Debug.LogException(ex);
}
}
delegate void UIMonoState_scheduleMicrotaskCallback(IntPtr callbackHandle);
[DllImport(NativeBindings.dllName)]
static extern void UIMonoState_scheduleMicrotask(UIMonoState_scheduleMicrotaskCallback callback,
IntPtr callbackHandle);
}
}