private async Task ProcessClip(ClipModel clip, string clipName) { GlobalEvents.MixerClipCreated(clip); string clipUrl = string.Format("https://mixer.com/{0}?clip={1}", ChannelSession.User.username, clip.shareableId); if (this.ShowClipInfoInChat) { await ChannelSession.Chat.SendMessage("Clip Created: " + clipUrl); } this.extraSpecialIdentifiers[MixerClipURLSpecialIdentifier] = clipUrl; if (this.DownloadClip) { if (!Directory.Exists(this.DownloadDirectory)) { string error = "ERROR: The download folder specified for Mixer Clips does not exist"; Logger.Log(error); await ChannelSession.Chat.Whisper(ChannelSession.User.username, error); return; } if (!ChannelSession.Services.FileService.FileExists(MixerClipsAction.GetFFMPEGExecutablePath())) { string error = "ERROR: FFMPEG could not be found and the Mixer Clip can not be converted without it"; Logger.Log(error); await ChannelSession.Chat.Whisper(ChannelSession.User.username, error); return; } ClipLocatorModel clipLocator = clip.contentLocators.FirstOrDefault(cl => cl.locatorType.Equals(VideoFileContentLocatorType)); if (clipLocator != null) { string destinationFile = Path.Combine(this.DownloadDirectory, clipName + ".mp4"); #pragma warning disable CS4014 // Because this call is not awaited, execution of the current method continues before the call is completed Task.Run(async() => { Process process = new Process(); process.StartInfo.FileName = MixerClipsAction.GetFFMPEGExecutablePath(); process.StartInfo.Arguments = string.Format("-i {0} -c copy -bsf:a aac_adtstoasc \"{1}\"", clipLocator.uri, destinationFile.ToFilePathString()); process.StartInfo.RedirectStandardOutput = true; process.StartInfo.UseShellExecute = false; process.StartInfo.CreateNoWindow = true; process.Start(); while (!process.HasExited) { await Task.Delay(500); } }); #pragma warning restore CS4014 // Because this call is not awaited, execution of the current method continues before the call is completed } } }
public override async Task <JObject> GetProcessedItem(UserViewModel user, IEnumerable <string> arguments, Dictionary <string, string> extraSpecialIdentifiers) { if (this.lastClip != null) { ClipLocatorModel clipLocator = this.lastClip.contentLocators.FirstOrDefault(cl => cl.locatorType.Equals(MixerClipsAction.VideoFileContentLocatorType)); if (clipLocator != null) { this.lastClipURL = clipLocator.uri; this.Effects.Duration = Math.Max(0, this.lastClip.durationInSeconds - 1); return(await base.GetProcessedItem(user, arguments, extraSpecialIdentifiers)); } this.lastClip = null; } return(null); }
public override Task <OverlayItemBase> GetProcessedItem(UserViewModel user, IEnumerable <string> arguments, Dictionary <string, string> extraSpecialIdentifiers) { if (this.lastClip != null) { ClipModel clip = this.lastClip; this.lastClip = null; OverlayMixerClip item = this.Copy <OverlayMixerClip>(); ClipLocatorModel clipLocator = clip.contentLocators.FirstOrDefault(cl => cl.locatorType.Equals(MixerClipsAction.VideoFileContentLocatorType)); if (clipLocator != null) { item.URL = clipLocator.uri; item.Duration = Math.Max(0, clip.durationInSeconds - 1); return(Task.FromResult <OverlayItemBase>(item)); } } return(Task.FromResult <OverlayItemBase>(null)); }
protected override async Task PerformInternal(UserViewModel user, IEnumerable <string> arguments) { if (ChannelSession.Chat != null) { await ChannelSession.Chat.SendMessage("Sending clip creation request to Mixer..."); string clipName = await this.ReplaceStringWithSpecialModifiers(this.ClipName, user, arguments); if (!string.IsNullOrEmpty(clipName) && MixerClipsAction.MinimumLength <= this.ClipLength && this.ClipLength <= MixerClipsAction.MaximumLength) { bool clipCreated = false; DateTimeOffset clipCreationTime = DateTimeOffset.Now; BroadcastModel broadcast = await ChannelSession.Connection.GetCurrentBroadcast(); if (broadcast != null) { if (await ChannelSession.Connection.CanClipBeMade(broadcast)) { clipCreated = await ChannelSession.Connection.CreateClip(new ClipRequestModel() { broadcastId = broadcast.id.ToString(), highlightTitle = clipName, clipDurationInSeconds = this.ClipLength }); } } if (clipCreated) { for (int i = 0; i < 10; i++) { await Task.Delay(2000); IEnumerable <ClipModel> clips = await ChannelSession.Connection.GetChannelClips(ChannelSession.Channel); ClipModel clip = clips.OrderByDescending(c => c.uploadDate).FirstOrDefault(); if (clip != null && clip.uploadDate.ToLocalTime() >= clipCreationTime && clip.title.Equals(clipName)) { await ChannelSession.Chat.SendMessage("Clip Created: " + string.Format("https://mixer.com/{0}?clip={1}", ChannelSession.User.username, clip.shareableId)); if (this.DownloadClip && Directory.Exists(this.DownloadDirectory) && ChannelSession.Services.FileService.FileExists(MixerClipsAction.GetFFMPEGExecutablePath())) { ClipLocatorModel clipLocator = clip.contentLocators.FirstOrDefault(cl => cl.locatorType.Equals(VideoFileContentLocatorType)); if (clipLocator != null) { char[] invalidChars = Path.GetInvalidFileNameChars(); string fileName = new string(clipName.Select(c => invalidChars.Contains(c) ? '_' : c).ToArray()); string destinationFile = Path.Combine(this.DownloadDirectory, fileName + ".mp4"); Process process = new Process(); process.StartInfo.FileName = MixerClipsAction.GetFFMPEGExecutablePath(); process.StartInfo.Arguments = string.Format("-i {0} -c copy -bsf:a aac_adtstoasc \"{1}\"", clipLocator.uri, destinationFile); process.StartInfo.RedirectStandardOutput = true; process.StartInfo.UseShellExecute = false; process.StartInfo.CreateNoWindow = true; process.Start(); while (!process.HasExited) { await Task.Delay(500); } } } return; } } await ChannelSession.Chat.SendMessage("Clip was created, but could not be retrieved at this time"); } else { await ChannelSession.Chat.SendMessage("Unable to create clip, please try again later"); } } } }