290 lines
9.5 KiB
C#
290 lines
9.5 KiB
C#
//////////////////////////////////////////////////////////////////////////////////
|
|
// //
|
|
// Copyright © 2005-2020 nzsjb //
|
|
// //
|
|
// This Program is free software; you can redistribute it and/or modify //
|
|
// it under the terms of the GNU General Public License as published by //
|
|
// the Free Software Foundation; either version 2, or (at your option) //
|
|
// any later version. //
|
|
// //
|
|
// This Program is distributed in the hope that it will be useful, //
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of //
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the //
|
|
// GNU General Public License for more details. //
|
|
// //
|
|
// You should have received a copy of the GNU General Public License //
|
|
// along with GNU Make; see the file COPYING. If not, write to //
|
|
// the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. //
|
|
// http://www.gnu.org/copyleft/gpl.html //
|
|
// //
|
|
//////////////////////////////////////////////////////////////////////////////////
|
|
|
|
using System;
|
|
using System.Collections.ObjectModel;
|
|
|
|
using DomainObjects;
|
|
|
|
namespace DVBServices
|
|
{
|
|
/// <summary>
|
|
/// The class that describes Open TV title data.
|
|
/// </summary>
|
|
public class OpenTVTitleData
|
|
{
|
|
/// <summary>
|
|
/// Get the event identification.
|
|
/// </summary>
|
|
public int EventID { get { return (eventID); } }
|
|
|
|
/// <summary>
|
|
/// Get the start time of the event.
|
|
/// </summary>
|
|
public DateTime StartTime
|
|
{
|
|
get
|
|
{
|
|
OpenTVTitleDataRecord record = (OpenTVTitleDataRecord)getRecord(OpenTVTitleDataRecord.TagValue);
|
|
return (baseDate + record.StartTimeOffset);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Get the duration of the event.
|
|
/// </summary>
|
|
public TimeSpan Duration
|
|
{
|
|
get
|
|
{
|
|
OpenTVTitleDataRecord record = (OpenTVTitleDataRecord)getRecord(OpenTVTitleDataRecord.TagValue);
|
|
return (record.Duration);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Get the theme identification of the event.
|
|
/// </summary>
|
|
public int CategoryID
|
|
{
|
|
get
|
|
{
|
|
OpenTVTitleDataRecord record = (OpenTVTitleDataRecord)getRecord(OpenTVTitleDataRecord.TagValue);
|
|
return (record.CategoryID);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Get the name of the event.
|
|
/// </summary>
|
|
public string EventName
|
|
{
|
|
get
|
|
{
|
|
OpenTVTitleDataRecord record = (OpenTVTitleDataRecord)getRecord(OpenTVTitleDataRecord.TagValue);
|
|
return (record.DecodedEventName);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Get the raw bytes of the event name.
|
|
/// </summary>
|
|
public byte[] EventNameBytes
|
|
{
|
|
get
|
|
{
|
|
OpenTVTitleDataRecord record = (OpenTVTitleDataRecord)getRecord(OpenTVTitleDataRecord.TagValue);
|
|
return (record.EventName);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Get the flags field of the event.
|
|
/// </summary>
|
|
public byte[] Flags
|
|
{
|
|
get
|
|
{
|
|
OpenTVTitleDataRecord record = (OpenTVTitleDataRecord)getRecord(OpenTVTitleDataRecord.TagValue);
|
|
return (record.Flags);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Get the collection of records for this title section.
|
|
/// </summary>
|
|
internal Collection<OpenTVRecordBase> Records
|
|
{
|
|
get
|
|
{
|
|
if (records == null)
|
|
records = new Collection<OpenTVRecordBase>();
|
|
return (records);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Get the collection of undefined records for this title section.
|
|
/// </summary>
|
|
internal Collection<OpenTVRecordBase> UndefinedRecords
|
|
{
|
|
get
|
|
{
|
|
if (records == null)
|
|
return (null);
|
|
|
|
Collection<OpenTVRecordBase> undefinedRecords = new Collection<OpenTVRecordBase>();
|
|
|
|
foreach (OpenTVRecordBase record in records)
|
|
{
|
|
if (record.IsUndefined)
|
|
undefinedRecords.Add(record);
|
|
}
|
|
|
|
return (undefinedRecords);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Return true if the entry is empty; false otherwise.
|
|
/// </summary>
|
|
public bool IsEmpty { get { return (records == null || records.Count == 0); } }
|
|
|
|
/// <summary>
|
|
/// Get the PID of the section containing the data.
|
|
/// </summary>
|
|
public int PID { get { return (pid); } }
|
|
/// <summary>
|
|
/// Get the table ID of the section containing the data.
|
|
/// </summary>
|
|
public int Table { get { return (table); } }
|
|
/// <summary>
|
|
/// Get the timestamp when the data arrived.
|
|
/// </summary>
|
|
public DateTime TimeStamp { get { return (timeStamp); } }
|
|
|
|
/// <summary>
|
|
/// Get the index of the next byte in the MPEG2 section following the title data.
|
|
/// </summary>
|
|
/// <exception cref="InvalidOperationException">
|
|
/// The title data has not been processed.
|
|
/// </exception>
|
|
public int Index
|
|
{
|
|
get
|
|
{
|
|
if (lastIndex == -1)
|
|
throw (new InvalidOperationException("OpenTVTitleData: Index requested before block processed"));
|
|
return (lastIndex);
|
|
}
|
|
}
|
|
|
|
private int eventID;
|
|
private int length;
|
|
|
|
private DateTime baseDate;
|
|
|
|
private int pid;
|
|
private int table;
|
|
private DateTime timeStamp;
|
|
|
|
private Collection<OpenTVRecordBase> records;
|
|
|
|
private int lastIndex = -1;
|
|
|
|
/// <summary>
|
|
/// Initialize a new instance of the OpenTVTitleData class.
|
|
/// </summary>
|
|
public OpenTVTitleData() { }
|
|
|
|
/// <summary>
|
|
/// Parse the title data.
|
|
/// </summary>
|
|
/// <param name="byteData">The MPEG2 section containing the title data.</param>
|
|
/// <param name="index">Index of the first byte of the title data in the MPEG2 section.</param>
|
|
/// <param name="baseDate">The base date for the programs.</param>
|
|
/// <param name="channel">The channel for the data.</param>
|
|
/// <param name="pid">The PID of the section.</param>
|
|
/// <param name="table">The table ID of the section.</param>
|
|
internal void Process(byte[] byteData, int index, DateTime baseDate, int channel, int pid, int table)
|
|
{
|
|
lastIndex = index;
|
|
|
|
this.pid = pid;
|
|
this.table = table;
|
|
this.baseDate = baseDate;
|
|
|
|
try
|
|
{
|
|
eventID = Utils.Convert2BytesToInt(byteData, lastIndex);
|
|
lastIndex += 2;
|
|
|
|
length = ((byteData[lastIndex] & 0x0f) * 256) + byteData[lastIndex + 1];
|
|
lastIndex += 2;
|
|
|
|
int recordLength = length;
|
|
|
|
while (recordLength != 0)
|
|
{
|
|
OpenTVRecordBase record = OpenTVRecordBase.Instance(byteData, lastIndex);
|
|
Records.Add(record);
|
|
|
|
lastIndex += record.TotalLength;
|
|
recordLength -= record.TotalLength;
|
|
}
|
|
|
|
timeStamp = DateTime.Now;
|
|
|
|
Validate();
|
|
}
|
|
catch (IndexOutOfRangeException)
|
|
{
|
|
throw (new ArgumentOutOfRangeException("lastIndex = " + lastIndex));
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Validate the title data fields.
|
|
/// </summary>
|
|
/// <exception cref="ArgumentOutOfRangeException">
|
|
/// A title data field is not valid.
|
|
/// </exception>
|
|
public void Validate() { }
|
|
|
|
/// <summary>
|
|
/// Log the title data fields.
|
|
/// </summary>
|
|
public void LogMessage()
|
|
{
|
|
if (Logger.ProtocolLogger == null)
|
|
return;
|
|
|
|
Logger.ProtocolLogger.Write(Logger.ProtocolIndent + "OPENTV TITLE DATA: Event ID: " + eventID +
|
|
" Length: " + length);
|
|
|
|
if (records != null)
|
|
{
|
|
Logger.IncrementProtocolIndent();
|
|
|
|
foreach (OpenTVRecordBase record in records)
|
|
record.LogMessage();
|
|
|
|
Logger.DecrementProtocolIndent();
|
|
}
|
|
}
|
|
|
|
private OpenTVRecordBase getRecord(int tag)
|
|
{
|
|
if (records == null)
|
|
return(null);
|
|
|
|
foreach (OpenTVRecordBase record in records)
|
|
{
|
|
if (record.Tag == tag)
|
|
return(record);
|
|
}
|
|
|
|
return(null);
|
|
}
|
|
}
|
|
}
|
|
|