vdr/player.h
Klaus Schmidinger ec0ec6da01 Version 2.3.2
Merry Christmas to all VDR users!

It's been a very busy year for me, in which I was unable to
spend as much time on VDR as I would have liked to. But now things
are settled again and I managed to prepare a new developer version
with the most important fixes and improvements. Please feel free
to tell me if I missed something important - some things may well
have slipped under my radar ;-).

So here's my Christmas gift for you!

VDR developer version 2.3.2 is now available at

       ftp://ftp.tvdr.de/vdr/Developer/vdr-2.3.2.tar.bz2

A 'diff' against the previous version is available at

       ftp://ftp.tvdr.de/vdr/Developer/vdr-2.3.1-2.3.2.diff

MD5 checksums:

6dbb208ea3d59658a18912b49af175b3  vdr-2.3.2.tar.bz2
68a0ed9f01048026333939d30e0a6474  vdr-2.3.1-2.3.2.diff

WARNING:
========

This is a *developer* version. Even though *I* use it in my productive
environment, I strongly recommend that you only use it under controlled
conditions and for testing and debugging.

From the HISTORY file:
- Fixed a crash when deleting a recording (reported by Oliver Endriss).
- Fixed an overflow of PIDs in a receiver (thanks to Robert Hannebauer).
- Updated the Italian OSD texts (thanks to Diego Pierotto).
- Fixed initializing device specific parameters in cDvbTransponderParameters.
- The function SetCurrentChannel(const cChannel *Channel) is now deprecated and
  may be removed in a future version. Use SetCurrentChannel(int ChannelNumber)
  instead.
- The SVDRP command DELC now refuses to delete the very last channel in the list,
  to avoid ending up with an empty channel list.
- The cRwLock class now allows nested read locks within a write lock from the
  same thread. This fixes possible crashes when moving or deleting channels in
  the menu or through SVDRP (as well as other operations that try to acquire a
  read lock within a write lock).
- Fixed a crash when trying to delete a channel that is being used by a timer.
- Fixed setting the current item and counter values in the Recordings menu after
  deleting the last recording in a subfolder.
- Fixed a crash when deleting a recording that is currently being replayed.
- Fixed a crash when moving a recording to a folder on a different volume.
  The cRecordingsHandler now performs its actual operations in a separate thread,
  thus avoiding locking problems and reducing the time between subsequent
  operations.
- Added a note to the description of cFont::Size(), regarding possible differences
  between it and cFont::Height() (suggested to Thomas Reufer).
- Made the cPlayer member functions FramesPerSecond, GetIndex and GetReplayMode
  'const' (thanks to Thomas Reufer).
- Fixed resuming replay at a given position, which was off by one frame (thanks
  to Thomas Reufer).
- Improved handling frame numbers to have a smoother progress display during
  replay of recordings with B-frames (thanks to Thomas Reufer).
- Fixed replaying recordings to their very end, if they don't end with an I-frame
  (thanks to Thomas Reufer).
- Implemented a frame parser for H.265 (HEVC) recordings (thanks to Thomas Reufer).
- Added cFont::Width(void) to get the default character width and allow stretched
  font drawing in high level OSDs (thanks to Thomas Reufer).
- Fixed regenerating the index of audio recordings (thanks to Thomas Reufer).
- Fixed building VDR with systemd >= 230 (thanks to Ville Skyttä).
- Sorted sources.conf by continous azimuth (thanks to Lucian Muresan).
- Added 'S58.5E Kazsat 3' to sources.conf (thanks to Aitugan Sarbassov).
- Fixed truncated date/time strings in the skins on multi-byte UTF-8 systems
  (reported by Sergey Chernyavskiy).
- Updated the Estonian OSD texts (thanks to Arthur Konovalov).
- Added a 'const' version of cTimers::GetTimer() (thanks to Lars Hanisch).
- Fixed a typo in the description of cTimers::GetTimersRead() (thanks to Lars
  Hanisch).
- Fixed a possible buffer overflow in handling CA descriptors (suggested by
  Lars Hanisch).
- Avoiding some duplicate code and unnecessary work in nit.c (thanks to Ville
  Skyttä).
- Added support for the systemd watchdog (thanks to Marc Perrudin),
- Added a short sleep to cTSBuffer::Action() to avoid high CPU usage (thanks to
  Sergey Chernyavskiy).
2017-02-01 00:05:46 +01:00

119 lines
6.4 KiB
C++

/*
* player.h: The basic player interface
*
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
* $Id: player.h 4.2 2016/12/22 10:38:11 kls Exp $
*/
#ifndef __PLAYER_H
#define __PLAYER_H
#include "device.h"
#include "osdbase.h"
class cPlayer {
friend class cDevice;
private:
cDevice *device;
ePlayMode playMode;
protected:
void DeviceClrAvailableTracks(bool DescriptionsOnly = false) { if (device) device->ClrAvailableTracks(DescriptionsOnly); }
bool DeviceSetAvailableTrack(eTrackType Type, int Index, uint16_t Id, const char *Language = NULL, const char *Description = NULL) { return device ? device->SetAvailableTrack(Type, Index, Id, Language, Description) : false; }
bool DeviceSetCurrentAudioTrack(eTrackType Type) { return device ? device->SetCurrentAudioTrack(Type) : false; }
bool DeviceSetCurrentSubtitleTrack(eTrackType Type) { return device ? device->SetCurrentSubtitleTrack(Type) : false; }
bool DevicePoll(cPoller &Poller, int TimeoutMs = 0) { return device ? device->Poll(Poller, TimeoutMs) : false; }
bool DeviceFlush(int TimeoutMs = 0) { return device ? device->Flush(TimeoutMs) : true; }
bool DeviceHasIBPTrickSpeed(void) { return device ? device->HasIBPTrickSpeed() : false; }
bool DeviceIsPlayingVideo(void) { return device ? device->IsPlayingVideo() : false; }
void DeviceTrickSpeed(int Speed, bool Forward) { if (device) device->TrickSpeed(Speed, Forward); }
void DeviceClear(void) { if (device) device->Clear(); }
void DevicePlay(void) { if (device) device->Play(); }
void DeviceFreeze(void) { if (device) device->Freeze(); }
void DeviceMute(void) { if (device) device->Mute(); }
void DeviceSetVideoDisplayFormat(eVideoDisplayFormat VideoDisplayFormat) { if (device) device->SetVideoDisplayFormat(VideoDisplayFormat); }
void DeviceStillPicture(const uchar *Data, int Length) { if (device) device->StillPicture(Data, Length); }
uint64_t DeviceGetSTC(void) { return device ? device->GetSTC() : -1; }
void Detach(void);
virtual void Activate(bool On) {}
// This function is called right after the cPlayer has been attached to
// (On == true) or before it gets detached from (On == false) a cDevice.
// It can be used to do things like starting/stopping a thread.
int PlayPes(const uchar *Data, int Length, bool VideoOnly = false);
// Sends the given PES Data to the device and returns the number of
// bytes that have actually been accepted by the device (or a
// negative value in case of an error).
int PlayTs(const uchar *Data, int Length, bool VideoOnly = false) { return device ? device->PlayTs(Data, Length, VideoOnly) : -1; }
// Sends the given TS packet to the device and returns a positive number
// if the packet has been accepted by the device, or a negative value in
// case of an error.
public:
cPlayer(ePlayMode PlayMode = pmAudioVideo);
virtual ~cPlayer();
bool IsAttached(void) { return device != NULL; }
virtual double FramesPerSecond(void) { return DEFAULTFRAMESPERSECOND; }
// Returns the number of frames per second of the currently played material.
virtual bool GetIndex(int &Current, int &Total, bool SnapToIFrame = false) { return false; }
// Returns the current and total frame index, optionally snapped to the
// nearest I-frame.
virtual bool GetFrameNumber(int &Current, int &Total) { return false; }
// Returns the current and total frame number. In contrast to GetIndex(),
// this function respects the chronological order of frames, which is
// different from its index for streams containing B frames (e.g. H264)
virtual bool GetReplayMode(bool &Play, bool &Forward, int &Speed) { return false; }
// Returns the current replay mode (if applicable).
// 'Play' tells whether we are playing or pausing, 'Forward' tells whether
// we are going forward or backward and 'Speed' is -1 if this is normal
// play/pause mode, 0 if it is single speed fast/slow forward/back mode
// and >0 if this is multi speed mode.
virtual void SetAudioTrack(eTrackType Type, const tTrackId *TrackId) {}
// Sets the current audio track to the given value.
// This is just a virtual hook for players that need to do special things
// in order to switch audio tracks.
virtual void SetSubtitleTrack(eTrackType Type, const tTrackId *TrackId) {}
// Sets the current subtitle track to the given value.
// This is just a virtual hook for players that need to do special things
// in order to switch subtitle tracks.
};
class cControl : public cOsdObject {
private:
static cControl *control;
static cMutex mutex;
bool attached;
bool hidden;
protected:
cPlayer *player;
public:
cControl(cPlayer *Player, bool Hidden = false);
virtual ~cControl();
virtual void Hide(void) = 0;
virtual cOsdObject *GetInfo(void);
///< Returns an OSD object that displays information about the currently
///< played programme. If no such information is available, NULL will be
///< returned.
virtual const cRecording *GetRecording(void);
///< Returns the cRecording that is currently being replayed, or NULL if
///< this player is not playing a cRecording.
virtual cString GetHeader(void);
///< This can be used by players that don't play a cRecording, but rather
///< do something completely different. The resulting string may be used by
///< skins as a last resort, in case they want to display the state of the
///< current player. The return value is expected to be a short, single line
///< string. The default implementation returns an empty string.
double FramesPerSecond(void) const { return player->FramesPerSecond(); }
bool GetIndex(int &Current, int &Total, bool SnapToIFrame = false) const { return player->GetIndex(Current, Total, SnapToIFrame); }
bool GetFrameNumber(int &Current, int &Total) const { return player->GetFrameNumber(Current, Total); }
bool GetReplayMode(bool &Play, bool &Forward, int &Speed) const { return player->GetReplayMode(Play, Forward, Speed); }
static void Launch(cControl *Control);
static void Attach(void);
static void Shutdown(void);
static cControl *Control(bool Hidden = false);
///< Returns the current replay control (if any) in case it is currently
///< visible. If Hidden is true, the control will be returned even if it is
///< currently hidden.
};
#endif //__PLAYER_H