|
|
c3ebff |
using System;
|
|
|
c3ebff |
using System.Collections.Generic;
|
|
|
c3ebff |
|
|
|
c3ebff |
namespace Assistance {
|
|
|
c3ebff |
public class InputModifierTangents: InputManager.Modifier {
|
|
|
c3ebff |
public class Modifier: Track.Modifier {
|
|
|
c3ebff |
public Modifier(Handler handler):
|
|
|
c3ebff |
base(handler) { }
|
|
|
c3ebff |
|
|
|
c3ebff |
public InputManager.KeyPoint.Holder holder = null;
|
|
|
c3ebff |
public readonly List<track.point> tangents = new List<track.point>();</track.point></track.point>
|
|
|
c3ebff |
|
|
|
c3ebff |
public override Track.WayPoint calcWayPoint(double originalIndex) {
|
|
|
c3ebff |
double frac;
|
|
|
c3ebff |
int i0 = original.floorIndex(originalIndex, out frac);
|
|
|
c3ebff |
int i1 = original.ceilIndex(originalIndex);
|
|
|
c3ebff |
Track.WayPoint p0 = original.getWayPoint(i0);
|
|
|
c3ebff |
Track.WayPoint p1 = original.getWayPoint(i1);
|
|
|
c3ebff |
p0.tangent = tangents[i0];
|
|
|
c3ebff |
p1.tangent = tangents[i1];
|
|
|
c3ebff |
return Track.interpolate(p0, p1, frac);
|
|
|
c3ebff |
}
|
|
|
c3ebff |
}
|
|
|
c3ebff |
|
|
|
c3ebff |
public override List<track> modify(Track track, InputManager.KeyPoint keyPoint, List<track> outTracks) {
|
|
|
c3ebff |
if (track.handler == null) {
|
|
|
c3ebff |
track.handler = new Track.Handler(this, track);
|
|
|
c3ebff |
track.handler.tracks.Add(new Track( new Modifier(track.handler) ));
|
|
|
c3ebff |
}
|
|
|
c3ebff |
|
|
|
c3ebff |
Track subTrack = track.handler.tracks[0];
|
|
|
c3ebff |
Modifier modifier = (Modifier)subTrack.modifier;
|
|
|
c3ebff |
outTracks.Add(subTrack);
|
|
|
c3ebff |
|
|
|
c3ebff |
if ( !track.isChanged
|
|
|
c3ebff |
&& track.points.Count == subTrack.points.Count
|
|
|
c3ebff |
&& track.points.Count == modifier.tangents.Count )
|
|
|
c3ebff |
return;
|
|
|
c3ebff |
|
|
|
c3ebff |
if (!track.isChanged && subTrack.points.Count == track.points.Count - 1) {
|
|
|
c3ebff |
// add temporary point
|
|
|
c3ebff |
modifier.tangents.Add(new Track.Point());
|
|
|
c3ebff |
subTrack.points.Add(track.getLast());
|
|
|
c3ebff |
++subTrack.wayPointsAdded;
|
|
|
c3ebff |
} else {
|
|
|
c3ebff |
// apply permanent changes
|
|
|
c3ebff |
|
|
|
c3ebff |
// remove points
|
|
|
c3ebff |
int start = track.points.Count - track.wayPointsAdded;
|
|
|
c3ebff |
if (start < 0) start = 0;
|
|
|
c3ebff |
if (start > 1) --start;
|
|
|
c3ebff |
if (subTrack.points.Count < start) {
|
|
|
c3ebff |
subTrack.points.RemoveRange(start, subTrack.points.Count - start);
|
|
|
c3ebff |
subTrack.wayPointsRemoved += subTrack.points.Count - start;
|
|
|
c3ebff |
}
|
|
|
c3ebff |
if (modifier.tangents.Count < start)
|
|
|
c3ebff |
modifier.tangents.RemoveRange(start, modifier.tangents.Count - start);
|
|
|
c3ebff |
|
|
|
c3ebff |
// add first point
|
|
|
c3ebff |
int index = start;
|
|
|
c3ebff |
if (index == 0) {
|
|
|
c3ebff |
modifier.tangents.Add(new Track.Point());
|
|
|
c3ebff |
subTrack.points.Add(track.getLast());
|
|
|
c3ebff |
++index;
|
|
|
c3ebff |
}
|
|
|
c3ebff |
|
|
|
c3ebff |
// add points with tangents
|
|
|
c3ebff |
if (track.points.Count > 2) {
|
|
|
c3ebff |
while(index < track.points.Count - 1) {
|
|
|
c3ebff |
Track.WayPoint p = track.points[index];
|
|
|
c3ebff |
double t0 = track.points[index-1].time;
|
|
|
c3ebff |
double t2 = track.points[index+1].time;
|
|
|
c3ebff |
double dt = t2 - t0;
|
|
|
c3ebff |
p.tangent = dt > Geometry.precision
|
|
|
c3ebff |
? (track.points[index+1].point - track.points[index-1].point)*(p.time - t0)/dt
|
|
|
c3ebff |
: new Track.Point();
|
|
|
c3ebff |
modifier.tangents.Add(p.tangent);
|
|
|
c3ebff |
subTrack.points.Add(p);
|
|
|
c3ebff |
++index;
|
|
|
c3ebff |
}
|
|
|
c3ebff |
}
|
|
|
c3ebff |
|
|
|
c3ebff |
track.wayPointsRemoved = 0;
|
|
|
c3ebff |
track.wayPointsAdded = 0;
|
|
|
c3ebff |
subTrack.wayPointsAdded += index - start;
|
|
|
c3ebff |
|
|
|
c3ebff |
// release previous key point
|
|
|
1d3aae |
if (modifier.holder) {
|
|
|
1d3aae |
modifier.holder.Dispose();
|
|
|
1d3aae |
modifier.holder = null;
|
|
|
1d3aae |
}
|
|
|
c3ebff |
|
|
|
c3ebff |
if (track.isFinished) {
|
|
|
c3ebff |
// finish
|
|
|
c3ebff |
modifier.tangents.Add(new Track.Point());
|
|
|
c3ebff |
subTrack.points.Add(track.getLast());
|
|
|
c3ebff |
++subTrack.wayPointsAdded;
|
|
|
c3ebff |
} else {
|
|
|
c3ebff |
// save key point
|
|
|
c3ebff |
modifier.holder = keyPoint.hold();
|
|
|
c3ebff |
}
|
|
|
c3ebff |
}
|
|
|
c3ebff |
}
|
|
|
c3ebff |
}
|
|
|
c3ebff |
}
|
|
|
c3ebff |
|