private void Declare() { CronusMax = new Output.CronusPlus.Write(this); Gamepad = new Output.Gamepad(this); Gimx = new Output.Gimx.Gimx(this); GimxRemote = new Output.Gimx.GimxRemote(this); Keyboard = new Input.KeyboardHook(this); Keymap = new Keymap(this); Menu = new Menu.ShowMenu(this); Mouse = new Input.Mouse.Hook(this); Remap = new Remapping(); System = new Configuration(this); VideoResolution = new VideoResolution(this); //Fix these later KeyboardInterface = new Input.KeyboardInterface(Home); KeyboardInterface.getSystemHandle(System); KeyboardInterface.getRemapHangle(Remap); KeyboardInterface.getKeymapHandle(Keymap); TitanOne = new Output.TitanOne.Write(Home, System, Gamepad); External = new ExternalScript(Home); VideoCapture = new VideoCapture.VideoCapture(Home, System); System.GetClassHandles(VideoCapture, CronusMax, TitanOne, VideoResolution); }
public static VideoResolutionWidthHeight Get(VideoResolution videoResolution) { var videoResolutionWidthHeight = new VideoResolutionWidthHeight(); if (videoResolution == VideoResolution.HD1080p) { videoResolutionWidthHeight.Width = 1920; videoResolutionWidthHeight.Height = 1080; } else if (videoResolution == VideoResolution.HD720p) { videoResolutionWidthHeight.Width = 1280; videoResolutionWidthHeight.Height = 720; } else if (videoResolution == VideoResolution.SD1024_768) { videoResolutionWidthHeight.Width = 1024; videoResolutionWidthHeight.Height = 768; } else if (videoResolution == VideoResolution.SD800_600) { videoResolutionWidthHeight.Width = 640; videoResolutionWidthHeight.Height = 480; } else if (videoResolution == VideoResolution.SD640_480) { videoResolutionWidthHeight.Width = 640; videoResolutionWidthHeight.Height = 480; } return(videoResolutionWidthHeight); }
/// <summary> /// Initializes an instance of <see cref="MuxedStreamInfo"/>. /// </summary> public MuxedStreamInfo( int tag, string url, Container container, FileSize size, Bitrate bitrate, string audioCodec, string videoCodec, string videoQualityLabel, VideoQuality videoQuality, VideoResolution resolution, Framerate framerate) { Tag = tag; Url = url; Container = container; Size = size; Bitrate = bitrate; AudioCodec = audioCodec; VideoCodec = videoCodec; VideoQualityLabel = videoQualityLabel; VideoQuality = videoQuality; Resolution = resolution; Framerate = framerate; }
/// <summary> /// Subscription for video and vbss. /// </summary> /// <param name="mediaType">vbss or video.</param> /// <param name="mediaSourceId">The video source Id.</param> /// <param name="videoResolution">The preferred video resolution.</param> /// <param name="socketId">Socket id requesting the video. For vbss it is always 0.</param> public void Subscribe(MediaType mediaType, uint mediaSourceId, VideoResolution videoResolution, uint socketId = 0) { try { this.ValidateSubscriptionMediaType(mediaType); this.logger.Info($"Subscribing to the video source: {mediaSourceId} on socket: {socketId} with the preferred resolution: {videoResolution} and mediaType: {mediaType}"); if (mediaType == MediaType.Vbss) { if (this.vbssSocket == null) { this.logger.Warn($"vbss socket not initialized"); } else { this.vbssSocket.Subscribe(videoResolution, mediaSourceId); } } else if (mediaType == MediaType.Video) { if (this.videoSockets == null) { this.logger.Warn($"video sockets were not created"); } else { this.videoSockets[(int)socketId].Subscribe(videoResolution, mediaSourceId); } } } catch (Exception ex) { this.logger.Error(ex, $"Video Subscription failed for the socket: {socketId} and MediaSourceId: {mediaSourceId} with exception"); } }
public void Init(Model model) { InitializeComponent(); OnCompleted += () => { disposables.Dispose(); }; VideoResolution resolution = null; //TODO rid of these checks if (model.size == null) { resolution = new VideoResolution() { height = 576, width = 720 }; } if (model.size.width < 1 || model.size.height < 1) { resolution = new VideoResolution() { height = 576, width = 720 }; } else { resolution = model.size; } InitAnnŠ¾tation(resolution); VideoStartup(model, resolution); }
private void OnResolutionItemSelected(int index) { VideoResolution resolution = (VideoResolution)index; switch (resolution) { case VideoResolution.Resolution480p: _width = 720; _height = 480; break; case VideoResolution.Resolution720p: _width = 1280; _height = 720; break; case VideoResolution.Resolution1080p: _width = 1920; _height = 1080; break; case VideoResolution.Resolution2160p: _width = 3840; _height = 2160; break; case VideoResolution.Resolution4320p: _width = 7680; _height = 4320; break; default: throw new ArgumentOutOfRangeException(); } }
public Model( string uri, VideoResolution size, string engineConfToken ) { this.uri = uri; this.size = size; this.engineConfToken = engineConfToken; }
/// <summary> /// Set video resolution. /// </summary> /// /// <param name="resolution">Video resolution to set.</param> /// /// <remarks> /// <para><note>Setting higher <see cref="SetQuality">quality level</see> and resolution /// may increase delays for other requests sent to SRV-1. So if /// robot is used not only for video, but also for controlling servos/motors, and higher /// response level is required, then do not set very high quality and resolution. /// </note></para> /// </remarks> /// /// <exception cref="ArgumentOutOfRangeException">Invalid resolution was specified.</exception> /// public void SetResolution(VideoResolution resolution) { if (!Enum.IsDefined(typeof(VideoResolution), resolution)) { throw new ArgumentException("Invalid resolution was specified."); } Send(new byte[] { (byte)resolution }); }
internal VideoEncoderConfiguration(VideoEncoding?encoding, float?quality, VideoResolution resolution, RateControl rateControl, H264Configuration h264, Mpeg4Configuration mpeg4) { Encoding = encoding; Quality = quality; Resolution = resolution; RateControl = rateControl; H264 = h264; Mpeg4 = mpeg4; }
private async Task ResolveAdaptiveStreamInfosAsync(PlayerContext context, string encodedData, ICollection <AudioStreamInfo> audioStreamInfos, ICollection <VideoStreamInfo> videoStreamInfos) { foreach (var streamEncoded in encodedData.Split(",")) { var streamInfoDic = UrlHelper.GetDictionaryFromUrlQuery(streamEncoded); var itag = streamInfoDic.Get("itag").ParseInt(); var url = streamInfoDic.Get("url"); var sig = streamInfoDic.GetOrDefault("s"); var contentLength = streamInfoDic.Get("clen").ParseLong(); var bitrate = streamInfoDic.Get("bitrate").ParseLong(); #if RELEASE if (!MediaStreamInfo.IsKnown(itag)) { continue; } #endif // Decipher signature if needed if (sig.IsNotBlank()) { var playerSource = await GetPlayerSourceAsync(context.SourceUrl).ConfigureAwait(false); sig = playerSource.Decipher(sig); url = UrlHelper.SetUrlQueryParameter(url, "signature", sig); } // Set rate bypass url = UrlHelper.SetUrlQueryParameter(url, "ratebypass", "yes"); // Check if audio var isAudio = streamInfoDic.Get("type").Contains("audio/"); // If audio stream if (isAudio) { var streamInfo = new AudioStreamInfo(itag, url, contentLength, bitrate); audioStreamInfos.Add(streamInfo); } // If video stream else { // Parse additional data var size = streamInfoDic.Get("size"); var width = size.SubstringUntil("x").ParseInt(); var height = size.SubstringAfter("x").ParseInt(); var resolution = new VideoResolution(width, height); var framerate = streamInfoDic.Get("fps").ParseInt(); var streamInfo = new VideoStreamInfo(itag, url, contentLength, bitrate, resolution, framerate); videoStreamInfos.Add(streamInfo); } } }
public Model( StreamSetup streamSetup, MediaUri mediaUri, VideoResolution encoderResolution, bool isUriEnabled, IMetadataReceiver metadataReceiver ) { this.streamSetup = streamSetup; this.mediaUri = mediaUri; this.encoderResolution = encoderResolution; this.isUriEnabled = isUriEnabled; this.metadataReceiver = metadataReceiver; }
public static Resolution Create(VideoResolution resolution) { return(resolution switch { VideoResolution.Hd => HD, VideoResolution.FullHd => FullHD, VideoResolution.Uhd4k => UltraHD4K, VideoResolution.Auto => Auto, _ => Auto, });
void VideoStartup(Model model, VideoResolution resolution) { //subscribe to metadata IMetadataReceiver metadataReceiver = null; if (AppDefaults.visualSettings.EnableGraphicAnnotation) { string vaConfToken = model.engineConfToken; var eventMetadataProcessor = new EventMetadataProcessor(); //eventMetadataProcessor.Processors.Add(new ObjectMotionMetadataProcessor(null, vaConfToken, movingObjectsHolder.EntityInitialized, movingObjectsHolder.EntityChanged, movingObjectsHolder.EntityDeleted)); eventMetadataProcessor.Processors.Add(new MotionAlarmMetadataProcessor(null, vaConfToken, alarmsHolder.EntityInitialized, alarmsHolder.EntityChanged, alarmsHolder.EntityDeleted)); eventMetadataProcessor.Processors.Add(new RegionMotionAlarmMetadataProcessor(null, vaConfToken, alarmsHolder.EntityInitialized, alarmsHolder.EntityChanged, alarmsHolder.EntityDeleted)); eventMetadataProcessor.Processors.Add(new LoiteringAlarmMetadataProcessor(null, vaConfToken, alarmsHolder.EntityInitialized, alarmsHolder.EntityChanged, alarmsHolder.EntityDeleted)); eventMetadataProcessor.Processors.Add(new AbandonedItemAlarmMetadataProcessor(null, vaConfToken, alarmsHolder.EntityInitialized, alarmsHolder.EntityChanged, alarmsHolder.EntityDeleted)); eventMetadataProcessor.Processors.Add(new TripwireAlarmMetadataProcessor(null, vaConfToken, alarmsHolder.EntityInitialized, alarmsHolder.EntityChanged, alarmsHolder.EntityDeleted)); eventMetadataProcessor.Processors.Add(new TamperingDetectorAlarmMetadataProcessor(null, vaConfToken, alarmsHolder.EntityInitialized, alarmsHolder.EntityChanged, alarmsHolder.EntityDeleted)); var sceneMetadataProcessor = new SceneMetadataProcessor(movingObjectsHolder.EntityInitialized, movingObjectsHolder.EntityChanged, movingObjectsHolder.EntityDeleted); var metadataProcessor = new MetadataProcessor(eventMetadataProcessor, sceneMetadataProcessor); metadataReceiver = new MetadataFramer(metadataProcessor.Process); } vidBuff = new VideoBuffer(resolution.width, resolution.height); var streamSetup = new StreamSetup() { transport = new Transport() { protocol = AppDefaults.visualSettings.Transport_Type } }; VideoPlayerView playview = new VideoPlayerView(); disposables.Add(playview); player.Child = playview; playview.Init(new VideoPlayerView.Model( streamSetup: streamSetup, mediaUri: new MediaUri() { uri = model.uri }, encoderResolution: new VideoResolution() { height = resolution.height, width = resolution.width }, isUriEnabled: false, //TODO if true then annotation is not positioned correctly metadataReceiver: metadataReceiver )); uriString.Visibility = System.Windows.Visibility.Visible; uriString.Text = model.uri; }
public void VideoResolution_Equality_Test() { var vr1 = new VideoResolution(800, 600); var vr2 = new VideoResolution(800, 600); var vr3 = new VideoResolution(640, 480); Assert.That(vr1, Is.EqualTo(vr2)); Assert.That(vr2, Is.Not.EqualTo(vr3)); Assert.That(vr1.GetHashCode(), Is.EqualTo(vr2.GetHashCode())); Assert.That(vr2.GetHashCode(), Is.Not.EqualTo(vr3.GetHashCode())); }
/// <summary> /// Initializes an instance of <see cref="MuxedStreamInfo"/>. /// </summary> public MuxedStreamInfo(int itag, string url, Container container, long size, AudioEncoding audioEncoding, VideoEncoding videoEncoding, string videoQualityLabel, VideoQuality videoQuality, VideoResolution resolution) : base(itag, url, container, size) { AudioEncoding = audioEncoding; VideoEncoding = videoEncoding; VideoQualityLabel = videoQualityLabel; VideoQuality = videoQuality; Resolution = resolution; }
/// <summary> /// Initializes an instance of <see cref="VideoStreamInfo"/>. /// </summary> public VideoStreamInfo(int itag, string url, Container container, long size, long bitrate, VideoEncoding videoEncoding, string videoQualityLabel, VideoQuality videoQuality, VideoResolution resolution, int framerate) : base(itag, url, container, size) { Bitrate = bitrate; VideoEncoding = videoEncoding; VideoQualityLabel = videoQualityLabel; VideoQuality = videoQuality; Resolution = resolution; Framerate = framerate; }
public static Model Create( string uri, VideoResolution size, string engineConfToken ) { var _this = new Model(); _this.uri = uri; _this.size = size; _this.engineConfToken = engineConfToken; return(_this); }
private void InitAnnŠ¾tation(VideoResolution resolution) { // transform from onvif Func <double, double> scaleX = (x) => (1 + x) * resolution.width / 2.0; Func <double, double> scaleY = (y) => (1 - y) * resolution.height / 2.0; { // objects objects.Width = resolution.width; objects.Height = resolution.height; movingObjectsHolder = new VAEntitiesHolder <VAObject, VAObjectSnapshot>(scaleX, scaleY, null); var binding = new Binding("Objects") { ElementName = root.Name }; objects.SetBinding(ItemsControl.ItemsSourceProperty, binding); } { // alarms alarms.Width = resolution.width; alarms.Height = resolution.height; /*((INotifyCollectionChanged)alarms.Items).CollectionChanged += (s, e) => * { * if (e.NewItems != null && e.NewItems.Count > 0) * { * Dispatcher.BeginInvoke( * new Action(delegate { ((ListBox)alarms).ScrollIntoView(e.NewItems[e.NewItems.Count - 1]); }) * , DispatcherPriority.SystemIdle); * } * };*/ ((INotifyCollectionChanged)alarms.Items).CollectionChanged += (s, e) => { if (e.NewItems != null && e.NewItems.Count > 0) { var c = alarms.ItemContainerGenerator.ContainerFromItem(e.NewItems[e.NewItems.Count - 1]); if (c is FrameworkElement) { ((FrameworkElement)c).BringIntoView(); } } }; alarmsHolder = new VAEntitiesHolder <VAAlarm, VAEntitySnapshot>(scaleX, scaleY, null); var binding = new Binding("Alarms") { ElementName = root.Name }; alarms.SetBinding(ItemsControl.ItemsSourceProperty, binding); } }
public void VideoResolution_Equality_Test() { var vr1 = new VideoResolution(800, 600); var vr2 = new VideoResolution(800, 600); var vr3 = new VideoResolution(640, 480); Assert.IsTrue(vr1 == vr2); Assert.IsFalse(vr2 == vr3); Assert.IsTrue(vr2 != vr3); Assert.AreEqual(vr1, vr2); Assert.AreNotEqual(vr2, vr3); Assert.AreEqual(vr1.GetHashCode(), vr2.GetHashCode()); Assert.AreNotEqual(vr2.GetHashCode(), vr3.GetHashCode()); }
public static Model Create( string profToken, VideoResolution resolution, int maxFrameRate, int minFrameRate, double frameRate, int maxEncodingInterval, int minEncodingInterval, int encodingInterval, int maxQuality, int minQuality, float quality, int maxBitrate, int minBitrate, double bitrate, int maxGovLength, int minGovLength, int govLength, VideoEncoding encoder, VideoEncoderConfigurationOptions encoderOptions ) { var _this = new Model(); _this.profToken = profToken; _this.maxFrameRate = maxFrameRate; _this.minFrameRate = minFrameRate; _this.maxEncodingInterval = maxEncodingInterval; _this.minEncodingInterval = minEncodingInterval; _this.maxQuality = maxQuality; _this.minQuality = minQuality; _this.maxBitrate = maxBitrate; _this.minBitrate = minBitrate; _this.maxGovLength = maxGovLength; _this.minGovLength = minGovLength; _this.encoderOptions = encoderOptions; _this.origin.resolution = resolution; _this.origin.frameRate = frameRate; _this.origin.encodingInterval = encodingInterval; _this.origin.quality = quality; _this.origin.bitrate = bitrate; _this.origin.govLength = govLength; _this.origin.encoder = encoder; _this.RevertChanges(); return(_this); }
///<summary> ŠŃŠµŠ½ŠŗŠ° ŠŗŠ°ŃŠµŃŃŠ²Š° Š²ŠøŠ“ŠµŠ¾. </summary> private void ChkVideoResolution() { int.TryParse(height, out int h); int.TryParse(width, out int w); if (((float)w / h) < 1.77f) { if (h < 700) { vidRes = VideoResolution.LQ; return; } if (h < 1000) { vidRes = VideoResolution.HD; return; } if (h < 1400) { vidRes = VideoResolution.FHD; return; } if (h < 2100) { vidRes = VideoResolution.QHD; return; } } else { if (w < 1200) { vidRes = VideoResolution.LQ; return; } if (w < 1900) { vidRes = VideoResolution.HD; return; } if (w < 2500) { vidRes = VideoResolution.FHD; return; } if (w < 4000) { vidRes = VideoResolution.QHD; return; } } vidRes = VideoResolution.UHD; }
public static Model Create( string videoSourceToken, string profToken, string videoSourceConfToken, string videoAnalyticsConfToken, VideoResolution encoderResolution ) { var _this = new Model(); _this.videoSourceToken = videoSourceToken; _this.profToken = profToken; _this.videoSourceConfToken = videoSourceConfToken; _this.videoAnalyticsConfToken = videoAnalyticsConfToken; _this.encoderResolution = encoderResolution; return(_this); }
public static Model Create( StreamSetup streamSetup, MediaUri mediaUri, VideoResolution encoderResolution, bool isUriEnabled, IMetadataReceiver metadataReceiver ) { var _this = new Model(); _this.streamSetup = streamSetup; _this.mediaUri = mediaUri; _this.encoderResolution = encoderResolution; _this.isUriEnabled = isUriEnabled; _this.metadataReceiver = metadataReceiver; return(_this); }
internal static string ToSerializedValue(this VideoResolution value) { switch (value) { case VideoResolution.All: return("All"); case VideoResolution.SD480p: return("SD480p"); case VideoResolution.HD720p: return("HD720p"); case VideoResolution.HD1080p: return("HD1080p"); } return(null); }
private void InitAnnŠ¾tation(VideoResolution resolution) { Func <double, double> scaleX = (x) => (1 + x) * resolution.width / 2.0; Func <double, double> scaleY = (y) => (1 - y) * resolution.height / 2.0; { // objects objects.Width = resolution.width; objects.Height = resolution.height; movingObjectsHolder = new VAEntitiesHolder <VAObject, VAObjectSnapshot>(scaleX, scaleY, null); var binding = new Binding("Objects") { ElementName = root.Name }; objects.SetBinding(ItemsControl.ItemsSourceProperty, binding); } { // alarms alarms.Width = resolution.width; alarms.Height = resolution.height; ((INotifyCollectionChanged)alarms.Items).CollectionChanged += (s, e) => { if (e.NewItems != null && e.NewItems.Count > 0) { var c = alarms.ItemContainerGenerator.ContainerFromItem(e.NewItems[e.NewItems.Count - 1]); if (c is FrameworkElement) { ((FrameworkElement)c).BringIntoView(); } } }; alarmsHolder = new VAEntitiesHolder <VAAlarm, VAEntitySnapshot>(scaleX, scaleY, null); var binding = new Binding("Alarms") { ElementName = root.Name }; alarms.SetBinding(ItemsControl.ItemsSourceProperty, binding); } }
void FindResolutions(IEnumerable <VideoResolution> videoResolutions, out VideoResolution highest, out VideoResolution lowest, out VideoResolution median) { BeginStep("Find highest and lowest resolutions for further testing"); List <VideoResolution> resolutions = videoResolutions.OrderBy(VR => VR.Height * VR.Width).ToList(); lowest = resolutions.First(); highest = resolutions.Last(); int cnt = resolutions.Count; int middle = (cnt + 1) / 2 - 1; median = resolutions[middle]; LogStepEvent(string.Format("Highest resolution: width ={0}, height = {1} ", highest.Width, highest.Height)); LogStepEvent(string.Format("Median resolution: width ={0}, height = {1} ", median.Width, median.Height)); LogStepEvent(string.Format("Lowest resolution: width ={0}, height = {1} ", lowest.Width, lowest.Height)); StepPassed(); }
private void BuildAndShowResolutionMenu() { using PopupMenu menu = new PopupMenu(this.RequireContext(), this.containerResolution, GravityFlags.End); /* * UHD4K is not supported in the Camera API 1. To use the Camera API 2, please contact * us at [email protected]. */ VideoResolution.GetValues() .Where(v => v != VideoResolution.Uhd4k) .Select(v => menu.Menu.Add(v.Name())) .ToList(); menu.MenuItemClick += async(object sender, PopupMenu.MenuItemClickEventArgs args) => { string selectedResolution = args.Item.TitleFormatted.ToString(); await this.viewModel.SetVideoResolutionAsync(Java.Lang.Enum.ValueOf(Java.Lang.Class.FromType(typeof(VideoResolution)), selectedResolution) as VideoResolution); this.RefreshResolutionData(); }; menu.Show(); }
/// <inheritdoc /> public async Task <MediaStreamInfoSet> GetVideoMediaStreamInfosAsync(string videoId) { videoId.GuardNotNull(nameof(videoId)); if (!ValidateVideoId(videoId)) { throw new ArgumentException($"Invalid YouTube video ID [{videoId}].", nameof(videoId)); } // Get player configuration var playerConfiguration = await GetPlayerConfigurationAsync(videoId).ConfigureAwait(false); // Prepare stream info maps var muxedStreamInfoMap = new Dictionary <int, MuxedStreamInfo>(); var audioStreamInfoMap = new Dictionary <int, AudioStreamInfo>(); var videoStreamInfoMap = new Dictionary <int, VideoStreamInfo>(); // Get muxed stream infos var muxedStreamInfoDics = playerConfiguration.MuxedStreamInfosUrlEncoded.EmptyIfNull().Split(",").Select(Url.SplitQuery); foreach (var streamInfoDic in muxedStreamInfoDics) { // Extract info var itag = streamInfoDic["itag"].ParseInt(); var url = streamInfoDic["url"]; // Decipher signature if needed var signature = streamInfoDic.GetValueOrDefault("s"); if (!signature.IsNullOrWhiteSpace()) { // Get cipher operations (cached) var cipherOperations = await GetCipherOperationsAsync(playerConfiguration.PlayerSourceUrl).ConfigureAwait(false); // Decipher signature signature = cipherOperations.Decipher(signature); // Set the corresponding parameter in the URL var signatureParameter = streamInfoDic.GetValueOrDefault("sp") ?? "signature"; url = Url.SetQueryParameter(url, signatureParameter, signature); } // Try to extract content length, otherwise get it manually var contentLength = Regex.Match(url, @"clen=(\d+)").Groups[1].Value.ParseLongOrDefault(); if (contentLength <= 0) { // Send HEAD request and get content length contentLength = await _httpClient.GetContentLengthAsync(url, false).ConfigureAwait(false) ?? 0; // If content length is still not available - stream is gone or faulty if (contentLength <= 0) { continue; } } // Extract container var containerRaw = streamInfoDic["type"].SubstringUntil(";").SubstringAfter("/"); var container = Heuristics.ContainerFromString(containerRaw); // Extract audio encoding var audioEncodingRaw = streamInfoDic["type"].SubstringAfter("codecs=\"").SubstringUntil("\"").Split(", ").Last(); var audioEncoding = Heuristics.AudioEncodingFromString(audioEncodingRaw); // Extract video encoding var videoEncodingRaw = streamInfoDic["type"].SubstringAfter("codecs=\"").SubstringUntil("\"").Split(", ").First(); var videoEncoding = Heuristics.VideoEncodingFromString(videoEncodingRaw); // Determine video quality from itag var videoQuality = Heuristics.VideoQualityFromItag(itag); // Determine video quality label from video quality var videoQualityLabel = Heuristics.VideoQualityToLabel(videoQuality); // Determine video resolution from video quality var resolution = Heuristics.VideoQualityToResolution(videoQuality); // Add to list muxedStreamInfoMap[itag] = new MuxedStreamInfo(itag, url, container, contentLength, audioEncoding, videoEncoding, videoQualityLabel, videoQuality, resolution); } // Get adaptive stream infos var adaptiveStreamInfoDics = playerConfiguration.AdaptiveStreamInfosUrlEncoded.EmptyIfNull().Split(",").Select(Url.SplitQuery); foreach (var streamInfoDic in adaptiveStreamInfoDics) { // Extract info var itag = streamInfoDic["itag"].ParseInt(); var url = streamInfoDic["url"]; var bitrate = streamInfoDic["bitrate"].ParseLong(); // Decipher signature if needed var signature = streamInfoDic.GetValueOrDefault("s"); if (!signature.IsNullOrWhiteSpace()) { // Get cipher operations (cached) var cipherOperations = await GetCipherOperationsAsync(playerConfiguration.PlayerSourceUrl).ConfigureAwait(false); // Decipher signature signature = cipherOperations.Decipher(signature); // Set the corresponding parameter in the URL var signatureParameter = streamInfoDic.GetValueOrDefault("sp") ?? "signature"; url = Url.SetQueryParameter(url, signatureParameter, signature); } // Try to extract content length, otherwise get it manually var contentLength = streamInfoDic.GetValueOrDefault("clen").ParseLongOrDefault(); if (contentLength <= 0) { // Send HEAD request and get content length contentLength = await _httpClient.GetContentLengthAsync(url, false).ConfigureAwait(false) ?? 0; // If content length is still not available - stream is gone or faulty if (contentLength <= 0) { continue; } } // Extract container var containerRaw = streamInfoDic["type"].SubstringUntil(";").SubstringAfter("/"); var container = Heuristics.ContainerFromString(containerRaw); // If audio-only if (streamInfoDic["type"].StartsWith("audio/", StringComparison.OrdinalIgnoreCase)) { // Extract audio encoding var audioEncodingRaw = streamInfoDic["type"].SubstringAfter("codecs=\"").SubstringUntil("\""); var audioEncoding = Heuristics.AudioEncodingFromString(audioEncodingRaw); // Add stream audioStreamInfoMap[itag] = new AudioStreamInfo(itag, url, container, contentLength, bitrate, audioEncoding); } // If video-only else { // Extract video encoding var videoEncodingRaw = streamInfoDic["type"].SubstringAfter("codecs=\"").SubstringUntil("\""); var videoEncoding = !videoEncodingRaw.Equals("unknown", StringComparison.OrdinalIgnoreCase) ? Heuristics.VideoEncodingFromString(videoEncodingRaw) : VideoEncoding.Av1; // HACK: issue 246 // Extract video quality label and video quality var videoQualityLabel = streamInfoDic["quality_label"]; var videoQuality = Heuristics.VideoQualityFromLabel(videoQualityLabel); // Extract resolution var width = streamInfoDic["size"].SubstringUntil("x").ParseInt(); var height = streamInfoDic["size"].SubstringAfter("x").ParseInt(); var resolution = new VideoResolution(width, height); // Extract framerate var framerate = streamInfoDic["fps"].ParseInt(); // Add to list videoStreamInfoMap[itag] = new VideoStreamInfo(itag, url, container, contentLength, bitrate, videoEncoding, videoQualityLabel, videoQuality, resolution, framerate); } } // Get dash manifest var dashManifestUrl = playerConfiguration.DashManifestUrl; if (!dashManifestUrl.IsNullOrWhiteSpace()) { // Extract signature var signature = Regex.Match(dashManifestUrl, "/s/(.*?)(?:/|$)").Groups[1].Value; // Decipher signature if needed if (!signature.IsNullOrWhiteSpace()) { // Get cipher operations (cached) var cipherOperations = await GetCipherOperationsAsync(playerConfiguration.PlayerSourceUrl).ConfigureAwait(false); // Decipher signature signature = cipherOperations.Decipher(signature); // Set the corresponding parameter in the URL dashManifestUrl = Url.SetRouteParameter(dashManifestUrl, "signature", signature); } // Get DASH manifest XML var dashManifestXml = await GetDashManifestXmlAsync(dashManifestUrl).ConfigureAwait(false); // Get representation nodes (skip partial streams) var streamInfoXmls = dashManifestXml.Descendants("Representation").Where(s => s.Descendants("Initialization").FirstOrDefault()?.Attribute("sourceURL")?.Value.Contains("sq/") != true); // Get DASH stream infos foreach (var streamInfoXml in streamInfoXmls) { // Extract info var itag = (int)streamInfoXml.Attribute("id"); var url = (string)streamInfoXml.Element("BaseURL"); var contentLength = Regex.Match(url, @"clen[/=](\d+)").Groups[1].Value.ParseLong(); var bitrate = (long)streamInfoXml.Attribute("bandwidth"); // Extract container var containerRaw = Regex.Match(url, @"mime[/=]\w*%2F([\w\d]*)").Groups[1].Value.UrlDecode(); var container = Heuristics.ContainerFromString(containerRaw); // If audio-only if (streamInfoXml.Element("AudioChannelConfiguration") != null) { // Extract audio encoding var audioEncodingRaw = (string)streamInfoXml.Attribute("codecs"); var audioEncoding = Heuristics.AudioEncodingFromString(audioEncodingRaw); // Add to list audioStreamInfoMap[itag] = new AudioStreamInfo(itag, url, container, contentLength, bitrate, audioEncoding); } // If video-only else { // Extract video encoding var videoEncodingRaw = (string)streamInfoXml.Attribute("codecs"); var videoEncoding = Heuristics.VideoEncodingFromString(videoEncodingRaw); // Extract resolution var width = (int)streamInfoXml.Attribute("width"); var height = (int)streamInfoXml.Attribute("height"); var resolution = new VideoResolution(width, height); // Extract framerate var framerate = (int)streamInfoXml.Attribute("frameRate"); // Determine video quality from itag var videoQuality = Heuristics.VideoQualityFromItag(itag); // Determine video quality label from video quality and framerate var videoQualityLabel = Heuristics.VideoQualityToLabel(videoQuality, framerate); // Add to list videoStreamInfoMap[itag] = new VideoStreamInfo(itag, url, container, contentLength, bitrate, videoEncoding, videoQualityLabel, videoQuality, resolution, framerate); } } } // Finalize stream info collections var muxedStreamInfos = muxedStreamInfoMap.Values.OrderByDescending(s => s.VideoQuality).ToArray(); var audioStreamInfos = audioStreamInfoMap.Values.OrderByDescending(s => s.Bitrate).ToArray(); var videoStreamInfos = videoStreamInfoMap.Values.OrderByDescending(s => s.VideoQuality).ToArray(); return(new MediaStreamInfoSet(muxedStreamInfos, audioStreamInfos, videoStreamInfos, playerConfiguration.HlsManifestUrl, playerConfiguration.ValidUntil)); }
public static bool ContainsResolution(this IEnumerable <VideoResolution> available, VideoResolution target) { if (available == null || target == null) { return(false); } else { return(available.FirstOrDefault(VR => VR.Height == target.Height && VR.Width == target.Width) != null); } }
/// <inheritdoc /> public async Task <MediaStreamInfoSet> GetVideoMediaStreamInfosAsync(string videoId) { videoId.GuardNotNull(nameof(videoId)); if (!ValidateVideoId(videoId)) { throw new ArgumentException($"Invalid YouTube video ID [{videoId}].", nameof(videoId)); } // Get player context var playerContext = await GetVideoPlayerContextAsync(videoId).ConfigureAwait(false); // Get video info var videoInfo = await GetVideoInfoAsync(videoId, playerContext.Sts).ConfigureAwait(false); // Check if requires purchase if (videoInfo.ContainsKey("ypc_vid")) { var previewVideoId = videoInfo["ypc_vid"]; throw new VideoRequiresPurchaseException(videoId, previewVideoId); } // Prepare stream info collections var muxedStreamInfoMap = new Dictionary <int, MuxedStreamInfo>(); var audioStreamInfoMap = new Dictionary <int, AudioStreamInfo>(); var videoStreamInfoMap = new Dictionary <int, VideoStreamInfo>(); // Resolve muxed streams var muxedStreamInfosEncoded = videoInfo.GetOrDefault("url_encoded_fmt_stream_map"); if (muxedStreamInfosEncoded.IsNotBlank()) { foreach (var streamEncoded in muxedStreamInfosEncoded.Split(",")) { var streamInfoDic = UrlEx.SplitQuery(streamEncoded); // Extract values var itag = streamInfoDic["itag"].ParseInt(); var url = streamInfoDic["url"]; var sig = streamInfoDic.GetOrDefault("s"); #if RELEASE if (!MediaStreamInfo.IsKnown(itag)) { continue; } #endif // Decipher signature if needed if (sig.IsNotBlank()) { var playerSource = await GetVideoPlayerSourceAsync(playerContext.SourceUrl).ConfigureAwait(false); sig = playerSource.Decipher(sig); url = UrlEx.SetQueryParameter(url, "signature", sig); } // Probe stream and get content length var contentLength = await _httpClient.GetContentLengthAsync(url, false).ConfigureAwait(false) ?? -1; // If probe failed, the stream is gone or faulty if (contentLength < 0) { continue; } var streamInfo = new MuxedStreamInfo(itag, url, contentLength); muxedStreamInfoMap[itag] = streamInfo; } } // Resolve adaptive streams var adaptiveStreamInfosEncoded = videoInfo.GetOrDefault("adaptive_fmts"); if (adaptiveStreamInfosEncoded.IsNotBlank()) { foreach (var streamEncoded in adaptiveStreamInfosEncoded.Split(",")) { var streamInfoDic = UrlEx.SplitQuery(streamEncoded); // Extract values var itag = streamInfoDic["itag"].ParseInt(); var url = streamInfoDic["url"]; var sig = streamInfoDic.GetOrDefault("s"); var contentLength = streamInfoDic["clen"].ParseLong(); var bitrate = streamInfoDic["bitrate"].ParseLong(); #if RELEASE if (!MediaStreamInfo.IsKnown(itag)) { continue; } #endif // Decipher signature if needed if (sig.IsNotBlank()) { var playerSource = await GetVideoPlayerSourceAsync(playerContext.SourceUrl).ConfigureAwait(false); sig = playerSource.Decipher(sig); url = UrlEx.SetQueryParameter(url, "signature", sig); } // Check if audio var isAudio = streamInfoDic["type"].Contains("audio/"); // If audio stream if (isAudio) { var streamInfo = new AudioStreamInfo(itag, url, contentLength, bitrate); audioStreamInfoMap[itag] = streamInfo; } // If video stream else { // Parse additional data var size = streamInfoDic["size"]; var width = size.SubstringUntil("x").ParseInt(); var height = size.SubstringAfter("x").ParseInt(); var resolution = new VideoResolution(width, height); var framerate = streamInfoDic["fps"].ParseInt(); var qualityLabel = streamInfoDic["quality_label"]; var streamInfo = new VideoStreamInfo(itag, url, contentLength, bitrate, resolution, framerate, qualityLabel); videoStreamInfoMap[itag] = streamInfo; } } } // Resolve dash streams var dashManifestUrl = videoInfo.GetOrDefault("dashmpd"); if (dashManifestUrl.IsNotBlank()) { // Parse signature var sig = Regex.Match(dashManifestUrl, @"/s/(.*?)(?:/|$)").Groups[1].Value; // Decipher signature if needed if (sig.IsNotBlank()) { var playerSource = await GetVideoPlayerSourceAsync(playerContext.SourceUrl).ConfigureAwait(false); sig = playerSource.Decipher(sig); dashManifestUrl = UrlEx.SetRouteParameter(dashManifestUrl, "signature", sig); } // Get the manifest var response = await _httpClient.GetStringAsync(dashManifestUrl).ConfigureAwait(false); var dashManifestXml = XElement.Parse(response).StripNamespaces(); var streamsXml = dashManifestXml.Descendants("Representation"); // Parse streams foreach (var streamXml in streamsXml) { // Skip partial streams if (streamXml.Descendants("Initialization").FirstOrDefault()?.Attribute("sourceURL")?.Value .Contains("sq/") == true) { continue; } // Extract values var itag = (int)streamXml.Attribute("id"); var url = (string)streamXml.Element("BaseURL"); var bitrate = (long)streamXml.Attribute("bandwidth"); #if RELEASE if (!MediaStreamInfo.IsKnown(itag)) { continue; } #endif // Parse content length var contentLength = Regex.Match(url, @"clen[/=](\d+)").Groups[1].Value.ParseLong(); // Check if audio stream var isAudio = streamXml.Element("AudioChannelConfiguration") != null; // If audio stream if (isAudio) { var streamInfo = new AudioStreamInfo(itag, url, contentLength, bitrate); audioStreamInfoMap[itag] = streamInfo; } // If video stream else { // Parse additional data var width = (int)streamXml.Attribute("width"); var height = (int)streamXml.Attribute("height"); var resolution = new VideoResolution(width, height); var framerate = (int)streamXml.Attribute("frameRate"); var streamInfo = new VideoStreamInfo(itag, url, contentLength, bitrate, resolution, framerate); videoStreamInfoMap[itag] = streamInfo; } } } // Get the raw HLS stream playlist (*.m3u8) var hlsLiveStreamUrl = videoInfo.GetOrDefault("hlsvp"); // Finalize stream info collections var muxedStreamInfos = muxedStreamInfoMap.Values.OrderByDescending(s => s.VideoQuality).ToArray(); var audioStreamInfos = audioStreamInfoMap.Values.OrderByDescending(s => s.Bitrate).ToArray(); var videoStreamInfos = videoStreamInfoMap.Values.OrderByDescending(s => s.VideoQuality).ToArray(); return(new MediaStreamInfoSet(muxedStreamInfos, audioStreamInfos, videoStreamInfos, hlsLiveStreamUrl)); }
public static void Init(string devKey, string devSecret, string appName, DeviceOrientation deviceOrientation, VideoResolution videoResolution) { #if UNITY_IPHONE // Call plugin only when running on real device if (Application.platform == RuntimePlatform.IPhonePlayer) { Debug.Log ("Kamcord.Init"); if (orientationWasPreviouslySet) { deviceOrientation = Kamcord.GetDeviceOrientation(); Debug.Log ("Setting device orientation to old orientation: " + deviceOrientation); } _KamcordInit(devKey, devSecret, appName, deviceOrientation.ToString(), videoResolution.ToString()); } else #endif { Debug.Log ("[NOT CALLED] Kamcord.Init"); } }
/// <summary> /// Set video resolution. /// </summary> /// /// <param name="resolution">Video resolution to set.</param> /// /// <remarks> /// <para><note>Setting higher <see cref="SetQuality">quality level</see> and resolution /// may increase delays for other requests sent to SRV-1. So if /// robot is used not only for video, but also for controlling servos/motors, and higher /// response level is required, then do not set very high quality and resolution. /// </note></para> /// </remarks> /// /// <exception cref="ArgumentOutOfRangeException">Invalid resolution was specified.</exception> /// public void SetResolution( VideoResolution resolution ) { if ( !Enum.IsDefined( typeof( VideoResolution ), resolution ) ) { throw new ArgumentException( "Invalid resolution was specified." ); } Send( new byte[] { (byte) resolution } ); }