/// <summary>
        /// Get an EncodeJob model for a LibHB Encode.
        /// </summary>
        /// <param name="task">
        /// The task.
        /// </param>
        /// <returns>
        /// An Interop.EncodeJob model.
        /// </returns>
        public static EncodeJob GetEncodeJob(EncodeTask task)
        {
            // The current Job Configuration
            EncodeTask work = task;

            // Which will be converted to this EncodeJob Model.
            EncodeJob       job     = new EncodeJob();
            EncodingProfile profile = new EncodingProfile();

            job.EncodingProfile = profile;

            // Audio Settings
            profile.AudioEncodings = new List <AudioEncoding>();
            job.ChosenAudioTracks  = new List <int>();
            foreach (AudioTrack track in work.AudioTracks)
            {
                AudioEncoding newTrack = new AudioEncoding
                {
                    Bitrate       = track.Bitrate,
                    Drc           = track.DRC,
                    Gain          = track.Gain,
                    Encoder       = Converters.GetCliAudioEncoder(track.Encoder),
                    InputNumber   = track.Track.HasValue ? track.Track.Value : 0,
                    Mixdown       = Converters.GetCliMixDown(track.MixDown),
                    SampleRateRaw = GetSampleRateRaw(track.SampleRate),
                };

                profile.AudioEncodings.Add(newTrack);
                if (track.Track != null)
                {
                    job.ChosenAudioTracks.Add(track.Track.Value);
                }
            }

            // Title Settings
            job.OutputPath = work.Destination;
            job.SourcePath = work.Source;
            job.Title      = work.Title;
            // job.SourceType = work.Type;
            switch (work.PointToPointMode)
            {
            case PointToPointMode.Chapters:
                job.RangeType = VideoRangeType.Chapters;
                break;

            case PointToPointMode.Seconds:
                job.RangeType = VideoRangeType.Seconds;
                break;

            case PointToPointMode.Frames:
                job.RangeType = VideoRangeType.Frames;
                break;
            }

            if (work.PointToPointMode == PointToPointMode.Seconds)
            {
                job.SecondsEnd   = work.EndPoint;
                job.SecondsStart = work.StartPoint;
            }
            if (work.PointToPointMode == PointToPointMode.Chapters)
            {
                job.ChapterStart = work.StartPoint;
                job.ChapterEnd   = work.EndPoint;
            }
            if (work.PointToPointMode == PointToPointMode.Frames)
            {
                job.FramesEnd   = work.EndPoint;
                job.FramesStart = work.StartPoint;
            }

            job.Angle           = work.Angle;
            job.EncodingProfile = profile;

            // Output Settings
            profile.IPod5GSupport = work.IPod5GSupport;
            profile.Optimize      = work.OptimizeMP4;
            switch (work.OutputFormat)
            {
            case OutputFormat.Mp4:
            case OutputFormat.M4V:
                profile.ContainerName = "av_mp4";     // TODO make part of enum.
                break;

            case OutputFormat.Mkv:
                profile.ContainerName = "av_mkv";     // TODO make part of enum.
                break;
            }

            // Picture Settings
            profile.Anamorphic = work.Anamorphic;
            profile.Cropping   = new Cropping
            {
                Top    = work.Cropping.Top,
                Bottom = work.Cropping.Bottom,
                Left   = work.Cropping.Left,
                Right  = work.Cropping.Right
            };
            profile.CroppingType = CroppingType.Custom; // TODO deal with this better
            profile.DisplayWidth = work.DisplayWidth.HasValue
                           ? int.Parse(Math.Round(work.DisplayWidth.Value, 0).ToString())
                           : 0;
            profile.PixelAspectX      = work.PixelAspectX;
            profile.PixelAspectY      = work.PixelAspectY;
            profile.Height            = work.Height.HasValue ? work.Height.Value : 0;
            profile.KeepDisplayAspect = work.KeepDisplayAspect;
            profile.MaxHeight         = work.MaxHeight.HasValue ? work.MaxHeight.Value : 0;
            profile.MaxWidth          = work.MaxWidth.HasValue ? work.MaxWidth.Value : 0;
            profile.Modulus           = work.Modulus.HasValue ? work.Modulus.Value : 16;
            profile.UseDisplayWidth   = true;
            profile.Width             = work.Width.HasValue ? work.Width.Value : 0;

            // Filter Settings
            profile.CustomDecomb      = work.CustomDecomb;
            profile.CustomDeinterlace = work.CustomDeinterlace;
            profile.CustomDenoise     = work.CustomDenoise;
            profile.CustomDetelecine  = work.CustomDetelecine;
            if (work.Deblock > 4)
            {
                profile.Deblock = work.Deblock;
            }
            profile.Decomb      = work.Decomb;
            profile.Deinterlace = work.Deinterlace;
            profile.Denoise     = work.Denoise;
            profile.Detelecine  = work.Detelecine;
            profile.Grayscale   = work.Grayscale;

            // Video Settings
            profile.Framerate           = work.Framerate.HasValue ? work.Framerate.Value : 0;
            profile.ConstantFramerate   = work.FramerateMode == FramerateMode.CFR;
            profile.Quality             = work.Quality.HasValue ? work.Quality.Value : 0;
            profile.VideoBitrate        = work.VideoBitrate.HasValue ? work.VideoBitrate.Value : 0;
            profile.VideoEncodeRateType = work.VideoEncodeRateType;
            profile.VideoEncoder        = Converters.GetVideoEncoder(work.VideoEncoder);

            if (work.VideoEncoder == VideoEncoder.X264)
            {
                profile.VideoPreset = work.X264Preset.ToString().ToLower().Replace(" ", string.Empty);
                profile.VideoTunes  = new List <string>();

                if (work.X264Tune != x264Tune.None)
                {
                    profile.VideoTunes.Add(work.X264Tune.ToString().ToLower().Replace(" ", string.Empty));
                }

                if (work.FastDecode)
                {
                    profile.VideoTunes.Add("fastdecode");
                }
            }
            else if (work.VideoEncoder == VideoEncoder.X265)
            {
                profile.VideoPreset  = work.X265Preset.ToString().ToLower().Replace(" ", string.Empty);
                profile.VideoProfile = work.H265Profile.ToString().ToLower().Replace(" ", string.Empty);
                profile.VideoTunes   = new List <string>();
            }

            profile.VideoLevel   = work.H264Level;
            profile.VideoProfile = work.H264Profile.ToString().ToLower().Replace(" ", string.Empty); // TODO change these away from strings.

            // Chapter Markers
            profile.IncludeChapterMarkers = work.IncludeChapterMarkers;
            job.CustomChapterNames        = work.ChapterNames.Select(item => item.ChapterName).ToList();
            job.UseDefaultChapterNames    = work.IncludeChapterMarkers;

            // Advanced Settings
            profile.VideoOptions = work.AdvancedEncoderOptions;

            // Subtitles
            job.Subtitles = new Subtitles {
                SourceSubtitles = new List <SourceSubtitle>(), SrtSubtitles = new List <SrtSubtitle>()
            };
            foreach (SubtitleTrack track in work.SubtitleTracks)
            {
                if (track.IsSrtSubtitle)
                {
                    job.Subtitles.SrtSubtitles.Add(
                        new SrtSubtitle
                    {
                        CharacterCode = track.SrtCharCode,
                        Default       = track.Default,
                        FileName      = track.SrtFileName,
                        LanguageCode  = track.SrtLang,
                        Offset        = track.SrtOffset
                    });
                }
                else
                {
                    if (track.SourceTrack != null)
                    {
                        job.Subtitles.SourceSubtitles.Add(
                            new SourceSubtitle
                        {
                            BurnedIn    = track.Burned,
                            Default     = track.Default,
                            Forced      = track.Forced,
                            TrackNumber = track.SourceTrack.TrackNumber
                        });
                    }
                }
            }

            return(job);
        }
示例#2
0
        /// <summary>
        /// Generate the Command Line Arguments for the Audio Settings Tab
        /// </summary>
        /// <param name="task">
        /// The encode task.
        /// </param>
        /// <returns>
        /// A Cli Query as a string
        /// </returns>
        private static string AudioSettingsQuery(EncodeTask task)
        {
            string query = string.Empty;

            ObservableCollection <AudioTrack> audioTracks = task.AudioTracks;

            List <int>          tracks      = new List <int>();
            List <AudioEncoder> codecs      = new List <AudioEncoder>();
            List <Mixdown>      mixdowns    = new List <Mixdown>();
            List <double>       samplerates = new List <double>();
            List <int>          bitrates    = new List <int>();
            List <double>       drcs        = new List <double>();
            List <double>       gains       = new List <double>();
            List <string>       trackNames  = new List <string>();

            // No Audio
            if (audioTracks.Count == 0)
            {
                query += " -a none ";
            }

            // Gather information about each audio track and store them in the declared lists.
            foreach (AudioTrack track in audioTracks)
            {
                if (track.Track == null)
                {
                    continue;
                }

                tracks.Add(track.Track.Value);

                // Audio Codec (-E)
                codecs.Add(track.Encoder);

                // Audio Mixdown (-6)
                mixdowns.Add(track.IsPassthru ? Mixdown.None : track.MixDown);

                // Sample Rate (-R)
                samplerates.Add(track.IsPassthru ? 0 : track.SampleRate);

                // Audio Bitrate (-B)
                bitrates.Add(track.IsPassthru ? 0 : track.Bitrate);

                // DRC (-D)
                drcs.Add(track.IsPassthru ? 0 : track.DRC);

                // Gain (--gain)
                gains.Add(track.IsPassthru ? 0 : track.Gain);

                // Audio Track Name (--aname)
                trackNames.Add(track.TrackName);
            }

            // Audio Track (-a)
            string audioItems = string.Empty;
            bool   firstLoop  = true;

            foreach (int item in tracks)
            {
                if (firstLoop)
                {
                    audioItems = item.ToString();
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -a " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // Audio Codec (-E)
            foreach (AudioEncoder item in codecs)
            {
                if (firstLoop)
                {
                    audioItems = Converters.GetCliAudioEncoder(item);
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + Converters.GetCliAudioEncoder(item);
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -E " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // Audio Mixdown (-6)
            foreach (Mixdown item in mixdowns)
            {
                if (firstLoop)
                {
                    audioItems = Converters.GetCliMixDown(item);
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + Converters.GetCliMixDown(item);
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -6 " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // Sample Rate (-R)
            foreach (double item in samplerates)
            {
                string add = (item == 0.0) ? "Auto" : item.ToString(new CultureInfo("en-US"));
                if (firstLoop)
                {
                    audioItems = add;
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + add;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -R " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // Audio Bitrate (-B)
            foreach (int item in bitrates)
            {
                if (firstLoop)
                {
                    audioItems = item.ToString();
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -B " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // DRC (-D)
            foreach (var itm in drcs)
            {
                string item = itm.ToString(new CultureInfo("en-US"));
                if (firstLoop)
                {
                    audioItems = item;
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -D " + audioItems;
            }

            audioItems = string.Empty; // Reset for another pass.
            firstLoop  = true;

            // Gain (--gain)
            foreach (var itm in gains)
            {
                string item = itm.ToString(new CultureInfo("en-US"));
                if (firstLoop)
                {
                    audioItems = item;
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " --gain " + audioItems;
            }

            audioItems = string.Empty; // Reset for another pass.
            firstLoop  = true;

            // Audio Track Names (--aname)
            bool foundTrackName = false;

            foreach (string trackName in trackNames)
            {
                if (!string.IsNullOrEmpty(trackName))
                {
                    foundTrackName = true;
                }

                if (firstLoop)
                {
                    audioItems = string.IsNullOrEmpty(trackName) ? "\"\"" : string.Format("\"{0}\"", trackName.Trim());
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + (string.IsNullOrEmpty(trackName) ? "\"\"" : string.Format("\"{0}\"", trackName.Trim()));
                }
            }
            if (foundTrackName)
            {
                query += string.Format(" --aname={0}", audioItems);
            }

            // Passthru Settings
            if (task.AllowedPassthruOptions != null)
            {
                string fallbackEncoders = string.Empty;

                if (task.AllowedPassthruOptions.AudioAllowAACPass != null && task.AllowedPassthruOptions.AudioAllowAACPass.Value)
                {
                    fallbackEncoders += "aac";
                }

                if (task.AllowedPassthruOptions.AudioAllowAC3Pass != null && task.AllowedPassthruOptions.AudioAllowAC3Pass.Value)
                {
                    fallbackEncoders += string.IsNullOrEmpty(fallbackEncoders) ? "ac3" : ",ac3";
                }

                if (task.AllowedPassthruOptions.AudioAllowDTSHDPass != null && task.AllowedPassthruOptions.AudioAllowDTSHDPass.Value)
                {
                    fallbackEncoders += string.IsNullOrEmpty(fallbackEncoders) ? "dtshd" : ",dtshd";
                }

                if (task.AllowedPassthruOptions.AudioAllowDTSPass != null && task.AllowedPassthruOptions.AudioAllowDTSPass.Value)
                {
                    fallbackEncoders += string.IsNullOrEmpty(fallbackEncoders) ? "dts" : ",dts";
                }

                if (task.AllowedPassthruOptions.AudioAllowMP3Pass != null && task.AllowedPassthruOptions.AudioAllowMP3Pass.Value)
                {
                    fallbackEncoders += string.IsNullOrEmpty(fallbackEncoders) ? "mp3" : ",mp3";
                }

                if (!string.IsNullOrEmpty(fallbackEncoders))
                {
                    // Special Case, The CLI alredy defaults to ALL, so if all area selected, then don't need to set copy mask
                    if (fallbackEncoders != "aac,ac3,dtshd,dts,mp3")
                    {
                        query += string.Format(" --audio-copy-mask {0}", fallbackEncoders);
                    }
                }
                else
                {
                    query += string.Format(" --audio-copy-mask none");
                }

                query += string.Format(" --audio-fallback {0}", Converters.GetCliAudioEncoder(task.AllowedPassthruOptions.AudioEncoderFallback));
            }

            return(query);
        }
示例#3
0
        /// <summary>
        /// Get an EncodeJob model for a LibHB Encode.
        /// </summary>
        /// <param name="task">
        /// The task.
        /// </param>
        /// <returns>
        /// An Interop.EncodeJob model.
        /// </returns>
        public static EncodeJob GetEncodeJob(QueueTask task)
        {
            // Sanity Checking
            if (task == null || task.Task == null)
            {
                return(null);
            }

            // The current Job Configuration
            EncodeTask work = task.Task;

            // Which will be converted to this EncodeJob Model.
            EncodeJob job = new EncodeJob();

            EncodingProfile profile = new EncodingProfile();

            job.EncodingProfile = profile;

            profile.Anamorphic = work.Anamorphic;

            profile.AudioEncodings = new List <AudioEncoding>();
            job.ChosenAudioTracks  = new List <int>();
            foreach (AudioTrack track in work.AudioTracks)
            {
                AudioEncoding newTrack = new AudioEncoding
                {
                    Bitrate       = track.Bitrate,
                    Drc           = track.DRC,
                    Gain          = track.Gain,
                    Encoder       = Converters.GetCliAudioEncoder(track.Encoder),
                    InputNumber   = track.Track.HasValue ? track.Track.Value : 0,
                    Mixdown       = Converters.GetCliMixDown(track.MixDown),
                    SampleRateRaw = GetSampleRateRaw(track.SampleRate),
                };

                profile.AudioEncodings.Add(newTrack);
                if (track.Track != null)
                {
                    job.ChosenAudioTracks.Add(track.Track.Value);
                }
            }
            profile.Cropping = new Cropping
            {
                Top    = work.Cropping.Top,
                Bottom = work.Cropping.Bottom,
                Left   = work.Cropping.Left,
                Right  = work.Cropping.Right
            };

            profile.CroppingType      = CroppingType.Custom; // TODO deal with this better
            profile.CustomDecomb      = work.CustomDecomb;
            profile.CustomDeinterlace = work.CustomDeinterlace;
            profile.CustomDenoise     = work.CustomDenoise;
            profile.CustomDetelecine  = work.CustomDetelecine;
            profile.Deblock           = work.Deblock;
            profile.Decomb            = work.Decomb;
            profile.Deinterlace       = work.Deinterlace;
            profile.Denoise           = work.Denoise;
            profile.Detelecine        = work.Detelecine;
            profile.DisplayWidth      = work.DisplayWidth.HasValue
                                       ? int.Parse(Math.Round(work.DisplayWidth.Value, 0).ToString())
                                       : 0;
            profile.Framerate             = work.Framerate.HasValue ? work.Framerate.Value : 0;
            profile.Grayscale             = work.Grayscale;
            profile.Height                = work.Height.HasValue ? work.Height.Value : 0;
            profile.IPod5GSupport         = work.IPod5GSupport;
            profile.IncludeChapterMarkers = work.IncludeChapterMarkers;
            profile.KeepDisplayAspect     = work.KeepDisplayAspect;
            profile.LargeFile             = work.LargeFile;
            profile.MaxHeight             = work.MaxHeight.HasValue ? work.MaxHeight.Value : 0;
            profile.MaxWidth              = work.MaxWidth.HasValue ? work.MaxWidth.Value : 0;
            profile.Modulus               = work.Modulus.HasValue ? work.Modulus.Value : 16;
            profile.Optimize              = work.OptimizeMP4;
            switch (work.OutputFormat)
            {
            case OutputFormat.Mp4:
            case OutputFormat.M4V:
                profile.OutputFormat = Container.Mp4;
                break;

            case OutputFormat.Mkv:
                profile.OutputFormat = Container.Mkv;
                break;
            }
            profile.ConstantFramerate = work.FramerateMode == FramerateMode.CFR;
            profile.PixelAspectX      = work.PixelAspectX;
            profile.PixelAspectY      = work.PixelAspectY;

            switch (work.OutputFormat)
            {
            case OutputFormat.Mp4:
                profile.PreferredExtension = OutputExtension.Mp4;
                break;

            case OutputFormat.M4V:
                profile.PreferredExtension = OutputExtension.M4v;
                break;
            }
            profile.Quality             = work.Quality.HasValue ? work.Quality.Value : 0;
            profile.UseDisplayWidth     = true;
            profile.VideoBitrate        = work.VideoBitrate.HasValue ? work.VideoBitrate.Value : 0;
            profile.VideoEncodeRateType = work.VideoEncodeRateType;
            profile.VideoEncoder        = Converters.GetVideoEncoder(work.VideoEncoder);
            profile.Width       = work.Width.HasValue ? work.Width.Value : 0;
            profile.X264Options = work.AdvancedEncoderOptions;

            if (work.PointToPointMode == PointToPointMode.Chapters)
            {
                job.ChapterStart = work.StartPoint;
                job.ChapterEnd   = work.EndPoint;
            }

            job.Angle           = work.Angle;
            job.EncodingProfile = profile;
            if (work.PointToPointMode == PointToPointMode.Frames)
            {
                job.FramesEnd   = work.EndPoint;
                job.FramesStart = work.StartPoint;
            }

            job.CustomChapterNames     = work.ChapterNames.Select(item => item.ChapterName).ToList();
            job.UseDefaultChapterNames = work.IncludeChapterMarkers;

            job.OutputPath = work.Destination;
            switch (work.PointToPointMode)
            {
            case PointToPointMode.Chapters:
                job.RangeType = VideoRangeType.Chapters;
                break;

            case PointToPointMode.Seconds:
                job.RangeType = VideoRangeType.Seconds;
                break;

            case PointToPointMode.Frames:
                job.RangeType = VideoRangeType.Frames;
                break;
            }

            if (work.PointToPointMode == PointToPointMode.Seconds)
            {
                job.SecondsEnd   = work.EndPoint;
                job.SecondsStart = work.StartPoint;
            }

            job.SourcePath = work.Source;
            // job.SourceType = work.Type;
            job.Title = work.Title;

            // Subtitles
            job.Subtitles = new Subtitles {
                SourceSubtitles = new List <SourceSubtitle>(), SrtSubtitles = new List <SrtSubtitle>()
            };
            foreach (SubtitleTrack track in work.SubtitleTracks)
            {
                if (track.IsSrtSubtitle)
                {
                    job.Subtitles.SrtSubtitles.Add(
                        new SrtSubtitle
                    {
                        CharacterCode = track.SrtCharCode,
                        Default       = track.Default,
                        FileName      = track.SrtFileName,
                        LanguageCode  = track.SrtLang,
                        Offset        = track.SrtOffset
                    });
                }
                else
                {
                    if (track.SourceTrack != null)
                    {
                        job.Subtitles.SourceSubtitles.Add(
                            new SourceSubtitle
                        {
                            BurnedIn    = track.Burned,
                            Default     = track.Default,
                            Forced      = track.Forced,
                            TrackNumber = track.SourceTrack.TrackNumber
                        });
                    }
                }
            }

            return(job);
        }
示例#4
0
        private static string AudioSettingsQuery(EncodeTask task)
        {
            string query = string.Empty;

            List <AudioTrack> audioTracks = task.AudioTracks;

            List <int>          tracks      = new List <int>();
            List <AudioEncoder> codecs      = new List <AudioEncoder>();
            List <Mixdown>      mixdowns    = new List <Mixdown>();
            List <double>       samplerates = new List <double>();
            List <int>          bitrates    = new List <int>();
            List <double>       drcs        = new List <double>();

            // No Audio
            if (audioTracks.Count == 0)
            {
                query += " -a none ";
            }

            // Gather information about each audio track and store them in the declared lists.
            foreach (AudioTrack track in audioTracks)
            {
                if (track.Track == null)
                {
                    continue;
                }

                tracks.Add(track.Track.Value);

                // Audio Codec (-E)
                codecs.Add(track.Encoder);

                // Audio Mixdown (-6)
                mixdowns.Add(track.MixDown);

                // Sample Rate (-R)
                samplerates.Add(track.SampleRate);

                // Audio Bitrate (-B)
                bitrates.Add(track.Bitrate);

                // DRC (-D)
                drcs.Add(track.DRC);
            }

            // Audio Track (-a)
            string audioItems = string.Empty;
            bool   firstLoop  = true;

            foreach (int item in tracks)
            {
                if (firstLoop)
                {
                    audioItems = item.ToString();
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -a " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // Audio Codec (-E)
            foreach (AudioEncoder item in codecs)
            {
                if (firstLoop)
                {
                    audioItems = Converters.GetCliAudioEncoder(item);
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -E " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // Audio Mixdown (-6)
            foreach (Mixdown item in mixdowns)
            {
                if (firstLoop)
                {
                    audioItems = Converters.GetCliMixDown(item);
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -6 " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // Sample Rate (-R)
            foreach (double item in samplerates)
            {
                if (firstLoop)
                {
                    audioItems = item.ToString();
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -R " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // Audio Bitrate (-B)
            foreach (int item in bitrates)
            {
                if (firstLoop)
                {
                    audioItems = item.ToString();
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -B " + audioItems;
            }
            firstLoop  = true;
            audioItems = string.Empty; // Reset for another pass.

            // DRC (-D)
            foreach (var itm in drcs)
            {
                string item = itm.ToString(new CultureInfo("en-US"));
                if (firstLoop)
                {
                    audioItems = item;
                    firstLoop  = false;
                }
                else
                {
                    audioItems += "," + item;
                }
            }
            if (audioItems.Trim() != String.Empty)
            {
                query += " -D " + audioItems;
            }

            return(query);
        }
        /// <summary>
        /// Get an EncodeJob model for a LibHB Encode.
        /// </summary>
        /// <param name="task">
        /// The task.
        /// </param>
        /// <param name="configuration">
        /// The configuration.
        /// </param>
        /// <returns>
        /// An Interop.EncodeJob model.
        /// </returns>
        public static EncodeJob GetEncodeJob(EncodeTask task, HBConfiguration configuration)
        {
            // The current Job Configuration
            EncodeTask work = task;

            // Which will be converted to this EncodeJob Model.
            EncodeJob job = new EncodeJob();

            // Audio Settings
            job.AudioEncodings = new List <AudioEncoding>();
            foreach (AudioTrack track in work.AudioTracks)
            {
                AudioEncoding newTrack = new AudioEncoding
                {
                    Bitrate        = track.Bitrate,
                    Drc            = track.DRC,
                    Gain           = track.Gain,
                    Encoder        = Converters.GetCliAudioEncoder(track.Encoder),
                    InputNumber    = track.Track.HasValue ? track.Track.Value : 0,
                    Mixdown        = Converters.GetCliMixDown(track.MixDown),
                    SampleRateRaw  = GetSampleRateRaw(track.SampleRate),
                    EncodeRateType = AudioEncodeRateType.Bitrate,
                    Name           = track.TrackName,
                    IsPassthru     = track.IsPassthru,
                };

                job.AudioEncodings.Add(newTrack);
            }

            // Title Settings
            job.OutputPath = work.Destination;
            job.SourcePath = work.Source;
            job.Title      = work.Title;

            // job.SourceType = work.Type;
            switch (work.PointToPointMode)
            {
            case PointToPointMode.Chapters:
                job.RangeType = VideoRangeType.Chapters;
                break;

            case PointToPointMode.Seconds:
                job.RangeType = VideoRangeType.Seconds;
                break;

            case PointToPointMode.Frames:
                job.RangeType = VideoRangeType.Frames;
                break;

            case PointToPointMode.Preview:
                job.RangeType = VideoRangeType.Preview;
                break;
            }

            if (work.PointToPointMode == PointToPointMode.Seconds)
            {
                job.SecondsEnd   = work.EndPoint;
                job.SecondsStart = work.StartPoint;
            }
            if (work.PointToPointMode == PointToPointMode.Chapters)
            {
                job.ChapterStart = work.StartPoint;
                job.ChapterEnd   = work.EndPoint;
            }
            if (work.PointToPointMode == PointToPointMode.Frames)
            {
                job.FramesEnd   = work.EndPoint;
                job.FramesStart = work.StartPoint;
            }

            if (work.PointToPointMode == PointToPointMode.Preview)
            {
                job.StartAtPreview = work.PreviewEncodeStartAt.HasValue ? work.PreviewEncodeStartAt.Value + 1 : 1;
                job.SecondsEnd     = work.PreviewEncodeDuration.HasValue ? work.PreviewEncodeDuration.Value : 30;
                job.SeekPoints     = configuration.PreviewScanCount;
            }

            job.Angle = work.Angle;

            // Output Settings
            job.IPod5GSupport = work.IPod5GSupport;
            job.Optimize      = work.OptimizeMP4;
            switch (work.OutputFormat)
            {
            case OutputFormat.Mp4:
                job.ContainerName = "av_mp4";     // TODO make part of enum.
                break;

            case OutputFormat.Mkv:
                job.ContainerName = "av_mkv";     // TODO make part of enum.
                break;
            }

            // Picture Settings
            job.Anamorphic = work.Anamorphic;
            job.Cropping   = new Cropping {
                Top = work.Cropping.Top, Bottom = work.Cropping.Bottom, Left = work.Cropping.Left, Right = work.Cropping.Right
            };
            job.DisplayWidth      = work.DisplayWidth.HasValue ? int.Parse(Math.Round(work.DisplayWidth.Value, 0).ToString()) : 0;
            job.PixelAspectX      = work.PixelAspectX;
            job.PixelAspectY      = work.PixelAspectY;
            job.Height            = work.Height.HasValue ? work.Height.Value : 0;
            job.KeepDisplayAspect = work.KeepDisplayAspect;
            job.MaxHeight         = work.MaxHeight.HasValue ? work.MaxHeight.Value : 0;
            job.MaxWidth          = work.MaxWidth.HasValue ? work.MaxWidth.Value : 0;
            job.Modulus           = work.Modulus.HasValue ? work.Modulus.Value : 16;
            job.UseDisplayWidth   = true;
            job.Width             = work.Width.HasValue ? work.Width.Value : 0;

            // Filter Settings
            job.CustomDecomb      = work.CustomDecomb;
            job.CustomDeinterlace = work.CustomDeinterlace;
            job.CustomDenoise     = work.CustomDenoise;
            job.DenoisePreset     = work.DenoisePreset.ToString().ToLower().Replace(" ", string.Empty);
            job.DenoiseTune       = work.DenoiseTune.ToString().ToLower().Replace(" ", string.Empty);
            job.CustomDetelecine  = work.CustomDetelecine;
            if (work.Deblock > 4)
            {
                job.Deblock = work.Deblock;
            }
            job.Decomb      = work.Decomb;
            job.Deinterlace = work.Deinterlace;
            job.Denoise     = work.Denoise;
            job.Detelecine  = work.Detelecine;
            job.Grayscale   = work.Grayscale;

            // Video Settings
            job.Framerate           = work.Framerate.HasValue ? work.Framerate.Value : 0;
            job.ConstantFramerate   = work.FramerateMode == FramerateMode.CFR;
            job.PeakFramerate       = work.FramerateMode == FramerateMode.PFR;
            job.Quality             = work.Quality.HasValue ? work.Quality.Value : 0;
            job.VideoBitrate        = work.VideoBitrate.HasValue ? work.VideoBitrate.Value : 0;
            job.VideoEncodeRateType = work.VideoEncodeRateType;
            job.VideoEncoder        = Converters.GetVideoEncoder(work.VideoEncoder);
            job.TwoPass             = work.TwoPass;
            job.TurboFirstPass      = work.TurboFirstPass;

            if (work.VideoEncoder == VideoEncoder.X264 || work.VideoEncoder == VideoEncoder.X265 || work.VideoEncoder == VideoEncoder.QuickSync)
            {
                job.VideoPreset  = work.VideoPreset.ShortName;
                job.VideoProfile = work.VideoProfile.ShortName;
                job.VideoLevel   = work.VideoLevel.ShortName;

                if (work.VideoEncoder != VideoEncoder.QuickSync)
                {
                    job.VideoTunes = new List <string>();
                    foreach (var item in work.VideoTunes)
                    {
                        job.VideoTunes.Add(item.ShortName);
                    }
                }
            }

            // Chapter Markers
            job.IncludeChapterMarkers  = work.IncludeChapterMarkers;
            job.CustomChapterNames     = work.ChapterNames.Select(item => item.ChapterName).ToList();
            job.UseDefaultChapterNames = work.IncludeChapterMarkers;

            // Advanced Settings
            job.VideoOptions = work.ShowAdvancedTab ? work.AdvancedEncoderOptions : work.ExtraAdvancedArguments;

            // Subtitles
            job.Subtitles = new Subtitles {
                SourceSubtitles = new List <SourceSubtitle>(), SrtSubtitles = new List <SrtSubtitle>()
            };
            foreach (SubtitleTrack track in work.SubtitleTracks)
            {
                if (track.IsSrtSubtitle)
                {
                    job.Subtitles.SrtSubtitles.Add(
                        new SrtSubtitle
                    {
                        CharacterCode = track.SrtCharCode,
                        Default       = track.Default,
                        FileName      = track.SrtPath,
                        LanguageCode  = track.SrtLang,
                        Offset        = track.SrtOffset,
                        BurnedIn      = track.Burned
                    });
                }
                else
                {
                    if (track.SourceTrack != null)
                    {
                        job.Subtitles.SourceSubtitles.Add(
                            new SourceSubtitle {
                            BurnedIn = track.Burned, Default = track.Default, Forced = track.Forced, TrackNumber = track.SourceTrack.TrackNumber
                        });
                    }
                }
            }

            return(job);
        }