mirror of
https://github.com/VDR4Arch/vdr.git
synced 2023-10-10 13:36:52 +02:00
Implemented audio track menu
This commit is contained in:
parent
286af66cfb
commit
0b3a801ab4
16
HISTORY
16
HISTORY
@ -3160,7 +3160,7 @@ Video Disk Recorder Revision History
|
|||||||
right day of week for timers in the future.
|
right day of week for timers in the future.
|
||||||
- Some improvements to cPoller (thanks to Marco Schlüßler).
|
- Some improvements to cPoller (thanks to Marco Schlüßler).
|
||||||
|
|
||||||
2004-12-26: Version 1.3.18
|
2005-01-02: Version 1.3.18
|
||||||
|
|
||||||
- Removed an unused variable from cTimer::GetWDayFromMDay() (thanks to Wayne Keer
|
- Removed an unused variable from cTimer::GetWDayFromMDay() (thanks to Wayne Keer
|
||||||
for reporting this one).
|
for reporting this one).
|
||||||
@ -3251,3 +3251,17 @@ Video Disk Recorder Revision History
|
|||||||
Zocholl for pointing out this problem).
|
Zocholl for pointing out this problem).
|
||||||
- Added cDevice::mutexReceiver to avoid a race condition when attaching/detaching
|
- Added cDevice::mutexReceiver to avoid a race condition when attaching/detaching
|
||||||
receivers from different threads.
|
receivers from different threads.
|
||||||
|
- The new remote control button "Audio" can be used to switch between different
|
||||||
|
audio tracks. The "Green" button in the "Main" menu has been changed from "Language"
|
||||||
|
to "Audio", since it now also controls switching between normal and Dolby Digital
|
||||||
|
audio tracks.
|
||||||
|
- The description of the audio tracks is now taken from the "component descriptors"
|
||||||
|
that are broadcast in the EPG data. However (as no big surprise), not all channels
|
||||||
|
actually provide useful data here, so there are now some additional EPG bugfixes,
|
||||||
|
which can be activated by setting the "EPG bugfix level" to 3.
|
||||||
|
- The format of the 'epg.data' files has been extended by the new tag 'X', which
|
||||||
|
contains the stream components of an event (see man vdr(5) for details).
|
||||||
|
- The cStatus class now has the new member function SetAudioTrack(), which can be
|
||||||
|
used to get notified when the audio track has been switched.
|
||||||
|
- Skins need to implement the new cSkinDisplayTrack class to display the audio
|
||||||
|
track menu.
|
||||||
|
26
MANUAL
26
MANUAL
@ -21,7 +21,7 @@ Version 1.2
|
|||||||
Menu Menu on Menu off Menu off Menu off Menu off Menu off Menu on
|
Menu Menu on Menu off Menu off Menu off Menu off Menu off Menu on
|
||||||
Back - Menu off VDR menu VDR menu Discard VDR menu Recordings menu
|
Back - Menu off VDR menu VDR menu Discard VDR menu Recordings menu
|
||||||
Red - Record Edit Edit ABC/abc Play/Commands(2) Jump
|
Red - Record Edit Edit ABC/abc Play/Commands(2) Jump
|
||||||
Green - Language New New Ins/Ovr Rewind Skip -60s
|
Green - Audio New New Ins/Ovr Rewind Skip -60s
|
||||||
Yellow - Pause live Delete Delete Delete Delete Skip +60s
|
Yellow - Pause live Delete Delete Delete Delete Skip +60s
|
||||||
Blue - Stop/Resume Mark On/Off(1) - Summary Stop
|
Blue - Stop/Resume Mark On/Off(1) - Summary Stop
|
||||||
0..9 Ch select - Sort(3) Day(4) Numeric inp. Exec cmd(2) Editing
|
0..9 Ch select - Sort(3) Day(4) Numeric inp. Exec cmd(2) Editing
|
||||||
@ -49,6 +49,8 @@ Version 1.2
|
|||||||
Volume- volume down
|
Volume- volume down
|
||||||
Mute mute
|
Mute mute
|
||||||
|
|
||||||
|
Audio select audio track
|
||||||
|
|
||||||
Schedule \
|
Schedule \
|
||||||
Channels |
|
Channels |
|
||||||
Timers | directly access the VDR
|
Timers | directly access the VDR
|
||||||
@ -187,15 +189,16 @@ Version 1.2
|
|||||||
To bring up the channel display without switching channels you can press
|
To bring up the channel display without switching channels you can press
|
||||||
the "Ok" button.
|
the "Ok" button.
|
||||||
|
|
||||||
* Selecting language specific audio track
|
* Selecting audio tracks
|
||||||
|
|
||||||
If the current channel provides different audio tracks (typically for
|
If the current channel or recording provides different audio tracks (for
|
||||||
different languages), the "Green" button in the "VDR" menu can be pressed
|
different languages or Dolby Digital), the "Green" button in the "VDR" menu can
|
||||||
to toggle between these. There can be two different audio PIDs per channel,
|
be pressed to bring up the "Audio" menu. Within this menu, the "Up" and "Down"
|
||||||
assuming that typically a channel broadcasts a country specific language
|
keys can be used to switch between the audio tracks. If your remote control has
|
||||||
plus the movie's original soundtrack.
|
a dedicated "Audio" button, the first press of that button brings up the "Audio"
|
||||||
Recordings made form such channels will contain both audio tracks, and when
|
menu, and every further press switches to the next available audio track.
|
||||||
replaying the desired audio track can be selected the same way.
|
The "Audio" menu will automatically disappear after 5 seconds of user inactivity,
|
||||||
|
or if any key other than the ones described above is pressed.
|
||||||
|
|
||||||
* Switching through channel groups
|
* Switching through channel groups
|
||||||
|
|
||||||
@ -495,14 +498,15 @@ Version 1.2
|
|||||||
A value of '0' completely turns off scanning on both single
|
A value of '0' completely turns off scanning on both single
|
||||||
and multiple card systems.
|
and multiple card systems.
|
||||||
|
|
||||||
EPG bugfix level = 2 Some tv stations transmit weirdly formatted EPG data.
|
EPG bugfix level = 3 Some tv stations transmit weirdly formatted EPG data.
|
||||||
VDR attempts to fix these bugs up to the given level:
|
VDR attempts to fix these bugs up to the given level:
|
||||||
0 = no EPG fixing
|
0 = no EPG fixing
|
||||||
1 = basic fixing of text location (Title, Episode and
|
1 = basic fixing of text location (Title, Episode and
|
||||||
Extended Description)
|
Extended Description)
|
||||||
2 = removal of excess whitespace and hyphens, mapping of
|
2 = removal of excess whitespace and hyphens, mapping of
|
||||||
wrongly used characters
|
wrongly used characters
|
||||||
Default is '2'.
|
3 = fix stream component descriptions
|
||||||
|
Default is '3'.
|
||||||
Note that after changing the setting of this parameter
|
Note that after changing the setting of this parameter
|
||||||
any EPG data that has already been received will remain
|
any EPG data that has already been received will remain
|
||||||
in its existing format - only newly received data will
|
in its existing format - only newly received data will
|
||||||
|
@ -1362,6 +1362,9 @@ public:
|
|||||||
virtual cSkinDisplayMenu *DisplayMenu(void);
|
virtual cSkinDisplayMenu *DisplayMenu(void);
|
||||||
virtual cSkinDisplayReplay *DisplayReplay(bool ModeOnly);
|
virtual cSkinDisplayReplay *DisplayReplay(bool ModeOnly);
|
||||||
virtual cSkinDisplayVolume *DisplayVolume(void);
|
virtual cSkinDisplayVolume *DisplayVolume(void);
|
||||||
|
<!--X1.3.18--><table width=100%><tr><td bgcolor=#FF0000> </td><td width=100%>
|
||||||
|
virtual cSkinDisplayMessage *DisplayTrack(int NumTracks, const char * const *Tracks);
|
||||||
|
<!--X1.3.18--></td></tr></table>
|
||||||
virtual cSkinDisplayMessage *DisplayMessage(void);
|
virtual cSkinDisplayMessage *DisplayMessage(void);
|
||||||
};
|
};
|
||||||
</pre></td></tr></table><p>
|
</pre></td></tr></table><p>
|
||||||
|
@ -9,6 +9,7 @@ VDR Plugin 'skincurses' Revision History
|
|||||||
|
|
||||||
- Fixed some default parameters.
|
- Fixed some default parameters.
|
||||||
|
|
||||||
2004-12-26: Version 0.0.3
|
2005-01-02: Version 0.0.3
|
||||||
|
|
||||||
- Made several functions threadsafe.
|
- Made several functions threadsafe.
|
||||||
|
- New audio track display.
|
||||||
|
@ -3,7 +3,7 @@
|
|||||||
*
|
*
|
||||||
* See the README file for copyright information and how to reach the author.
|
* See the README file for copyright information and how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: skincurses.c 1.3 2004/12/26 11:36:35 kls Exp $
|
* $Id: skincurses.c 1.4 2005/01/02 15:11:29 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <ncurses.h>
|
#include <ncurses.h>
|
||||||
@ -558,6 +558,68 @@ void cSkinCursesDisplayVolume::Flush(void)
|
|||||||
osd->Flush();
|
osd->Flush();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// --- cSkinCursesDisplayTracks ----------------------------------------------
|
||||||
|
|
||||||
|
class cSkinCursesDisplayTracks : public cSkinDisplayTracks {
|
||||||
|
private:
|
||||||
|
cOsd *osd;
|
||||||
|
int itemsWidth;
|
||||||
|
int currentIndex;
|
||||||
|
void SetItem(const char *Text, int Index, bool Current);
|
||||||
|
public:
|
||||||
|
cSkinCursesDisplayTracks(const char *Title, int NumTracks, const char * const *Tracks);
|
||||||
|
virtual ~cSkinCursesDisplayTracks();
|
||||||
|
virtual void SetTrack(int Index, const char * const *Tracks);
|
||||||
|
virtual void Flush(void);
|
||||||
|
};
|
||||||
|
|
||||||
|
cSkinCursesDisplayTracks::cSkinCursesDisplayTracks(const char *Title, int NumTracks, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
currentIndex = -1;
|
||||||
|
itemsWidth = Font.Width(Title);
|
||||||
|
for (int i = 0; i < NumTracks; i++)
|
||||||
|
itemsWidth = max(itemsWidth, Font.Width(Tracks[i]));
|
||||||
|
itemsWidth = min(itemsWidth, OsdWidth);
|
||||||
|
osd = new cCursesOsd(0, 0);
|
||||||
|
osd->DrawRectangle(0, 0, OsdWidth - 1, OsdHeight - 1, clrBackground);
|
||||||
|
osd->DrawText(0, 0, Title, clrBlack, clrCyan, &Font, itemsWidth);
|
||||||
|
for (int i = 0; i < NumTracks; i++)
|
||||||
|
SetItem(Tracks[i], i, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
cSkinCursesDisplayTracks::~cSkinCursesDisplayTracks()
|
||||||
|
{
|
||||||
|
delete osd;
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinCursesDisplayTracks::SetItem(const char *Text, int Index, bool Current)
|
||||||
|
{
|
||||||
|
int y = 1 + Index;
|
||||||
|
int ColorFg, ColorBg;
|
||||||
|
if (Current) {
|
||||||
|
ColorFg = clrBlack;
|
||||||
|
ColorBg = clrCyan;
|
||||||
|
currentIndex = Index;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
ColorFg = clrWhite;
|
||||||
|
ColorBg = clrBackground;
|
||||||
|
}
|
||||||
|
osd->DrawText(0, y, Text, ColorFg, ColorBg, &Font, itemsWidth);
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinCursesDisplayTracks::SetTrack(int Index, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
if (currentIndex >= 0)
|
||||||
|
SetItem(Tracks[currentIndex], currentIndex, false);
|
||||||
|
SetItem(Tracks[Index], Index, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinCursesDisplayTracks::Flush(void)
|
||||||
|
{
|
||||||
|
osd->Flush();
|
||||||
|
}
|
||||||
|
|
||||||
// --- cSkinCursesDisplayMessage ---------------------------------------------
|
// --- cSkinCursesDisplayMessage ---------------------------------------------
|
||||||
|
|
||||||
class cSkinCursesDisplayMessage : public cSkinDisplayMessage {
|
class cSkinCursesDisplayMessage : public cSkinDisplayMessage {
|
||||||
@ -600,6 +662,7 @@ public:
|
|||||||
virtual cSkinDisplayMenu *DisplayMenu(void);
|
virtual cSkinDisplayMenu *DisplayMenu(void);
|
||||||
virtual cSkinDisplayReplay *DisplayReplay(bool ModeOnly);
|
virtual cSkinDisplayReplay *DisplayReplay(bool ModeOnly);
|
||||||
virtual cSkinDisplayVolume *DisplayVolume(void);
|
virtual cSkinDisplayVolume *DisplayVolume(void);
|
||||||
|
virtual cSkinDisplayTracks *DisplayTracks(const char *Title, int NumTracks, const char * const *Tracks);
|
||||||
virtual cSkinDisplayMessage *DisplayMessage(void);
|
virtual cSkinDisplayMessage *DisplayMessage(void);
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -633,6 +696,11 @@ cSkinDisplayVolume *cSkinCurses::DisplayVolume(void)
|
|||||||
return new cSkinCursesDisplayVolume;
|
return new cSkinCursesDisplayVolume;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cSkinDisplayTracks *cSkinCurses::DisplayTracks(const char *Title, int NumTracks, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
return new cSkinCursesDisplayTracks(Title, NumTracks, Tracks);
|
||||||
|
}
|
||||||
|
|
||||||
cSkinDisplayMessage *cSkinCurses::DisplayMessage(void)
|
cSkinDisplayMessage *cSkinCurses::DisplayMessage(void)
|
||||||
{
|
{
|
||||||
return new cSkinCursesDisplayMessage;
|
return new cSkinCursesDisplayMessage;
|
||||||
|
27
device.c
27
device.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: device.c 1.64 2004/12/24 15:37:11 kls Exp $
|
* $Id: device.c 1.65 2005/01/02 14:08:40 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "device.h"
|
#include "device.h"
|
||||||
@ -604,15 +604,19 @@ void cDevice::ClrAvailableTracks(void)
|
|||||||
memset(availableTracks, 0, sizeof(availableTracks));
|
memset(availableTracks, 0, sizeof(availableTracks));
|
||||||
}
|
}
|
||||||
|
|
||||||
bool cDevice::SetAvailableTrack(eTrackType Type, int Index, uint16_t Id, const char *Language, uint32_t Flags)
|
bool cDevice::SetAvailableTrack(eTrackType Type, int Index, uint16_t Id, const char *Language, const char *Description, uint32_t Flags)
|
||||||
{
|
{
|
||||||
eTrackType t = eTrackType(Type + Index);
|
eTrackType t = eTrackType(Type + Index);
|
||||||
if ((Type == ttAudio && IS_AUDIO_TRACK(t)) ||
|
if ((Type == ttAudio && IS_AUDIO_TRACK(t)) ||
|
||||||
(Type == ttDolby && IS_DOLBY_TRACK(t))) {
|
(Type == ttDolby && IS_DOLBY_TRACK(t))) {
|
||||||
if (Language)
|
if (Language)
|
||||||
strn0cpy(availableTracks[t].language, Language, sizeof(availableTracks[t].language));
|
strn0cpy(availableTracks[t].language, Language, sizeof(availableTracks[t].language));
|
||||||
availableTracks[t].flags = Flags;
|
if (Description)
|
||||||
availableTracks[t].id = Id; // setting 'id' last to avoid the need for extensive locking
|
strn0cpy(availableTracks[t].description, Description, sizeof(availableTracks[t].description));
|
||||||
|
if (Id) {
|
||||||
|
availableTracks[t].flags = Flags;
|
||||||
|
availableTracks[t].id = Id; // setting 'id' last to avoid the need for extensive locking
|
||||||
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -652,21 +656,6 @@ bool cDevice::SetCurrentAudioTrack(eTrackType Type)
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool cDevice::IncCurrentAudioTrack(void)
|
|
||||||
{
|
|
||||||
int i = currentAudioTrack + 1;
|
|
||||||
for (;;) {
|
|
||||||
if (i > ttDolbyLast)
|
|
||||||
i = ttAudioFirst;
|
|
||||||
if (i == currentAudioTrack)
|
|
||||||
break;
|
|
||||||
if (availableTracks[i].id)
|
|
||||||
return SetCurrentAudioTrack(eTrackType(i));
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool cDevice::CanReplay(void) const
|
bool cDevice::CanReplay(void) const
|
||||||
{
|
{
|
||||||
return HasDecoder();
|
return HasDecoder();
|
||||||
|
15
device.h
15
device.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: device.h 1.48 2004/12/24 14:57:24 kls Exp $
|
* $Id: device.h 1.49 2005/01/02 14:08:36 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __DEVICE_H
|
#ifndef __DEVICE_H
|
||||||
@ -75,8 +75,9 @@ enum eTrackType { ttNone,
|
|||||||
#define IS_DOLBY_TRACK(t) (ttDolbyFirst <= (t) && (t) <= ttDolbyLast)
|
#define IS_DOLBY_TRACK(t) (ttDolbyFirst <= (t) && (t) <= ttDolbyLast)
|
||||||
|
|
||||||
struct tTrackId {
|
struct tTrackId {
|
||||||
uint16_t id; // The PES packet id or the PID.
|
uint16_t id; // The PES packet id or the PID.
|
||||||
char language[8]; // something like either "eng" or "deu/eng"
|
char language[8]; // something like either "eng" or "deu/eng"
|
||||||
|
char description[32]; // something like "Dolby Digital 5.1"
|
||||||
// for future use:
|
// for future use:
|
||||||
uint32_t flags; // Used to further identify the actual track.
|
uint32_t flags; // Used to further identify the actual track.
|
||||||
};
|
};
|
||||||
@ -319,10 +320,12 @@ protected:
|
|||||||
///< Sets the current audio track to the given value.
|
///< Sets the current audio track to the given value.
|
||||||
public:
|
public:
|
||||||
void ClrAvailableTracks(void);
|
void ClrAvailableTracks(void);
|
||||||
bool SetAvailableTrack(eTrackType Type, int Index, uint16_t Id, const char *Language = NULL, uint32_t Flags = 0);
|
bool SetAvailableTrack(eTrackType Type, int Index, uint16_t Id, const char *Language = NULL, const char *Description = NULL, uint32_t Flags = 0);
|
||||||
///< Sets the track of the given Type and Index to the given values.
|
///< Sets the track of the given Type and Index to the given values.
|
||||||
///< Type must be one of the basic eTrackType values, like ttAudio or ttDolby.
|
///< Type must be one of the basic eTrackType values, like ttAudio or ttDolby.
|
||||||
///< Index tells which track of the given basic type is meant.
|
///< Index tells which track of the given basic type is meant.
|
||||||
|
///< If Id is 0 any existing id (and flags) will be left untouched and only the
|
||||||
|
///< given Language and Description will be set.
|
||||||
///< \return Returns true if the track was set correctly, false otherwise.
|
///< \return Returns true if the track was set correctly, false otherwise.
|
||||||
const tTrackId *GetTrack(eTrackType Type);
|
const tTrackId *GetTrack(eTrackType Type);
|
||||||
///< Returns a pointer to the given track id, or NULL if Type is not
|
///< Returns a pointer to the given track id, or NULL if Type is not
|
||||||
@ -335,10 +338,6 @@ public:
|
|||||||
bool SetCurrentAudioTrack(eTrackType Type);
|
bool SetCurrentAudioTrack(eTrackType Type);
|
||||||
///< Sets the current audio track to the given Type.
|
///< Sets the current audio track to the given Type.
|
||||||
///< \return Returns true if Type is a valid audio track, false otherwise.
|
///< \return Returns true if Type is a valid audio track, false otherwise.
|
||||||
bool IncCurrentAudioTrack(void);
|
|
||||||
///< Sets the current audio track to the next available track (wraps to
|
|
||||||
///< to the first one if necessary).
|
|
||||||
///< \return Returns true if the audio track has been changed, false otherwise.
|
|
||||||
|
|
||||||
// Audio facilities
|
// Audio facilities
|
||||||
|
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: dvbdevice.c 1.107 2004/12/17 14:19:48 kls Exp $
|
* $Id: dvbdevice.c 1.108 2005/01/02 11:51:18 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "dvbdevice.h"
|
#include "dvbdevice.h"
|
||||||
@ -860,10 +860,8 @@ void cDvbDevice::SetAudioTrackDevice(eTrackType Type)
|
|||||||
else if (IS_DOLBY_TRACK(Type)) {
|
else if (IS_DOLBY_TRACK(Type)) {
|
||||||
// Currently this works only in Transfer Mode
|
// Currently this works only in Transfer Mode
|
||||||
cChannel *Channel = Channels.GetByNumber(CurrentChannel());
|
cChannel *Channel = Channels.GetByNumber(CurrentChannel());
|
||||||
if (Channel) {
|
if (Channel)
|
||||||
SetChannelDevice(Channel, false);
|
SetChannelDevice(Channel, false); // this implicitly starts Transfer Mode
|
||||||
cControl::Launch(new cTransferControl(this, Channel->Vpid(), Channel->Apid(0), Channel->Apid(1), Channel->Dpid(0), Channel->Dpid(1)));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
32
eit.c
32
eit.c
@ -8,7 +8,7 @@
|
|||||||
* Robert Schneider <Robert.Schneider@web.de> and Rolf Hakenes <hakenes@hippomi.de>.
|
* Robert Schneider <Robert.Schneider@web.de> and Rolf Hakenes <hakenes@hippomi.de>.
|
||||||
* Adapted to 'libsi' for VDR 1.3.0 by Marcel Wiesweg <marcel.wiesweg@gmx.de>.
|
* Adapted to 'libsi' for VDR 1.3.0 by Marcel Wiesweg <marcel.wiesweg@gmx.de>.
|
||||||
*
|
*
|
||||||
* $Id: eit.c 1.101 2004/12/26 10:38:46 kls Exp $
|
* $Id: eit.c 1.102 2005/01/02 11:52:12 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "eit.h"
|
#include "eit.h"
|
||||||
@ -91,6 +91,8 @@ cEIT::cEIT(cSchedules *Schedules, int Source, u_char Tid, const u_char *Data)
|
|||||||
SI::ExtendedEventDescriptors *ExtendedEventDescriptors = NULL;
|
SI::ExtendedEventDescriptors *ExtendedEventDescriptors = NULL;
|
||||||
SI::ShortEventDescriptor *ShortEventDescriptor = NULL;
|
SI::ShortEventDescriptor *ShortEventDescriptor = NULL;
|
||||||
cLinkChannels *LinkChannels = NULL;
|
cLinkChannels *LinkChannels = NULL;
|
||||||
|
int NumComponents = 0;
|
||||||
|
SI::ComponentDescriptor *ComponentDescriptors[MAXCOMPONENTS];
|
||||||
for (SI::Loop::Iterator it2; (d = SiEitEvent.eventDescriptors.getNext(it2)); ) {
|
for (SI::Loop::Iterator it2; (d = SiEitEvent.eventDescriptors.getNext(it2)); ) {
|
||||||
switch (d->getDescriptorTag()) {
|
switch (d->getDescriptorTag()) {
|
||||||
case SI::ExtendedEventDescriptorTag: {
|
case SI::ExtendedEventDescriptorTag: {
|
||||||
@ -186,6 +188,20 @@ cEIT::cEIT(cSchedules *Schedules, int Source, u_char Tid, const u_char *Data)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case SI::ComponentDescriptorTag: {
|
||||||
|
SI::ComponentDescriptor *cd = (SI::ComponentDescriptor *)d;
|
||||||
|
uchar Stream = cd->getStreamContent();
|
||||||
|
uchar Type = cd->getComponentType();
|
||||||
|
if (1 <= Stream && Stream <= 2 && Type != 0) {
|
||||||
|
if (NumComponents < MAXCOMPONENTS) {
|
||||||
|
ComponentDescriptors[NumComponents++] = cd;
|
||||||
|
d = NULL; // so that it is not deleted
|
||||||
|
}
|
||||||
|
else
|
||||||
|
dsyslog("more than %d component descriptors!", MAXCOMPONENTS);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
default: ;
|
default: ;
|
||||||
}
|
}
|
||||||
delete d;
|
delete d;
|
||||||
@ -205,8 +221,20 @@ cEIT::cEIT(cSchedules *Schedules, int Source, u_char Tid, const u_char *Data)
|
|||||||
delete ExtendedEventDescriptors;
|
delete ExtendedEventDescriptors;
|
||||||
delete ShortEventDescriptor;
|
delete ShortEventDescriptor;
|
||||||
|
|
||||||
pEvent->FixEpgBugs();
|
if (NumComponents > 0) {
|
||||||
|
cComponents *Components = new cComponents(NumComponents);
|
||||||
|
for (int i = 0; i < NumComponents; i++) {
|
||||||
|
char buffer[256];
|
||||||
|
SI::ComponentDescriptor *cd = ComponentDescriptors[i];
|
||||||
|
Components->SetComponent(i, cd->getStreamContent(), cd->getComponentType(), I18nNormalizeLanguageCode(cd->languageCode), cd->description.getText(buffer, sizeof(buffer)));
|
||||||
|
delete cd;
|
||||||
|
}
|
||||||
|
pEvent->SetComponents(Components);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
pEvent->SetComponents(NULL);
|
||||||
|
|
||||||
|
pEvent->FixEpgBugs();
|
||||||
if (LinkChannels)
|
if (LinkChannels)
|
||||||
channel->SetLinkChannels(LinkChannels);
|
channel->SetLinkChannels(LinkChannels);
|
||||||
if (Tid == 0x4E) { // we trust only the present/following info on the actual TS
|
if (Tid == 0x4E) { // we trust only the present/following info on the actual TS
|
||||||
|
165
epg.c
165
epg.c
@ -7,7 +7,7 @@
|
|||||||
* Original version (as used in VDR before 1.3.0) written by
|
* Original version (as used in VDR before 1.3.0) written by
|
||||||
* Robert Schneider <Robert.Schneider@web.de> and Rolf Hakenes <hakenes@hippomi.de>.
|
* Robert Schneider <Robert.Schneider@web.de> and Rolf Hakenes <hakenes@hippomi.de>.
|
||||||
*
|
*
|
||||||
* $Id: epg.c 1.23 2004/12/26 11:32:01 kls Exp $
|
* $Id: epg.c 1.24 2005/01/02 11:25:25 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "epg.h"
|
#include "epg.h"
|
||||||
@ -16,6 +16,66 @@
|
|||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
|
|
||||||
|
// --- tComponent ------------------------------------------------------------
|
||||||
|
|
||||||
|
cString tComponent::ToString(void)
|
||||||
|
{
|
||||||
|
char buffer[256];
|
||||||
|
snprintf(buffer, sizeof(buffer), "%X %02X %-3s %s", stream, type, language, description ? description : "");
|
||||||
|
return buffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool tComponent::FromString(const char *s)
|
||||||
|
{
|
||||||
|
unsigned int Stream, Type;
|
||||||
|
int n = sscanf(s, "%X %02X %3c %a[^\n]", &Stream, &Type, language, &description);
|
||||||
|
if (n != 4)
|
||||||
|
description = NULL;
|
||||||
|
else if (isempty(description)) {
|
||||||
|
free(description);
|
||||||
|
description = NULL;
|
||||||
|
}
|
||||||
|
stream = Stream;
|
||||||
|
type = Type;
|
||||||
|
return n >= 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
// --- cComponents -----------------------------------------------------------
|
||||||
|
|
||||||
|
cComponents::cComponents(int NumComponents)
|
||||||
|
{
|
||||||
|
numComponents = NumComponents;
|
||||||
|
components = MALLOC(tComponent, numComponents);
|
||||||
|
memset(components, 0, sizeof(tComponent) * numComponents);
|
||||||
|
}
|
||||||
|
|
||||||
|
cComponents::~cComponents(void)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < numComponents; i++)
|
||||||
|
free(components[i].description);
|
||||||
|
free(components);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool cComponents::SetComponent(int Index, const char *s)
|
||||||
|
{
|
||||||
|
if (Index < numComponents)
|
||||||
|
return components[Index].FromString(s);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool cComponents::SetComponent(int Index, uchar Stream, uchar Type, const char *Language, const char *Description)
|
||||||
|
{
|
||||||
|
if (Index < numComponents) {
|
||||||
|
tComponent *p = &components[Index];
|
||||||
|
p->stream = Stream;
|
||||||
|
p->type = Type;
|
||||||
|
strn0cpy(p->language, Language, sizeof(p->language));
|
||||||
|
p->description = strcpyrealloc(p->description, !isempty(Description) ? Description : NULL);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
// --- cEvent ----------------------------------------------------------------
|
// --- cEvent ----------------------------------------------------------------
|
||||||
|
|
||||||
cEvent::cEvent(tChannelID ChannelID, u_int16_t EventID)
|
cEvent::cEvent(tChannelID ChannelID, u_int16_t EventID)
|
||||||
@ -28,6 +88,7 @@ cEvent::cEvent(tChannelID ChannelID, u_int16_t EventID)
|
|||||||
title = NULL;
|
title = NULL;
|
||||||
shortText = NULL;
|
shortText = NULL;
|
||||||
description = NULL;
|
description = NULL;
|
||||||
|
components = NULL;
|
||||||
startTime = 0;
|
startTime = 0;
|
||||||
duration = 0;
|
duration = 0;
|
||||||
vps = 0;
|
vps = 0;
|
||||||
@ -39,6 +100,7 @@ cEvent::~cEvent()
|
|||||||
free(title);
|
free(title);
|
||||||
free(shortText);
|
free(shortText);
|
||||||
free(description);
|
free(description);
|
||||||
|
delete components;
|
||||||
}
|
}
|
||||||
|
|
||||||
int cEvent::Compare(const cListObject &ListObject) const
|
int cEvent::Compare(const cListObject &ListObject) const
|
||||||
@ -85,6 +147,12 @@ void cEvent::SetDescription(const char *Description)
|
|||||||
description = strcpyrealloc(description, Description);
|
description = strcpyrealloc(description, Description);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void cEvent::SetComponents(cComponents *Components)
|
||||||
|
{
|
||||||
|
delete components;
|
||||||
|
components = Components;
|
||||||
|
}
|
||||||
|
|
||||||
void cEvent::SetStartTime(time_t StartTime)
|
void cEvent::SetStartTime(time_t StartTime)
|
||||||
{
|
{
|
||||||
startTime = StartTime;
|
startTime = StartTime;
|
||||||
@ -168,6 +236,12 @@ void cEvent::Dump(FILE *f, const char *Prefix) const
|
|||||||
fprintf(f, "%sD %s\n", Prefix, description);
|
fprintf(f, "%sD %s\n", Prefix, description);
|
||||||
strreplace(description, '|', '\n');
|
strreplace(description, '|', '\n');
|
||||||
}
|
}
|
||||||
|
if (components) {
|
||||||
|
for (int i = 0; i < components->NumComponents(); i++) {
|
||||||
|
tComponent *p = components->Component(i);
|
||||||
|
fprintf(f, "%sX %s\n", Prefix, *p->ToString());
|
||||||
|
}
|
||||||
|
}
|
||||||
if (vps)
|
if (vps)
|
||||||
fprintf(f, "%sV %ld\n", Prefix, vps);
|
fprintf(f, "%sV %ld\n", Prefix, vps);
|
||||||
fprintf(f, "%se\n", Prefix);
|
fprintf(f, "%se\n", Prefix);
|
||||||
@ -178,6 +252,8 @@ bool cEvent::Read(FILE *f, cSchedule *Schedule)
|
|||||||
{
|
{
|
||||||
if (Schedule) {
|
if (Schedule) {
|
||||||
cEvent *Event = NULL;
|
cEvent *Event = NULL;
|
||||||
|
int NumComponents = 0;
|
||||||
|
char *ComponentStrings[MAXCOMPONENTS];
|
||||||
char *s;
|
char *s;
|
||||||
cReadLine ReadLine;
|
cReadLine ReadLine;
|
||||||
while ((s = ReadLine.Read(f)) != NULL) {
|
while ((s = ReadLine.Read(f)) != NULL) {
|
||||||
@ -199,6 +275,7 @@ bool cEvent::Read(FILE *f, cSchedule *Schedule)
|
|||||||
Event->SetDuration(Duration);
|
Event->SetDuration(Duration);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
NumComponents = 0;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 'T': if (Event)
|
case 'T': if (Event)
|
||||||
@ -212,10 +289,26 @@ bool cEvent::Read(FILE *f, cSchedule *Schedule)
|
|||||||
Event->SetDescription(t);
|
Event->SetDescription(t);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case 'X': if (Event) {
|
||||||
|
if (NumComponents < MAXCOMPONENTS)
|
||||||
|
ComponentStrings[NumComponents++] = strdup(t);
|
||||||
|
else
|
||||||
|
dsyslog("more than %d component descriptors!", MAXCOMPONENTS);
|
||||||
|
}
|
||||||
|
break;
|
||||||
case 'V': if (Event)
|
case 'V': if (Event)
|
||||||
Event->SetVps(atoi(t));
|
Event->SetVps(atoi(t));
|
||||||
break;
|
break;
|
||||||
case 'e': Event = NULL;
|
case 'e': if (Event && NumComponents > 0) {
|
||||||
|
cComponents *Components = new cComponents(NumComponents);
|
||||||
|
for (int i = 0; i < NumComponents; i++) {
|
||||||
|
if (!Components->SetComponent(i, ComponentStrings[i]))
|
||||||
|
esyslog("ERROR: faulty component string in EPG data: '%s'", ComponentStrings[i]);
|
||||||
|
free(ComponentStrings[i]);
|
||||||
|
}
|
||||||
|
Event->SetComponents(Components);
|
||||||
|
}
|
||||||
|
Event = NULL;
|
||||||
break;
|
break;
|
||||||
case 'c': // to keep things simple we react on 'c' here
|
case 'c': // to keep things simple we react on 'c' here
|
||||||
return true;
|
return true;
|
||||||
@ -228,7 +321,7 @@ bool cEvent::Read(FILE *f, cSchedule *Schedule)
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
#define MAXEPGBUGFIXSTATS 8
|
#define MAXEPGBUGFIXSTATS 12
|
||||||
#define MAXEPGBUGFIXCHANS 100
|
#define MAXEPGBUGFIXCHANS 100
|
||||||
struct tEpgBugFixStats {
|
struct tEpgBugFixStats {
|
||||||
int hits;
|
int hits;
|
||||||
@ -476,6 +569,72 @@ void cEvent::FixEpgBugs(void)
|
|||||||
strreplace(title, '`', '\'');
|
strreplace(title, '`', '\'');
|
||||||
strreplace(shortText, '`', '\'');
|
strreplace(shortText, '`', '\'');
|
||||||
strreplace(description, '`', '\'');
|
strreplace(description, '`', '\'');
|
||||||
|
|
||||||
|
if (Setup.EPGBugfixLevel <= 2)
|
||||||
|
return;
|
||||||
|
|
||||||
|
// The stream components have a "description" field which some channels
|
||||||
|
// apparently have no idea of how to set correctly:
|
||||||
|
if (components) {
|
||||||
|
for (int i = 0; i < components->NumComponents(); i++) {
|
||||||
|
tComponent *p = components->Component(i);
|
||||||
|
switch (p->stream) {
|
||||||
|
case 0x01: { // video
|
||||||
|
if (p->description) {
|
||||||
|
if (strcasecmp(p->description, "Video") == 0 ||
|
||||||
|
strcasecmp(p->description, "Bildformat") == 0) {
|
||||||
|
// Yes, we know it's video - that's what the 'stream' code
|
||||||
|
// is for! But _which_ video is it?
|
||||||
|
free(p->description);
|
||||||
|
p->description = NULL;
|
||||||
|
EpgBugFixStat(8, ChannelID());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!p->description) {
|
||||||
|
switch (p->type) {
|
||||||
|
case 0x01:
|
||||||
|
case 0x05: p->description = strdup("4:3"); break;
|
||||||
|
case 0x02:
|
||||||
|
case 0x03:
|
||||||
|
case 0x06:
|
||||||
|
case 0x07: p->description = strdup("16:9"); break;
|
||||||
|
case 0x04:
|
||||||
|
case 0x08: p->description = strdup(">16:9"); break;
|
||||||
|
case 0x09:
|
||||||
|
case 0x0D: p->description = strdup("HD 4:3"); break;
|
||||||
|
case 0x0A:
|
||||||
|
case 0x0B:
|
||||||
|
case 0x0E:
|
||||||
|
case 0x0F: p->description = strdup("HD 16:9"); break;
|
||||||
|
case 0x0C:
|
||||||
|
case 0x10: p->description = strdup("HD >16:9"); break;
|
||||||
|
}
|
||||||
|
EpgBugFixStat(9, ChannelID());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 0x02: { // audio
|
||||||
|
if (p->description) {
|
||||||
|
if (strcasecmp(p->description, "Audio") == 0) {
|
||||||
|
// Yes, we know it's audio - that's what the 'stream' code
|
||||||
|
// is for! But _which_ audio is it?
|
||||||
|
free(p->description);
|
||||||
|
p->description = NULL;
|
||||||
|
EpgBugFixStat(10, ChannelID());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!p->description) {
|
||||||
|
switch (p->type) {
|
||||||
|
case 0x05: p->description = strdup("Dolby Digital"); break;
|
||||||
|
// all others will just display the language
|
||||||
|
}
|
||||||
|
EpgBugFixStat(11, ChannelID());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
54
epg.h
54
epg.h
@ -7,7 +7,7 @@
|
|||||||
* Original version (as used in VDR before 1.3.0) written by
|
* Original version (as used in VDR before 1.3.0) written by
|
||||||
* Robert Schneider <Robert.Schneider@web.de> and Rolf Hakenes <hakenes@hippomi.de>.
|
* Robert Schneider <Robert.Schneider@web.de> and Rolf Hakenes <hakenes@hippomi.de>.
|
||||||
*
|
*
|
||||||
* $Id: epg.h 1.18 2004/12/26 11:31:27 kls Exp $
|
* $Id: epg.h 1.19 2005/01/02 10:44:41 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __EPG_H
|
#ifndef __EPG_H
|
||||||
@ -17,26 +17,50 @@
|
|||||||
#include "thread.h"
|
#include "thread.h"
|
||||||
#include "tools.h"
|
#include "tools.h"
|
||||||
|
|
||||||
#define MAXEPGBUGFIXLEVEL 2
|
#define MAXEPGBUGFIXLEVEL 3
|
||||||
|
#define MAXCOMPONENTS 32
|
||||||
|
|
||||||
enum eDumpMode { dmAll, dmPresent, dmFollowing, dmAtTime };
|
enum eDumpMode { dmAll, dmPresent, dmFollowing, dmAtTime };
|
||||||
|
|
||||||
|
struct tComponent {
|
||||||
|
uchar stream;
|
||||||
|
uchar type;
|
||||||
|
char language[4];
|
||||||
|
char *description;
|
||||||
|
cString ToString(void);
|
||||||
|
bool FromString(const char *s);
|
||||||
|
};
|
||||||
|
|
||||||
|
class cComponents {
|
||||||
|
private:
|
||||||
|
int numComponents;
|
||||||
|
tComponent *components;
|
||||||
|
public:
|
||||||
|
cComponents(int NumComponents);
|
||||||
|
~cComponents(void);
|
||||||
|
int NumComponents(void) const { return numComponents; }
|
||||||
|
bool SetComponent(int Index, const char *s);
|
||||||
|
bool SetComponent(int Index, uchar Stream, uchar Type, const char *Language, const char *Description);
|
||||||
|
tComponent *Component(int Index) const { return (Index < numComponents) ? &components[Index] : NULL; }
|
||||||
|
};
|
||||||
|
|
||||||
class cSchedule;
|
class cSchedule;
|
||||||
|
|
||||||
class cEvent : public cListObject {
|
class cEvent : public cListObject {
|
||||||
private:
|
private:
|
||||||
tChannelID channelID; // Channel ID of program for this event
|
tChannelID channelID; // Channel ID of program for this event
|
||||||
u_int16_t eventID; // Event ID of this event
|
u_int16_t eventID; // Event ID of this event
|
||||||
uchar tableID; // Table ID this event came from
|
uchar tableID; // Table ID this event came from
|
||||||
uchar version; // Version number of section this event came from
|
uchar version; // Version number of section this event came from
|
||||||
int runningStatus; // 0=undefined, 1=not running, 2=starts in a few seconds, 3=pausing, 4=running
|
int runningStatus; // 0=undefined, 1=not running, 2=starts in a few seconds, 3=pausing, 4=running
|
||||||
char *title; // Title of this event
|
char *title; // Title of this event
|
||||||
char *shortText; // Short description of this event (typically the episode name in case of a series)
|
char *shortText; // Short description of this event (typically the episode name in case of a series)
|
||||||
char *description; // Description of this event
|
char *description; // Description of this event
|
||||||
time_t startTime; // Start time of this event
|
cComponents *components; // The stream components of this event (separated by '\n')
|
||||||
int duration; // Duration of this event in seconds
|
time_t startTime; // Start time of this event
|
||||||
time_t vps; // Video Programming Service timestamp (VPS, aka "Programme Identification Label", PIL)
|
int duration; // Duration of this event in seconds
|
||||||
time_t seen; // When this event was last seen in the data stream
|
time_t vps; // Video Programming Service timestamp (VPS, aka "Programme Identification Label", PIL)
|
||||||
|
time_t seen; // When this event was last seen in the data stream
|
||||||
public:
|
public:
|
||||||
cEvent(tChannelID ChannelID, u_int16_t EventID);
|
cEvent(tChannelID ChannelID, u_int16_t EventID);
|
||||||
~cEvent();
|
~cEvent();
|
||||||
@ -49,6 +73,7 @@ public:
|
|||||||
const char *Title(void) const { return title; }
|
const char *Title(void) const { return title; }
|
||||||
const char *ShortText(void) const { return shortText; }
|
const char *ShortText(void) const { return shortText; }
|
||||||
const char *Description(void) const { return description; }
|
const char *Description(void) const { return description; }
|
||||||
|
const cComponents *Components(void) const { return components; }
|
||||||
time_t StartTime(void) const { return startTime; }
|
time_t StartTime(void) const { return startTime; }
|
||||||
time_t EndTime(void) const { return startTime + duration; }
|
time_t EndTime(void) const { return startTime + duration; }
|
||||||
int Duration(void) const { return duration; }
|
int Duration(void) const { return duration; }
|
||||||
@ -67,6 +92,7 @@ public:
|
|||||||
void SetTitle(const char *Title);
|
void SetTitle(const char *Title);
|
||||||
void SetShortText(const char *ShortText);
|
void SetShortText(const char *ShortText);
|
||||||
void SetDescription(const char *Description);
|
void SetDescription(const char *Description);
|
||||||
|
void SetComponents(cComponents *Components); // Will take ownership of Components!
|
||||||
void SetStartTime(time_t StartTime);
|
void SetStartTime(time_t StartTime);
|
||||||
void SetDuration(int Duration);
|
void SetDuration(int Duration);
|
||||||
void SetVps(time_t Vps);
|
void SetVps(time_t Vps);
|
||||||
|
23
i18n.c
23
i18n.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: i18n.c 1.166 2004/12/18 16:44:24 kls Exp $
|
* $Id: i18n.c 1.167 2004/12/27 11:10:42 kls Exp $
|
||||||
*
|
*
|
||||||
* Translations provided by:
|
* Translations provided by:
|
||||||
*
|
*
|
||||||
@ -4610,6 +4610,27 @@ const tI18nPhrase Phrases[] = {
|
|||||||
"Hääletu",
|
"Hääletu",
|
||||||
"Sluk lyd",
|
"Sluk lyd",
|
||||||
},
|
},
|
||||||
|
{ "Audio",
|
||||||
|
"Audio",
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
"",// TODO
|
||||||
|
},
|
||||||
// Miscellaneous:
|
// Miscellaneous:
|
||||||
{ "yes",
|
{ "yes",
|
||||||
"ja",
|
"ja",
|
||||||
|
3
keys.c
3
keys.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: keys.c 1.6 2004/12/19 11:25:47 kls Exp $
|
* $Id: keys.c 1.7 2004/12/27 11:08:34 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "keys.h"
|
#include "keys.h"
|
||||||
@ -44,6 +44,7 @@ static tKey keyTable[] = { // "Up" and "Down" must be the first two keys!
|
|||||||
{ kVolUp, "Volume+" },
|
{ kVolUp, "Volume+" },
|
||||||
{ kVolDn, "Volume-" },
|
{ kVolDn, "Volume-" },
|
||||||
{ kMute, "Mute" },
|
{ kMute, "Mute" },
|
||||||
|
{ kAudio, "Audio" },
|
||||||
{ kSchedule, "Schedule" },
|
{ kSchedule, "Schedule" },
|
||||||
{ kChannels, "Channels" },
|
{ kChannels, "Channels" },
|
||||||
{ kTimers, "Timers" },
|
{ kTimers, "Timers" },
|
||||||
|
3
keys.h
3
keys.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: keys.h 1.5 2002/12/14 15:49:42 kls Exp $
|
* $Id: keys.h 1.6 2004/12/27 11:10:59 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __KEYS_H
|
#ifndef __KEYS_H
|
||||||
@ -38,6 +38,7 @@ enum eKeys { // "Up" and "Down" must be the first two keys!
|
|||||||
kVolUp,
|
kVolUp,
|
||||||
kVolDn,
|
kVolDn,
|
||||||
kMute,
|
kMute,
|
||||||
|
kAudio,
|
||||||
kSchedule,
|
kSchedule,
|
||||||
kChannels,
|
kChannels,
|
||||||
kTimers,
|
kTimers,
|
||||||
|
126
menu.c
126
menu.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: menu.c 1.323 2004/12/26 12:18:29 kls Exp $
|
* $Id: menu.c 1.324 2005/01/02 15:03:53 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "menu.h"
|
#include "menu.h"
|
||||||
@ -2410,7 +2410,7 @@ void cMenuMain::Set(const char *Plugin)
|
|||||||
|
|
||||||
// Color buttons:
|
// Color buttons:
|
||||||
|
|
||||||
SetHelp(!replaying ? tr("Record") : NULL, cDevice::PrimaryDevice()->NumAudioTracks() > 1 ? tr("Language") : NULL, replaying ? NULL : tr("Pause"), replaying ? tr("Button$Stop") : cReplayControl::LastReplayed() ? tr("Resume") : NULL);
|
SetHelp(!replaying ? tr("Record") : NULL, cDevice::PrimaryDevice()->NumAudioTracks() > 1 ? tr("Audio") : NULL, replaying ? NULL : tr("Pause"), replaying ? tr("Button$Stop") : cReplayControl::LastReplayed() ? tr("Resume") : NULL);
|
||||||
Display();
|
Display();
|
||||||
lastActivity = time(NULL);
|
lastActivity = time(NULL);
|
||||||
}
|
}
|
||||||
@ -2471,8 +2471,10 @@ eOSState cMenuMain::ProcessKey(eKeys Key)
|
|||||||
state = replaying ? osContinue : osRecord;
|
state = replaying ? osContinue : osRecord;
|
||||||
break;
|
break;
|
||||||
case kGreen: if (!HadSubMenu) {
|
case kGreen: if (!HadSubMenu) {
|
||||||
cDevice::PrimaryDevice()->IncCurrentAudioTrack();
|
if (cDevice::PrimaryDevice()->NumAudioTracks() > 1) {
|
||||||
state = osEnd;
|
cRemote::Put(kAudio, true);
|
||||||
|
state = osEnd;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case kYellow: if (!HadSubMenu)
|
case kYellow: if (!HadSubMenu)
|
||||||
@ -2764,6 +2766,122 @@ eOSState cDisplayVolume::ProcessKey(eKeys Key)
|
|||||||
return timeout.TimedOut() ? osEnd : osContinue;
|
return timeout.TimedOut() ? osEnd : osContinue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// --- cDisplayTracks --------------------------------------------------------
|
||||||
|
|
||||||
|
#define TRACKTIMEOUT 5000 //ms
|
||||||
|
|
||||||
|
cDisplayTracks *cDisplayTracks::currentDisplayTracks = NULL;
|
||||||
|
|
||||||
|
cDisplayTracks::cDisplayTracks(void)
|
||||||
|
:cOsdObject(true)
|
||||||
|
{
|
||||||
|
// Get the actual audio track descriptions from the EPG if we're not replaying:
|
||||||
|
if (!cDevice::PrimaryDevice()->Replaying() || cTransferControl::ReceiverDevice()) {
|
||||||
|
cChannel *Channel = Channels.GetByNumber(cDevice::CurrentChannel());
|
||||||
|
if (Channel) {
|
||||||
|
cSchedulesLock SchedulesLock;
|
||||||
|
const cSchedules *Schedules = cSchedules::Schedules(SchedulesLock);
|
||||||
|
if (Schedules) {
|
||||||
|
const cSchedule *Schedule = Schedules->GetSchedule(Channel->GetChannelID());
|
||||||
|
if (Schedule) {
|
||||||
|
const cEvent *Present = Schedule->GetPresentEvent(true);
|
||||||
|
if (Present) {
|
||||||
|
const cComponents *Components = Present->Components();
|
||||||
|
if (Components) {
|
||||||
|
int indexAudio = 0;
|
||||||
|
int indexDolby = 0;
|
||||||
|
for (int i = 0; i < Components->NumComponents(); i++) {
|
||||||
|
const tComponent *p = Components->Component(i);
|
||||||
|
if (p->stream == 2) {
|
||||||
|
if (p->type == 0x05)
|
||||||
|
cDevice::PrimaryDevice()->SetAvailableTrack(ttDolby, indexDolby++, 0, NULL, p->description);
|
||||||
|
else
|
||||||
|
cDevice::PrimaryDevice()->SetAvailableTrack(ttAudio, indexAudio++, 0, NULL, p->description);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
currentDisplayTracks = this;
|
||||||
|
numTracks = track = 0;
|
||||||
|
eTrackType CurrentAudioTrack = cDevice::PrimaryDevice()->GetCurrentAudioTrack();
|
||||||
|
for (int i = ttAudioFirst; i <= ttDolbyLast; i++) {
|
||||||
|
const tTrackId *TrackId = cDevice::PrimaryDevice()->GetTrack(eTrackType(i));
|
||||||
|
if (TrackId && TrackId->id) {
|
||||||
|
types[numTracks] = eTrackType(i);
|
||||||
|
descriptions[numTracks] = strdup(*TrackId->description ? TrackId->description : *TrackId->language ? TrackId->language : itoa(i));
|
||||||
|
if (i == CurrentAudioTrack)
|
||||||
|
track = numTracks;
|
||||||
|
numTracks++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
timeout.Set(TRACKTIMEOUT);
|
||||||
|
displayTracks = Skins.Current()->DisplayTracks(tr("Audio"), numTracks, descriptions);
|
||||||
|
Show();
|
||||||
|
}
|
||||||
|
|
||||||
|
cDisplayTracks::~cDisplayTracks()
|
||||||
|
{
|
||||||
|
delete displayTracks;
|
||||||
|
currentDisplayTracks = NULL;
|
||||||
|
for (int i = 0; i < numTracks; i++)
|
||||||
|
free(descriptions[i]);
|
||||||
|
cStatus::MsgOsdClear();
|
||||||
|
}
|
||||||
|
|
||||||
|
void cDisplayTracks::Show(void)
|
||||||
|
{
|
||||||
|
displayTracks->SetTrack(track, descriptions);
|
||||||
|
displayTracks->Flush();
|
||||||
|
cStatus::MsgSetAudioTrack(track, descriptions);
|
||||||
|
}
|
||||||
|
|
||||||
|
cDisplayTracks *cDisplayTracks::Create(void)
|
||||||
|
{
|
||||||
|
if (!currentDisplayTracks)
|
||||||
|
new cDisplayTracks;
|
||||||
|
return currentDisplayTracks;
|
||||||
|
}
|
||||||
|
|
||||||
|
void cDisplayTracks::Process(eKeys Key)
|
||||||
|
{
|
||||||
|
if (currentDisplayTracks)
|
||||||
|
currentDisplayTracks->ProcessKey(Key);
|
||||||
|
}
|
||||||
|
|
||||||
|
eOSState cDisplayTracks::ProcessKey(eKeys Key)
|
||||||
|
{
|
||||||
|
int oldTrack = track;
|
||||||
|
switch (Key) {
|
||||||
|
case kUp|k_Repeat:
|
||||||
|
case kUp:
|
||||||
|
case kDown|k_Repeat:
|
||||||
|
case kDown:
|
||||||
|
if (NORMALKEY(Key) == kUp && track > 0)
|
||||||
|
track--;
|
||||||
|
else if (NORMALKEY(Key) == kDown && track < numTracks - 1)
|
||||||
|
track++;
|
||||||
|
timeout.Set(TRACKTIMEOUT);
|
||||||
|
break;
|
||||||
|
case kAudio:
|
||||||
|
if (++track >= numTracks)
|
||||||
|
track = 0;
|
||||||
|
timeout.Set(TRACKTIMEOUT);
|
||||||
|
break;
|
||||||
|
case kNone: break;
|
||||||
|
default: return osEnd;
|
||||||
|
}
|
||||||
|
if (track != oldTrack) {
|
||||||
|
Show();
|
||||||
|
cDevice::PrimaryDevice()->SetCurrentAudioTrack(types[track]);
|
||||||
|
}
|
||||||
|
return timeout.TimedOut() ? osEnd : osContinue;
|
||||||
|
}
|
||||||
|
|
||||||
// --- cRecordControl --------------------------------------------------------
|
// --- cRecordControl --------------------------------------------------------
|
||||||
|
|
||||||
cRecordControl::cRecordControl(cDevice *Device, cTimer *Timer, bool Pause)
|
cRecordControl::cRecordControl(cDevice *Device, cTimer *Timer, bool Pause)
|
||||||
|
19
menu.h
19
menu.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: menu.h 1.65 2004/12/19 17:59:47 kls Exp $
|
* $Id: menu.h 1.66 2005/01/02 14:38:00 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __MENU_H
|
#ifndef __MENU_H
|
||||||
@ -75,6 +75,23 @@ public:
|
|||||||
eOSState ProcessKey(eKeys Key);
|
eOSState ProcessKey(eKeys Key);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class cDisplayTracks : public cOsdObject {
|
||||||
|
private:
|
||||||
|
cSkinDisplayTracks *displayTracks;
|
||||||
|
cTimeMs timeout;
|
||||||
|
eTrackType types[ttMaxTrackTypes];
|
||||||
|
char *descriptions[ttMaxTrackTypes];
|
||||||
|
int numTracks, track;
|
||||||
|
static cDisplayTracks *currentDisplayTracks;
|
||||||
|
virtual void Show(void);
|
||||||
|
cDisplayTracks(void);
|
||||||
|
public:
|
||||||
|
virtual ~cDisplayTracks();
|
||||||
|
static cDisplayTracks *Create(void);
|
||||||
|
static void Process(eKeys Key);
|
||||||
|
eOSState ProcessKey(eKeys Key);
|
||||||
|
};
|
||||||
|
|
||||||
class cMenuCam : public cOsdMenu {
|
class cMenuCam : public cOsdMenu {
|
||||||
private:
|
private:
|
||||||
cCiMenu *ciMenu;
|
cCiMenu *ciMenu;
|
||||||
|
4
player.h
4
player.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: player.h 1.13 2004/12/12 11:20:19 kls Exp $
|
* $Id: player.h 1.14 2004/12/30 10:44:34 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __PLAYER_H
|
#ifndef __PLAYER_H
|
||||||
@ -19,7 +19,7 @@ private:
|
|||||||
cDevice *device;
|
cDevice *device;
|
||||||
ePlayMode playMode;
|
ePlayMode playMode;
|
||||||
protected:
|
protected:
|
||||||
bool DeviceSetAvailableTrack(eTrackType Type, int Index, uint16_t Id, const char *Language = NULL, uint32_t Flags = 0) { return device ? device->SetAvailableTrack(Type, Index, Id, Language, Flags) : false; }
|
bool DeviceSetAvailableTrack(eTrackType Type, int Index, uint16_t Id, const char *Language = NULL, const char *Description = NULL, uint32_t Flags = 0) { return device ? device->SetAvailableTrack(Type, Index, Id, Language, Description, Flags) : false; }
|
||||||
bool DevicePoll(cPoller &Poller, int TimeoutMs = 0) { return device ? device->Poll(Poller, TimeoutMs) : 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 DeviceFlush(int TimeoutMs = 0) { return device ? device->Flush(TimeoutMs) : true; }
|
||||||
void DeviceTrickSpeed(int Speed) { if (device) device->TrickSpeed(Speed); }
|
void DeviceTrickSpeed(int Speed) { if (device) device->TrickSpeed(Speed); }
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: skinclassic.c 1.9 2004/12/26 11:33:53 kls Exp $
|
* $Id: skinclassic.c 1.10 2005/01/02 14:41:08 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "skinclassic.h"
|
#include "skinclassic.h"
|
||||||
@ -502,6 +502,84 @@ void cSkinClassicDisplayVolume::Flush(void)
|
|||||||
osd->Flush();
|
osd->Flush();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// --- cSkinClassicDisplayTracks ---------------------------------------------
|
||||||
|
|
||||||
|
class cSkinClassicDisplayTracks : public cSkinDisplayTracks {
|
||||||
|
private:
|
||||||
|
cOsd *osd;
|
||||||
|
int x0, x1;
|
||||||
|
int y0, y1, y2;
|
||||||
|
int lineHeight;
|
||||||
|
int currentIndex;
|
||||||
|
void SetItem(const char *Text, int Index, bool Current);
|
||||||
|
public:
|
||||||
|
cSkinClassicDisplayTracks(const char *Title, int NumTracks, const char * const *Tracks);
|
||||||
|
virtual ~cSkinClassicDisplayTracks();
|
||||||
|
virtual void SetTrack(int Index, const char * const *Tracks);
|
||||||
|
virtual void Flush(void);
|
||||||
|
};
|
||||||
|
|
||||||
|
cSkinClassicDisplayTracks::cSkinClassicDisplayTracks(const char *Title, int NumTracks, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
const cFont *font = cFont::GetFont(fontOsd);
|
||||||
|
lineHeight = font->Height();
|
||||||
|
currentIndex = -1;
|
||||||
|
int ItemsWidth = font->Width(Title);
|
||||||
|
for (int i = 0; i < NumTracks; i++)
|
||||||
|
ItemsWidth = max(ItemsWidth, font->Width(Tracks[i]));
|
||||||
|
ItemsWidth += 10;
|
||||||
|
x0 = 0;
|
||||||
|
x1 = Setup.OSDWidth;
|
||||||
|
int d = x1 - x0;
|
||||||
|
if (d > ItemsWidth) {
|
||||||
|
d = (d - ItemsWidth) & ~0x07; // must be multiple of 8
|
||||||
|
x1 -= d;
|
||||||
|
}
|
||||||
|
y0 = 0;
|
||||||
|
y1 = lineHeight;
|
||||||
|
y2 = y1 + NumTracks * lineHeight;
|
||||||
|
osd = cOsdProvider::NewOsd(Setup.OSDLeft, Setup.OSDTop + Setup.OSDHeight - y2);
|
||||||
|
tArea Areas[] = { { x0, y0, x1 - 1, y2 - 1, 4 } };
|
||||||
|
osd->SetAreas(Areas, sizeof(Areas) / sizeof(tArea));
|
||||||
|
osd->DrawText(x0, y0, Title, Theme.Color(clrMenuTitleFg), Theme.Color(clrMenuTitleBg), font, x1 - x0);
|
||||||
|
for (int i = 0; i < NumTracks; i++)
|
||||||
|
SetItem(Tracks[i], i, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
cSkinClassicDisplayTracks::~cSkinClassicDisplayTracks()
|
||||||
|
{
|
||||||
|
delete osd;
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinClassicDisplayTracks::SetItem(const char *Text, int Index, bool Current)
|
||||||
|
{
|
||||||
|
int y = y1 + Index * lineHeight;
|
||||||
|
tColor ColorFg, ColorBg;
|
||||||
|
if (Current) {
|
||||||
|
ColorFg = Theme.Color(clrMenuItemCurrentFg);
|
||||||
|
ColorBg = Theme.Color(clrMenuItemCurrentBg);
|
||||||
|
currentIndex = Index;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
ColorFg = Theme.Color(clrMenuItemSelectable);
|
||||||
|
ColorBg = Theme.Color(clrBackground);
|
||||||
|
}
|
||||||
|
const cFont *font = cFont::GetFont(fontOsd);
|
||||||
|
osd->DrawText(x0, y, Text, ColorFg, ColorBg, font, x1 - x0);
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinClassicDisplayTracks::SetTrack(int Index, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
if (currentIndex >= 0)
|
||||||
|
SetItem(Tracks[currentIndex], currentIndex, false);
|
||||||
|
SetItem(Tracks[Index], Index, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinClassicDisplayTracks::Flush(void)
|
||||||
|
{
|
||||||
|
osd->Flush();
|
||||||
|
}
|
||||||
|
|
||||||
// --- cSkinClassicDisplayMessage --------------------------------------------
|
// --- cSkinClassicDisplayMessage --------------------------------------------
|
||||||
|
|
||||||
class cSkinClassicDisplayMessage : public cSkinDisplayMessage {
|
class cSkinClassicDisplayMessage : public cSkinDisplayMessage {
|
||||||
@ -571,6 +649,12 @@ cSkinDisplayVolume *cSkinClassic::DisplayVolume(void)
|
|||||||
return new cSkinClassicDisplayVolume;
|
return new cSkinClassicDisplayVolume;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
cSkinDisplayTracks *cSkinClassic::DisplayTracks(const char *Title, int NumTracks, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
return new cSkinClassicDisplayTracks(Title, NumTracks, Tracks);
|
||||||
|
}
|
||||||
|
|
||||||
cSkinDisplayMessage *cSkinClassic::DisplayMessage(void)
|
cSkinDisplayMessage *cSkinClassic::DisplayMessage(void)
|
||||||
{
|
{
|
||||||
return new cSkinClassicDisplayMessage;
|
return new cSkinClassicDisplayMessage;
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: skinclassic.h 1.1 2004/04/18 09:38:02 kls Exp $
|
* $Id: skinclassic.h 1.2 2005/01/02 14:38:56 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __SKINCLASSIC_H
|
#ifndef __SKINCLASSIC_H
|
||||||
@ -20,6 +20,7 @@ public:
|
|||||||
virtual cSkinDisplayMenu *DisplayMenu(void);
|
virtual cSkinDisplayMenu *DisplayMenu(void);
|
||||||
virtual cSkinDisplayReplay *DisplayReplay(bool ModeOnly);
|
virtual cSkinDisplayReplay *DisplayReplay(bool ModeOnly);
|
||||||
virtual cSkinDisplayVolume *DisplayVolume(void);
|
virtual cSkinDisplayVolume *DisplayVolume(void);
|
||||||
|
virtual cSkinDisplayTracks *DisplayTracks(const char *Title, int NumTracks, const char * const *Tracks);
|
||||||
virtual cSkinDisplayMessage *DisplayMessage(void);
|
virtual cSkinDisplayMessage *DisplayMessage(void);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
18
skins.h
18
skins.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: skins.h 1.4 2004/12/26 11:57:54 kls Exp $
|
* $Id: skins.h 1.5 2005/01/02 14:36:19 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __SKINS_H
|
#ifndef __SKINS_H
|
||||||
@ -66,8 +66,6 @@ public:
|
|||||||
Red = Video options
|
Red = Video options
|
||||||
Green = Info now
|
Green = Info now
|
||||||
Yellow = Info next
|
Yellow = Info next
|
||||||
Blue = Audio options
|
|
||||||
AudioOptions
|
|
||||||
VideoOptions
|
VideoOptions
|
||||||
*/
|
*/
|
||||||
};
|
};
|
||||||
@ -223,6 +221,14 @@ public:
|
|||||||
///< indicator shall be displayed.
|
///< indicator shall be displayed.
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class cSkinDisplayTracks : public cSkinDisplay {
|
||||||
|
///< This class implements the track display.
|
||||||
|
public:
|
||||||
|
virtual void SetTrack(int Index, const char * const *Tracks) = 0;
|
||||||
|
///< Sets the current track to the one given by Index, which
|
||||||
|
///< points into the Tracks array of strings.
|
||||||
|
};
|
||||||
|
|
||||||
class cSkinDisplayMessage : public cSkinDisplay {
|
class cSkinDisplayMessage : public cSkinDisplay {
|
||||||
///< This class implements a simple message display.
|
///< This class implements a simple message display.
|
||||||
public:
|
public:
|
||||||
@ -275,6 +281,12 @@ public:
|
|||||||
virtual cSkinDisplayVolume *DisplayVolume(void) = 0;
|
virtual cSkinDisplayVolume *DisplayVolume(void) = 0;
|
||||||
///< Creates and returns a new object for displaying the current volume.
|
///< Creates and returns a new object for displaying the current volume.
|
||||||
///< The caller must delete the object after use.
|
///< The caller must delete the object after use.
|
||||||
|
virtual cSkinDisplayTracks *DisplayTracks(const char *Title, int NumTracks, const char * const *Tracks) = 0;
|
||||||
|
///< Creates and returns a new object for displaying the available tracks.
|
||||||
|
///< NumTracks indicates how many entries in Tracks are available.
|
||||||
|
///< Tracks will be valid throughout the entire lifetime of the returned
|
||||||
|
///< cSkinDisplayTrack object.
|
||||||
|
///< The caller must delete the object after use.
|
||||||
virtual cSkinDisplayMessage *DisplayMessage(void) = 0;
|
virtual cSkinDisplayMessage *DisplayMessage(void) = 0;
|
||||||
///< Creates and returns a new object for displaying a message.
|
///< Creates and returns a new object for displaying a message.
|
||||||
///< The caller must delete the object after use.
|
///< The caller must delete the object after use.
|
||||||
|
141
skinsttng.c
141
skinsttng.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: skinsttng.c 1.9 2004/12/26 11:34:29 kls Exp $
|
* $Id: skinsttng.c 1.10 2005/01/02 14:41:49 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
// Star Trek: The Next Generation® is a registered trademark of Paramount Pictures
|
// Star Trek: The Next Generation® is a registered trademark of Paramount Pictures
|
||||||
@ -822,6 +822,140 @@ void cSkinSTTNGDisplayVolume::Flush(void)
|
|||||||
osd->Flush();
|
osd->Flush();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// --- cSkinSTTNGDisplayTracks -----------------------------------------------
|
||||||
|
|
||||||
|
class cSkinSTTNGDisplayTracks : public cSkinDisplayTracks {
|
||||||
|
private:
|
||||||
|
cOsd *osd;
|
||||||
|
int x0, x1, x2, x3, x4, x5, x6, x7;
|
||||||
|
int y0, y1, y2, y3, y4, y5, y6, y7;
|
||||||
|
int lineHeight;
|
||||||
|
tColor frameColor;
|
||||||
|
int currentIndex;
|
||||||
|
void SetItem(const char *Text, int Index, bool Current);
|
||||||
|
public:
|
||||||
|
cSkinSTTNGDisplayTracks(const char *Title, int NumTracks, const char * const *Tracks);
|
||||||
|
virtual ~cSkinSTTNGDisplayTracks();
|
||||||
|
virtual void SetTrack(int Index, const char * const *Tracks);
|
||||||
|
virtual void Flush(void);
|
||||||
|
};
|
||||||
|
|
||||||
|
cSkinSTTNGDisplayTracks::cSkinSTTNGDisplayTracks(const char *Title, int NumTracks, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
const cFont *font = cFont::GetFont(fontOsd);
|
||||||
|
lineHeight = font->Height();
|
||||||
|
frameColor = Theme.Color(clrMenuFrame);
|
||||||
|
currentIndex = -1;
|
||||||
|
int ItemsWidth = font->Width(Title);
|
||||||
|
for (int i = 0; i < NumTracks; i++)
|
||||||
|
ItemsWidth = max(ItemsWidth, font->Width(Tracks[i]));
|
||||||
|
ItemsWidth += 10;
|
||||||
|
x0 = 0;
|
||||||
|
x1 = lineHeight / 2;
|
||||||
|
x3 = (x1 + Roundness + Gap + 7) & ~0x07; // must be multiple of 8
|
||||||
|
x2 = x3 - Gap;
|
||||||
|
x7 = Setup.OSDWidth;
|
||||||
|
x6 = x7 - lineHeight / 2;
|
||||||
|
x4 = (x6 - lineHeight / 2 - Gap) & ~0x07; // must be multiple of 8
|
||||||
|
x5 = x4 + Gap;
|
||||||
|
int d = x4 - x3;
|
||||||
|
if (d > ItemsWidth) {
|
||||||
|
d = (d - ItemsWidth) & ~0x07; // must be multiple of 8
|
||||||
|
x4 -= d;
|
||||||
|
x5 -= d;
|
||||||
|
x6 -= d;
|
||||||
|
x7 -= d;
|
||||||
|
}
|
||||||
|
y0 = 0;
|
||||||
|
y1 = lineHeight;
|
||||||
|
y2 = y1 + Roundness;
|
||||||
|
y3 = y2 + Gap;
|
||||||
|
// limit to Setup.OSDHeight? - what if height is too big???
|
||||||
|
y4 = y3 + NumTracks * lineHeight + 2 * Roundness;
|
||||||
|
y5 = y4 + Gap;
|
||||||
|
y6 = y5 + Roundness;
|
||||||
|
y7 = y6 + cFont::GetFont(fontSml)->Height();
|
||||||
|
int yt = (y0 + y1) / 2;
|
||||||
|
int yb = (y6 + y7) / 2;
|
||||||
|
osd = cOsdProvider::NewOsd(Setup.OSDLeft, Setup.OSDTop + Setup.OSDHeight - y7);
|
||||||
|
tArea Areas[] = { { x0, y0, x7 - 1, y7 - 1, 4 } };
|
||||||
|
if (osd->CanHandleAreas(Areas, sizeof(Areas) / sizeof(tArea)) == oeOk)
|
||||||
|
osd->SetAreas(Areas, sizeof(Areas) / sizeof(tArea));
|
||||||
|
else {
|
||||||
|
tArea Areas[] = { { x0, y0, x7 - 1, y3 - 1, 2 },
|
||||||
|
{ x0, y3, x3 - 1, y4 - 1, 1 },
|
||||||
|
{ x3, y3, x4 - 1, y4 - 1, 2 },
|
||||||
|
{ x4, y3, x7 - 1, y4 - 1, 2 },
|
||||||
|
{ x0, y4, x7 - 1, y7 - 1, 4 }
|
||||||
|
};
|
||||||
|
osd->SetAreas(Areas, sizeof(Areas) / sizeof(tArea));
|
||||||
|
}
|
||||||
|
osd->DrawRectangle(x0, y0, x7 - 1, y7 - 1, Theme.Color(clrBackground));
|
||||||
|
osd->DrawRectangle(x0, y0, x1 - 1, y1 - 1, clrTransparent);
|
||||||
|
osd->DrawRectangle(x0, y6, x1 - 1, y7 - 1, clrTransparent);
|
||||||
|
osd->DrawRectangle(x6, y0, x7 - 1, yt - 1, clrTransparent);
|
||||||
|
osd->DrawRectangle(x6, yb, x7 - 1, y7 - 1, clrTransparent);
|
||||||
|
osd->DrawEllipse (x0, y0, x1 - 1, y1 - 1, frameColor, 2);
|
||||||
|
osd->DrawRectangle(x1, y0, x2 - 1, y1 - 1, frameColor);
|
||||||
|
osd->DrawRectangle(x3, y0, x4 - 1, y1 - 1, frameColor);
|
||||||
|
osd->DrawRectangle(x5, y0, x6 - 1, y1 - 1, frameColor);
|
||||||
|
osd->DrawEllipse (x6, y0, x7 - 1, y1 - 1, frameColor, 5);
|
||||||
|
osd->DrawRectangle(x0, y1, x1 - 1, y6 - 1, frameColor);
|
||||||
|
osd->DrawEllipse (x1, y1, x2 - 1, y2 - 1, frameColor, -2);
|
||||||
|
osd->DrawEllipse (x1, y5, x2 - 1, y6 - 1, frameColor, -3);
|
||||||
|
osd->DrawEllipse (x0, y6, x1 - 1, y7 - 1, frameColor, 3);
|
||||||
|
osd->DrawRectangle(x1, y6, x2 - 1, y7 - 1, frameColor);
|
||||||
|
osd->DrawRectangle(x3, y6, x4 - 1, y7 - 1, frameColor);
|
||||||
|
osd->DrawRectangle(x5, y6, x6 - 1, y7 - 1, frameColor);
|
||||||
|
osd->DrawEllipse (x6, y6, x7 - 1, y7 - 1, frameColor, 5);
|
||||||
|
osd->DrawText(x3 + 5, y0, Title, Theme.Color(clrMenuTitle), frameColor, font, x4 - x3 - 5);
|
||||||
|
for (int i = 0; i < NumTracks; i++)
|
||||||
|
SetItem(Tracks[i], i, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
cSkinSTTNGDisplayTracks::~cSkinSTTNGDisplayTracks()
|
||||||
|
{
|
||||||
|
delete osd;
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinSTTNGDisplayTracks::SetItem(const char *Text, int Index, bool Current)
|
||||||
|
{
|
||||||
|
int y = y3 + Roundness + Index * lineHeight;
|
||||||
|
tColor ColorFg, ColorBg;
|
||||||
|
if (Current) {
|
||||||
|
ColorFg = Theme.Color(clrMenuItemCurrentFg);
|
||||||
|
ColorBg = Theme.Color(clrMenuItemCurrentBg);
|
||||||
|
osd->DrawEllipse (x1, y - Roundness, x2 - 1, y - 1, frameColor, -3);
|
||||||
|
osd->DrawRectangle(x1, y, x2 - 1, y + lineHeight - 1, frameColor);
|
||||||
|
osd->DrawEllipse (x1, y + lineHeight, x2 - 1, y + lineHeight + Roundness - 1, frameColor, -2);
|
||||||
|
osd->DrawRectangle(x3, y, x4 - 1, y + lineHeight - 1, ColorBg);
|
||||||
|
currentIndex = Index;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
ColorFg = Theme.Color(clrMenuItemSelectable);
|
||||||
|
ColorBg = Theme.Color(clrBackground);
|
||||||
|
if (currentIndex == Index) {
|
||||||
|
osd->DrawRectangle(x1, y - Roundness, x2 - 1, y + lineHeight + Roundness - 1, Theme.Color(clrBackground));
|
||||||
|
osd->DrawRectangle(x3, y, x4 - 1, y + lineHeight - 1, Theme.Color(clrBackground));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const cFont *font = cFont::GetFont(fontOsd);
|
||||||
|
int xt = x3 + 5;
|
||||||
|
osd->DrawText(xt, y, Text, ColorFg, ColorBg, font, x4 - xt);
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinSTTNGDisplayTracks::SetTrack(int Index, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
if (currentIndex >= 0)
|
||||||
|
SetItem(Tracks[currentIndex], currentIndex, false);
|
||||||
|
SetItem(Tracks[Index], Index, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void cSkinSTTNGDisplayTracks::Flush(void)
|
||||||
|
{
|
||||||
|
osd->Flush();
|
||||||
|
}
|
||||||
|
|
||||||
// --- cSkinSTTNGDisplayMessage ----------------------------------------------
|
// --- cSkinSTTNGDisplayMessage ----------------------------------------------
|
||||||
|
|
||||||
class cSkinSTTNGDisplayMessage : public cSkinDisplayMessage {
|
class cSkinSTTNGDisplayMessage : public cSkinDisplayMessage {
|
||||||
@ -909,6 +1043,11 @@ cSkinDisplayVolume *cSkinSTTNG::DisplayVolume(void)
|
|||||||
return new cSkinSTTNGDisplayVolume;
|
return new cSkinSTTNGDisplayVolume;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cSkinDisplayTracks *cSkinSTTNG::DisplayTracks(const char *Title, int NumTracks, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
return new cSkinSTTNGDisplayTracks(Title, NumTracks, Tracks);
|
||||||
|
}
|
||||||
|
|
||||||
cSkinDisplayMessage *cSkinSTTNG::DisplayMessage(void)
|
cSkinDisplayMessage *cSkinSTTNG::DisplayMessage(void)
|
||||||
{
|
{
|
||||||
return new cSkinSTTNGDisplayMessage;
|
return new cSkinSTTNGDisplayMessage;
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: skinsttng.h 1.1 2004/04/18 09:38:47 kls Exp $
|
* $Id: skinsttng.h 1.2 2005/01/02 14:39:29 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __SKINSTTNG_H
|
#ifndef __SKINSTTNG_H
|
||||||
@ -20,6 +20,7 @@ public:
|
|||||||
virtual cSkinDisplayMenu *DisplayMenu(void);
|
virtual cSkinDisplayMenu *DisplayMenu(void);
|
||||||
virtual cSkinDisplayReplay *DisplayReplay(bool ModeOnly);
|
virtual cSkinDisplayReplay *DisplayReplay(bool ModeOnly);
|
||||||
virtual cSkinDisplayVolume *DisplayVolume(void);
|
virtual cSkinDisplayVolume *DisplayVolume(void);
|
||||||
|
virtual cSkinDisplayTracks *DisplayTracks(const char *Title, int NumTracks, const char * const *Tracks);
|
||||||
virtual cSkinDisplayMessage *DisplayMessage(void);
|
virtual cSkinDisplayMessage *DisplayMessage(void);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
8
status.c
8
status.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: status.c 1.5 2003/05/03 14:47:44 kls Exp $
|
* $Id: status.c 1.6 2005/01/02 12:09:12 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "status.h"
|
#include "status.h"
|
||||||
@ -47,6 +47,12 @@ void cStatus::MsgSetVolume(int Volume, bool Absolute)
|
|||||||
sm->SetVolume(Volume, Absolute);
|
sm->SetVolume(Volume, Absolute);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void cStatus::MsgSetAudioTrack(int Index, const char * const *Tracks)
|
||||||
|
{
|
||||||
|
for (cStatus *sm = statusMonitors.First(); sm; sm = statusMonitors.Next(sm))
|
||||||
|
sm->SetAudioTrack(Index, Tracks);
|
||||||
|
}
|
||||||
|
|
||||||
void cStatus::MsgOsdClear(void)
|
void cStatus::MsgOsdClear(void)
|
||||||
{
|
{
|
||||||
for (cStatus *sm = statusMonitors.First(); sm; sm = statusMonitors.Next(sm))
|
for (cStatus *sm = statusMonitors.First(); sm; sm = statusMonitors.Next(sm))
|
||||||
|
6
status.h
6
status.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: status.h 1.6 2003/05/03 14:43:18 kls Exp $
|
* $Id: status.h 1.7 2005/01/02 12:08:12 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __STATUS_H
|
#ifndef __STATUS_H
|
||||||
@ -36,6 +36,9 @@ protected:
|
|||||||
virtual void SetVolume(int Volume, bool Absolute) {}
|
virtual void SetVolume(int Volume, bool Absolute) {}
|
||||||
// The volume has been set to the given value, either
|
// The volume has been set to the given value, either
|
||||||
// absolutely or relative to the current volume.
|
// absolutely or relative to the current volume.
|
||||||
|
virtual void SetAudioTrack(int Index, const char * const *Tracks) {}
|
||||||
|
// The audio track has been set to the one given by Index, which
|
||||||
|
// points into the Tracks array of strings.
|
||||||
virtual void OsdClear(void) {}
|
virtual void OsdClear(void) {}
|
||||||
// The OSD has been cleared.
|
// The OSD has been cleared.
|
||||||
virtual void OsdTitle(const char *Title) {}
|
virtual void OsdTitle(const char *Title) {}
|
||||||
@ -67,6 +70,7 @@ public:
|
|||||||
static void MsgRecording(const cDevice *Device, const char *Name);
|
static void MsgRecording(const cDevice *Device, const char *Name);
|
||||||
static void MsgReplaying(const cControl *Control, const char *Name);
|
static void MsgReplaying(const cControl *Control, const char *Name);
|
||||||
static void MsgSetVolume(int Volume, bool Absolute);
|
static void MsgSetVolume(int Volume, bool Absolute);
|
||||||
|
static void MsgSetAudioTrack(int Index, const char * const *Tracks);
|
||||||
static void MsgOsdClear(void);
|
static void MsgOsdClear(void);
|
||||||
static void MsgOsdTitle(const char *Title);
|
static void MsgOsdTitle(const char *Title);
|
||||||
static void MsgOsdStatusMessage(const char *Message);
|
static void MsgOsdStatusMessage(const char *Message);
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: transfer.c 1.19 2004/11/28 11:51:00 kls Exp $
|
* $Id: transfer.c 1.20 2004/12/27 11:08:34 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "transfer.h"
|
#include "transfer.h"
|
||||||
@ -58,11 +58,7 @@ void cTransfer::Action(void)
|
|||||||
int PollTimeouts = 0;
|
int PollTimeouts = 0;
|
||||||
uchar *p = NULL;
|
uchar *p = NULL;
|
||||||
int Result = 0;
|
int Result = 0;
|
||||||
// XXX Apparently this isn't necessary with the new PES data handling that
|
#define FW_NEEDS_BUFFER_RESERVE_FOR_AC3
|
||||||
// XXX was intorduced in VDR 1.3.18. If you do need this, enable the following
|
|
||||||
// XXX line and send an email to kls@cadsoft.de. If nobody requires this, it
|
|
||||||
// XXX will be removed later. kls 2004-12-27
|
|
||||||
//#define FW_NEEDS_BUFFER_RESERVE_FOR_AC3
|
|
||||||
#ifdef FW_NEEDS_BUFFER_RESERVE_FOR_AC3
|
#ifdef FW_NEEDS_BUFFER_RESERVE_FOR_AC3
|
||||||
bool Cleared = false;
|
bool Cleared = false;
|
||||||
bool GotBufferReserve = false;
|
bool GotBufferReserve = false;
|
||||||
|
11
vdr.5
11
vdr.5
@ -8,7 +8,7 @@
|
|||||||
.\" License as specified in the file COPYING that comes with the
|
.\" License as specified in the file COPYING that comes with the
|
||||||
.\" vdr distribution.
|
.\" vdr distribution.
|
||||||
.\"
|
.\"
|
||||||
.\" $Id: vdr.5 1.30 2004/12/18 12:40:47 kls Exp $
|
.\" $Id: vdr.5 1.31 2005/01/02 13:57:10 kls Exp $
|
||||||
.\"
|
.\"
|
||||||
.TH vdr 5 "19 Dec 2004" "1.3.18" "Video Disk Recorder Files"
|
.TH vdr 5 "19 Dec 2004" "1.3.18" "Video Disk Recorder Files"
|
||||||
.SH NAME
|
.SH NAME
|
||||||
@ -613,6 +613,7 @@ l l.
|
|||||||
\fBT\fR@<title>
|
\fBT\fR@<title>
|
||||||
\fBS\fR@<short text>
|
\fBS\fR@<short text>
|
||||||
\fBD\fR@<description>
|
\fBD\fR@<description>
|
||||||
|
\fBX\fR@<stream> <type> <language> <descr>
|
||||||
\fBV\fR@<vps time>
|
\fBV\fR@<vps time>
|
||||||
\fBe\fR@
|
\fBe\fR@
|
||||||
\fBc\fR@
|
\fBc\fR@
|
||||||
@ -622,8 +623,10 @@ Lowercase characters mark the end of a sequence that was started by the
|
|||||||
corresponding uppercase character. The outer frame consists of a sequence
|
corresponding uppercase character. The outer frame consists of a sequence
|
||||||
of one or more \fBC\fR...\fBc\fR (Channel) entries. Inside these any number of
|
of one or more \fBC\fR...\fBc\fR (Channel) entries. Inside these any number of
|
||||||
\fBE\fR...\fBe\fR (Event) entries are allowed.
|
\fBE\fR...\fBe\fR (Event) entries are allowed.
|
||||||
The \fBT\fR, \fBS\fR and \fBD\fR entries are optional (although every event
|
All other tags are optional (although every event
|
||||||
should at least have a \fBT\fR entry).
|
should at least have a \fBT\fR entry).
|
||||||
|
There may be several \fBX\fR tags, depending on the number of tracks (video, audio etc.)
|
||||||
|
the event provides.
|
||||||
|
|
||||||
.TS
|
.TS
|
||||||
tab (@);
|
tab (@);
|
||||||
@ -636,6 +639,10 @@ l l.
|
|||||||
<title> @is the title of the event
|
<title> @is the title of the event
|
||||||
<short text> @is the short text of the event (typically the name of the episode etc.)
|
<short text> @is the short text of the event (typically the name of the episode etc.)
|
||||||
<description> @is the description of the event (any '|' characters will be interpreted as newlines)
|
<description> @is the description of the event (any '|' characters will be interpreted as newlines)
|
||||||
|
<stream> @is the stream content (1 = video, 2 = audio)
|
||||||
|
<type> @is the stream type according to ETSI EN 300 468
|
||||||
|
<language> @is the three letter language code
|
||||||
|
<descr> @is the description of this stream component
|
||||||
<vps time> @is the Video Programming Service time of this event
|
<vps time> @is the Video Programming Service time of this event
|
||||||
.TE
|
.TE
|
||||||
|
|
||||||
|
12
vdr.c
12
vdr.c
@ -22,7 +22,7 @@
|
|||||||
*
|
*
|
||||||
* The project's page is at http://www.cadsoft.de/vdr
|
* The project's page is at http://www.cadsoft.de/vdr
|
||||||
*
|
*
|
||||||
* $Id: vdr.c 1.196 2004/12/26 10:30:30 kls Exp $
|
* $Id: vdr.c 1.197 2005/01/02 14:39:41 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <getopt.h>
|
#include <getopt.h>
|
||||||
@ -678,7 +678,7 @@ int main(int argc, char *argv[])
|
|||||||
case kChanDn:
|
case kChanDn:
|
||||||
cDevice::SwitchChannel(NORMALKEY(key) == kChanUp ? 1 : -1);
|
cDevice::SwitchChannel(NORMALKEY(key) == kChanUp ? 1 : -1);
|
||||||
break;
|
break;
|
||||||
// Volume Control:
|
// Volume control:
|
||||||
case kVolUp|k_Repeat:
|
case kVolUp|k_Repeat:
|
||||||
case kVolUp:
|
case kVolUp:
|
||||||
case kVolDn|k_Repeat:
|
case kVolDn|k_Repeat:
|
||||||
@ -697,6 +697,14 @@ int main(int argc, char *argv[])
|
|||||||
cDisplayVolume::Process(key);
|
cDisplayVolume::Process(key);
|
||||||
key = kNone; // nobody else needs to see these keys
|
key = kNone; // nobody else needs to see these keys
|
||||||
break;
|
break;
|
||||||
|
// Audio track control:
|
||||||
|
case kAudio:
|
||||||
|
if (!Menu && !cOsd::IsOpen())
|
||||||
|
Menu = Temp = cDisplayTracks::Create();
|
||||||
|
else
|
||||||
|
cDisplayTracks::Process(key);
|
||||||
|
key = kNone;
|
||||||
|
break;
|
||||||
// Pausing live video:
|
// Pausing live video:
|
||||||
case kPause:
|
case kPause:
|
||||||
if (!cControl::Control()) {
|
if (!cControl::Control()) {
|
||||||
|
Loading…
Reference in New Issue
Block a user