private double GetFadeLength(Track fromTrack, Track toTrack)
        {
            if (fromTrack == null && toTrack == null) return 0F;

            if (toTrack == null) return fromTrack.SamplesToSeconds(fromTrack.FullEndLoopLength);
            if (fromTrack == null) return BpmHelper.GetDefaultLoopLength(toTrack.StartBpm)/4D;

            var fadeInLength = toTrack.FullStartLoopLengthSeconds;
            if (fadeInLength == 0)
                fadeInLength = BpmHelper.GetDefaultLoopLength(toTrack.StartBpm);

            var fadeOutLength = GetExtendedFadeOutLength(fromTrack, toTrack);

            if (!HasExtendedMixAttributes(fromTrack, toTrack))
            {
                if (fromTrack.PowerDownOnEnd)
                {
                    fadeOutLength = GetPowerDownFadeLength(fromTrack);
                    fadeOutLength = BpmHelper.GetLengthAdjustedToMatchAnotherTrack(fromTrack, toTrack, fadeOutLength);
                }

                if (toTrack.StartBpm > (fromTrack.EndBpm * 1.1M))
                {
                    fadeOutLength = fadeOutLength / 2;
                }
            }

            var fadeLength = fadeOutLength;
            if (fadeInLength < fadeLength) fadeLength = fadeInLength;
            return fadeLength;
        }
        /// <summary>
        ///     Saves the track details to the track comment tag
        /// </summary>
        /// <param name="track">The track.</param>
        public static void SaveExtendedAttributes(Track track)
        {
            var attributes = new Dictionary<string, string>();

            if (track.StartBpm != 0)
                attributes.Add("StartBPM", $"{track.StartBpm}");

            if (track.EndBpm != 0)
                attributes.Add("EndBPM", $"{track.EndBpm}");

            attributes.Add("Duration", $"{track.LengthSeconds}");

            if (track.FadeInStart != 0)
                attributes.Add("FadeIn", $"{track.SamplesToSeconds(track.FadeInStart):0.000}");

            if (track.FadeOutStart != 0)
                attributes.Add("FadeOut", $"{track.SamplesToSeconds(track.FadeOutStart):0.000}");

            if (track.BpmAdjustmentRatio != 1)
                attributes.Add("BPMAdjust", $"{track.BpmAdjustmentRatio}");

            if (track.FadeInLength != 0)
                attributes.Add("FadeInLengthInSeconds", $"{track.FadeInLengthSeconds:0.000}");

            if (track.StartLoopCount > 0)
                attributes.Add("StartLoopCount", $"{track.StartLoopCount}");

            if (track.FadeOutLength != 0)
                attributes.Add("FadeOutLengthInSeconds", $"{track.SamplesToSeconds(track.FadeOutLength):0.000}");

            if (track.EndLoopCount > 0)
                attributes.Add("EndLoopCount", $"{track.EndLoopCount}");

            if (track.UsePreFadeIn)
            {
                attributes.Add("PreFadeInStartVolume", $"{track.PreFadeInStartVolume*100:00}");
                attributes.Add("PreFadeInPosition", $"{track.SamplesToSeconds(track.PreFadeInStart):0.000}");
            }

            if (track.PowerDownOnEnd) attributes.Add("PowerDown", $"{track.PowerDownOnEnd}");

            if (track.HasSkipSection)
            {
                attributes.Add("SkipStart", $"{track.SamplesToSeconds(track.SkipStart):0.000}");
                attributes.Add("SkipLengthInSeconds", $"{track.SamplesToSeconds(track.SkipLength):0.000}");
            }

            if (track.Rank != 1)
                attributes.Add("Rank", $"{track.Rank}");

            if (track.Key != "")
                attributes.Add("Key", track.Key);

            var extendedAttributeFile = GetExtendedAttributeFile(track.Description);
            SaveExtendedAttributes(attributes, extendedAttributeFile);
        }
        private static IEnumerable<TrackSample> GetTrackSamples(Track track)
        {
            DebugHelper.WriteLine("GetTrackSamples for " + track.Description);

            var trackSamples = new List<TrackSample>();
            if (track.UsePreFadeIn)
            {

                trackSamples.Add(new TrackSample
                {
                    IsLooped = false,
                    Start = track.SamplesToSeconds(track.PreFadeInStart),
                    Length = track.PreFadeInLengthSeconds,
                    Description = "Pre Fade In",
                    Key = "PreFadeIn"
                });
            }

            trackSamples.Add(new TrackSample
            {
                IsLooped = track.IsLoopedAtStart,
                Start = track.SamplesToSeconds(track.FadeInStart),
                Length = track.FadeInLengthSeconds,
                Description = "Fade In",
                Key = "FadeIn"
            });

            trackSamples.Add(new TrackSample
            {
                IsLooped = track.IsLoopedAtEnd,
                Start = track.SamplesToSeconds(track.FadeOutStart),
                Length = track.FadeOutLengthSeconds,
                Description = "Fade Out",
                Key = "FadeOut"
            });

            trackSamples.AddRange(GetAdditionalTrackSamples(track.Description));

            return trackSamples;
        }