/// <summary> /// Beendet die Aufzeichnung in eine Datei. /// </summary> public void CloseStream() { // Load using (var stream = m_TransportStream) { // Wipe out m_TransportStream = null; // Reset time LastActivationTime = null; // Forget current settings ActiveSelection = null; // Nothing more to do if (null == stream) { return; } // Increment file counter ++m_FileCount; // Stop EPG receiver Hardware.RemoveProgramGuideConsumer(DispatchEPG); // Stop all consumers foreach (var consumer in m_Consumers) { try { // Try to stop the individual stream Hardware.SetConsumerState(consumer, null); } catch { // Ignore any error } } // Forget consumers m_Consumers.Clear(); // Send all the rest to the file (if any) stream.Flush(); // Update byte count BytesBias += stream.Length; } }
/// <summary> /// Beginnt die Aufzeichnung in einen <i>Transport Stream</i> - optional als /// Datei. /// </summary> /// <param name="nextPID">Die erste Datenstromkennung (PID), die in der Aufzeichnungsdatei verwendet werden darf.</param> /// <param name="recreate">Gesetzt, wenn ein Neustart aufgrund veränderter Nutzdatenströme erforderlich wurde.</param> /// <exception cref="ArgumentException">Eine Aufzeichnung der angegebenen Quelle ist nicht möglich.</exception> private void CreateStream(short nextPID, bool recreate) { // Try to get the full name var filePath = m_OriginalPath; if (filePath != null) { if (m_FileCount > 0) { // Split off the parts var name = Path.GetFileNameWithoutExtension(filePath); var dir = Path.GetDirectoryName(filePath); var ext = Path.GetExtension(filePath); // Construct new name filePath = Path.Combine(dir, $"{name} - {m_FileCount}{ext}"); } } // Try to decrypt if (m_Decrypting = m_OriginalSettings.IsEncrypted) { try { // Process Hardware.Decrypt(Source); } catch { // Ignore any error m_Decrypting = false; } } // Type of the video EPG.StreamTypes?videoType; // Video first if (m_OriginalSettings.VideoStream == 0) { videoType = null; } else { videoType = (m_OriginalSettings.VideoType == VideoTypes.H264) ? EPG.StreamTypes.H264 : EPG.StreamTypes.Video13818; } // Get the buffer size var bufferSize = (FileBufferSizeChooser == null) ? null : FileBufferSizeChooser(videoType); // Create the new stream m_TransportStream = new Manager(filePath, nextPID, bufferSize.GetValueOrDefault(Manager.DefaultBufferSize)); // Attach PCR sink m_TransportStream.OnWritingPCR = m_WritePCRSink; // Report of the actually selected streams StreamSelection result = new StreamSelection(); // Cleanup on any error try { // Video first if (videoType.HasValue) { AddConsumer(m_OriginalSettings.VideoStream, StreamTypes.Video, m_TransportStream.AddVideo((byte)videoType.Value)); } // Select audio ProcessAudioSelection(AudioTypes.MP2, result.MP2Tracks, StreamSelection.MP2Tracks); ProcessAudioSelection(AudioTypes.AC3, result.AC3Tracks, StreamSelection.AC3Tracks); // Videotext if (StreamSelection.Videotext) { if (0 != m_OriginalSettings.TextStream) { // Register AddConsumer(m_OriginalSettings.TextStream, StreamTypes.VideoText, m_TransportStream.AddTeleText()); // Remember result.Videotext = true; } } // Subtitle streams var subtitles = new Dictionary <ushort, List <EPG.SubtitleInfo> >(); // Preset mode result.SubTitles.LanguageMode = LanguageModes.All; // All audio // Subtitles foreach (var subtitle in m_OriginalSettings.Subtitles) { // Check for primary if (StreamSelection.SubTitles.LanguageMode == LanguageModes.Primary) { // Attach to the list AddSubtitleInformation(subtitle, subtitles); // Copy over result.SubTitles.LanguageMode = LanguageModes.Primary; // Remember result.SubTitles.Languages.Add(subtitle.Language); // Done break; } // Standard selection if (StreamSelection.SubTitles.Contains(subtitle.Language)) { // Attach to the list AddSubtitleInformation(subtitle, subtitles); // Remember result.SubTitles.Languages.Add(subtitle.Language); } else { // At least one is excluded result.SubTitles.LanguageMode = LanguageModes.Selection; } } // Clear flag if no audio is used if (LanguageModes.All == result.SubTitles.LanguageMode) { if (result.SubTitles.Languages.Count < 1) { result.SubTitles.LanguageMode = LanguageModes.Selection; } } // Process all subtitles foreach (var current in subtitles) { AddConsumer(current.Key, StreamTypes.SubTitle, m_TransportStream.AddSubtitles(current.Value.ToArray())); } // See if program guide is requested bool epg = StreamSelection.ProgramGuide; // May want to disable if (epg) { if ((Hardware.Profile != null) && Hardware.Profile.DisableProgramGuide) { epg = false; } else if (Profile != null) { if (Profile.GetFilter(Source).DisableProgramGuide) { epg = false; } } } // EPG if (epg) { // Activate dispatch m_TransportStream.SetEPGMapping(Source.Network, Source.TransportStream, Source.Service); // Start it Hardware.AddProgramGuideConsumer(DispatchEPG); // Remember result.ProgramGuide = true; } // Counter int started = 0; try { // Start all foreach (var consumer in m_Consumers) { try { // Forward Hardware.SetConsumerState(consumer, true); // Count it ++started; } catch (OutOfConsumersException) { // Translate throw new OutOfConsumersException(m_Consumers.Count, started) { RequestedSelection = result }; } } } catch { // Detach EPG Hardware.RemoveProgramGuideConsumer(DispatchEPG); // Cleanup on all errors foreach (var consumer in m_Consumers) { try { // Remove Hardware.SetConsumerState(consumer, null); } catch { // Ignore any error } } // Forward throw; } // Remember path if (filePath != null) { m_AllFiles.Add(new FileStreamInformation { FilePath = filePath, VideoType = m_OriginalSettings.VideoType }); } // Remember the time LastActivationTime = DateTime.UtcNow; } catch { // Simply forget m_TransportStream.Dispose(); m_TransportStream = null; // Forward throw; } // Get the next free PID NextStreamIdentifier = m_TransportStream.NextPID; // Remember the streams we use ActiveSelection = result; // Attach to clients var createNotify = OnCreatedStream; // Report if (createNotify != null) { createNotify(this); } }