public int[] BuildPitch(PitchInfo pitchInfo)
        {
            var    pitches = new List <int>();
            var    interv  = INTERVAL_TICK;
            var    i       = -1;
            double xl      = 0;   // x local
            var    dir     = -99; // up or down
            double y       = -99; // point value
            double xk      = -99; // sin width
            double yk      = -99; // sin height
            double C       = -99; // normalize to zero
            bool   IsNextPointTime;
            bool   IsLastPoint;
            int    nextX;
            int    thisX;

            for (var x = pitchInfo.Start; x <= pitchInfo.End; x += interv)
            {
                // only S shape is allowed
                nextX           = (int)pitchInfo.PitchPoints[i + 1].X;
                thisX           = x;
                IsNextPointTime = thisX < 0 ? thisX + interv >= nextX : thisX + interv >= nextX;
                IsLastPoint     = i + 2 == pitchInfo.PitchPoints.Length;
                while (IsNextPointTime && !IsLastPoint || i < 0)
                {
                    // goto next pitch points pair
                    i++;
                    xk              = pitchInfo.PitchPoints[i + 1].X - pitchInfo.PitchPoints[i].X;
                    yk              = pitchInfo.PitchPoints[i + 1].Y - pitchInfo.PitchPoints[i].Y;
                    dir             = pitchInfo.PitchPoints[i + 1].Y > pitchInfo.PitchPoints[i].Y ? 1 : -1;
                    dir             = pitchInfo.PitchPoints[i + 1].Y == pitchInfo.PitchPoints[i].Y ? 0 : dir;
                    C               = pitchInfo.PitchPoints[i + 1].Y;
                    xl              = 0;
                    nextX           = (int)(pitchInfo.PitchPoints[i + 1].X / interv - 0.5 * IntervalMs);
                    nextX          -= (int)(nextX % IntervalMs);
                    thisX           = (int)Math.Ceiling((double)x / interv);
                    IsNextPointTime = thisX >= nextX;
                    IsLastPoint     = i + 2 == pitchInfo.PitchPoints.Length;
                }

                if (dir == -99)
                {
                    throw new Exception();
                }
                yk = Math.Round(yk, 3);
                var X = Math.Abs(xk) < 5 ? 0 : 1 / xk * 10 * xl / Math.PI;
                y  = -yk * (0.5 * Math.Cos(X) + 0.5) + C;
                y *= 10;
                pitches.Add((int)Math.Round(y));
                xl += interv;
            }

            //if (i < pitchInfo.PitchPoints.Length - 2)
            //    throw new Exception("Some points was not processed");
            return(pitches.ToArray());
        }
示例#2
0
 public SimulationStep()
 {
     Pitch        = new PitchInfo();
     Control      = new ControlInfo();
     Coordinates  = new CoordinatesInfo();
     Velocity     = new VelocityInfo();
     Acceleration = new AccelerationInfo();
     Atmosphere   = new AtmosphereInfo();
     Aerodynamics = new AerodynamicsInfo();
     Control      = new ControlInfo();
 }
        public PitchInfo BuildPitchInfo(RenderNote note, RenderNote prevNote, RenderNote nextNote)
        {
            var pitchInfo       = new PitchInfo();
            var autoPitchLength = 40;
            var autoPitchOffset = -20;
            var firstNoteRaise  = 10;

            var oto = note.Oto;
            var pps = new List <PitchPoint>();

            foreach (var pp in note.PitchBend.Points)
            {
                pps.Add(pp);
            }
            if (pps.Count == 0)
            {
                var offsetY = prevNote == null ? firstNoteRaise : GetPitchDiff(note.NoteNum, prevNote.NoteNum);
                pps.Add(new PitchPoint(MusicMath.Current.TickToMillisecond(autoPitchOffset, Tempo), -offsetY));
                pps.Add(new PitchPoint(MusicMath.Current.TickToMillisecond(autoPitchOffset + autoPitchLength, Tempo), 0));
                note.PitchBend.Data = pps;
            }

            var cutoffFromNext = nextNote != null ? nextNote.Oto.StraightPreutterance : 0;

            // end and start ms
            var    startMs = pps.First().X < -oto.Preutterance ? pps.First().X : -oto.Preutterance;
            double endMs   = MusicMath.Current.TickToMillisecond(note.FinalLength, Tempo) - cutoffFromNext;

            // if not all the length involved, add end and/or start pitch points
            if (pps.First().X > startMs)
            {
                pps.Insert(0, new PitchPoint(startMs, pps.First().Y));
            }
            if (pps.Last().X < endMs)
            {
                pps.Add(new PitchPoint(endMs, pps.Last().Y));
            }

            var start = (int)MusicMath.Current.SnapMs(pps.First().X, Tempo);
            var end   = (int)MusicMath.Current.SnapMs(pps.Last().X, Tempo);

            // combine all
            pitchInfo.Start       = start;
            pitchInfo.End         = end;
            pitchInfo.PitchPoints = pps.ToArray();
            return(pitchInfo);
        }