/// <summary> /// The meat of the recompute engine, updating hit test and the /// cached frames. /// </summary> private void ThreadUnsafeRunFrames(int start, int count) { var steps = new frameinfo[count]; var collisionlist = new List <LinkedList <int> >(count); frameinfo current = _frames[start - 1]; int framecount = _frames.Count; var bones = _track.Bones; using (changesync.AcquireWrite()) { // we use the savedcells buffer exactly so runframes can // be completely consistent with the track state at the // time of running // we could also get a lock on the track grid, but that would // block user input on the track until we finish running. _savedcells.Clear(); } using (var sync = changesync.AcquireRead()) { _hittest.MarkFirstInvalid(start); for (int i = 0; i < count; i++) { int currentframe = start + i; var collisions = new LinkedList <int>(); var oldtrigid = current.TriggerLineID; var zoom = current.Rider = current.Rider.Simulate( _savedcells, bones, ref current.TriggerLineID, collisions, frameid: currentframe); if (current.TriggerLineID != oldtrigid) { current.TriggerHitFrame = currentframe; } if (current.TriggerLineID != -1) { var std = (StandardLine)_track.LineLookup[current.TriggerLineID]; Debug.Assert(std.Trigger != null, "Trigger line proc on line with no trigger"); var delta = currentframe - current.TriggerHitFrame; if (!std.Trigger.Activate(delta, ref current.Zoom)) { current.TriggerLineID = -1; current.TriggerHitFrame = -1; } } steps[i] = current; collisionlist.Add(collisions); // 10 seconds of frames, // couldnt hurt to check? if ((i + 1) % 400 == 0) { sync.ReleaseWaiting(); } } _hittest.AddFrames(collisionlist); } if (start + count > framecount) { _frames.EnsureCapacity(start + count); _frames.UnsafeSetCount(start + count); } for (int i = 0; i < steps.Length; i++) { _frames.unsafe_array[start + i] = steps[i]; } FrameInvalidated?.Invoke(this, start); }
/// <summary> /// The meat of the recompute engine, updating hit test and the /// cached frames. /// </summary> public void ThreadUnsafeRunFrames(int start, int count) { var steps = new frameinfo[count]; var collisionlist = new List <LinkedList <int> >(count); frameinfo current = _frames[start - 1]; int framecount = _frames.Count; var bones = _track.Bones; using (changesync.AcquireWrite()) { // we use the savedcells buffer exactly so runframes can // be completely consistent with the track state at the // time of running // we could also get a lock on the track grid, but that would // block user input on the track until we finish running. _savedcells.Clear(); } using (var sync = changesync.AcquireRead()) { _hittest.MarkFirstInvalid(start); GameTrigger[] triggers = new GameTrigger[GameTrigger.TriggerTypes]; for (int i = 0; i < count; i++) { int currentframe = start + i; var collisions = new LinkedList <int>(); current.Rider = current.Rider.Simulate( _savedcells, bones, collisions, frameid: currentframe); if (GetTriggersForFrame(triggers, currentframe)) { var zoomtrigger = triggers[(int)TriggerType.Zoom]; if (zoomtrigger != null) { var delta = currentframe - zoomtrigger.Start; zoomtrigger.ActivateZoom(delta, ref current.Zoom); } var bgtrigger = triggers[(int)TriggerType.BGChange]; if (bgtrigger != null) { var delta = currentframe - bgtrigger.Start; Constants.StaticTriggerBGColor = _frames[start - 1].BGColor; bgtrigger.ActivateBG(delta, currentframe, ref Constants.StaticTriggerBGColor, ref Constants.TriggerBGColor, ref current.BGColor); } var linetrigger = triggers[(int)TriggerType.LineColor]; if (linetrigger != null) { var delta = currentframe - linetrigger.Start; Constants.StaticTriggerLineColorChange = _frames[start - 1].LineColor; linetrigger.ActivateLine(delta, ref Constants.StaticTriggerLineColorChange, ref Constants.TriggerLineColorChange, currentframe, ref current.LineColor); } } steps[i] = current; collisionlist.Add(collisions); // 10 seconds of frames, // couldnt hurt to check? if ((i + 1) % 400 == 0) { sync.ReleaseWaiting(); } } _hittest.AddFrames(collisionlist); } if (start + count > framecount) { _frames.EnsureCapacity(start + count); _frames.UnsafeSetCount(start + count); } for (int i = 0; i < steps.Length; i++) { _frames.unsafe_array[start + i] = steps[i]; } FrameInvalidated?.Invoke(this, start); }