[mythtv] [PATCH] Beginning radio pvr support
Jeremy Palenchar
jeremyp at mindspring.com
Sat Jan 10 21:06:40 EST 2004
My .02 -
There was some discussion a while back about having a screen saver or no
signal sent to the video card if the OSD was left up. This prevents burn-in
and can allow EntergyStar devices to StandBy.
Something like that feels appropriate here.
I have a macro on my current reciever to turn off the TV while I am
listening to CD's from the CD changer.
It would be nice if we could display some kind of screen saver or blank the
screen when we're listening to sources that do not have a video component.
Pressing a key on the remote would, of course, bring the OSD back.
-J
-----Original Message-----
From: mythtv-dev-bounces at mythtv.org [mailto:mythtv-dev-bounces at mythtv.org]
On Behalf Of Dan Sheridan
Sent: Saturday, January 10, 2004 10:22 AM
To: Development of mythtv
Subject: [mythtv] [PATCH] Beginning radio pvr support
This is a very hacky first attempt (which doesn't work!) at radio support
within mythtv. I am aiming to support radio as another input:
channels can be selected and recorded as if they were TV channels. I have
tuning and input selection sorted out, using an extra column in the
cardinput table to indicate a radio input (though the device name should
probably be in the capturecard table).
My problems are:
o Notifying the various threads that the current stream is
audio-only. At the moment I have a call to a function in
ChannelBase, but this feels messy.
o NuppelVideoRecorder, when setting up, can select a channel. I think
for symmetry that it should use the Channel class instead of
calling the ioctl itself -- is there any reason why it doesn't at
the moment?
o I need to stop the video thread while allowing the audio thread to
continue. You can see my failed attempt below. Any ideas on how I
should be going about this?
When backend support is complete, I'd like to modify the frontend to simply
keep all of the OSDs switch on, with a black bacground, when a stream
without video is played.
Dan.
--
Dan Sheridan -- Research Student -- LFCS, Division of Informatics
University of Edinburgh, King's Buildings, Mayfield Road EH9 3JZ
Index: mythtv/libs/libmythtv/NuppelVideoRecorder.cpp
===================================================================
RCS file: /var/lib/mythcvs/mythtv/libs/libmythtv/NuppelVideoRecorder.cpp,v
retrieving revision 1.152
diff -u -r1.152 NuppelVideoRecorder.cpp
--- mythtv/libs/libmythtv/NuppelVideoRecorder.cpp 7 Jan 2004 06:14:04
-0000 1.152
+++ mythtv/libs/libmythtv/NuppelVideoRecorder.cpp 10 Jan 2004 18:11:05
-0000
@@ -366,6 +366,7 @@
void NuppelVideoRecorder::Unpause(void)
{
+ isradio = channelObj->GetCurrentInputRadio();
pausewritethread = false;
paused = false;
}
@@ -1027,6 +1028,13 @@
gettimeofday(&stm, &tzone);
continue;
}
+ if (isradio)
+ {
+ usleep(500);
+ if (cleartimeonpause)
+ gettimeofday(&stm, &tzone);
+ continue;
+ }
frame = 0;
mm.frame = 0;
@@ -2433,7 +2441,7 @@
} action = ACTION_NONE;
int firsttimecode = -1;
- if (videobuffer[act_video_encode]->freeToEncode)
+ if (!isradio && videobuffer[act_video_encode]->freeToEncode)
{
action = ACTION_VIDEO;
firsttimecode = videobuffer[act_video_encode]->timecode;
Index: mythtv/libs/libmythtv/NuppelVideoRecorder.h
===================================================================
RCS file: /var/lib/mythcvs/mythtv/libs/libmythtv/NuppelVideoRecorder.h,v
retrieving revision 1.66
diff -u -r1.66 NuppelVideoRecorder.h
--- mythtv/libs/libmythtv/NuppelVideoRecorder.h 7 Jan 2004 06:14:04 -0000
1.66
+++ mythtv/libs/libmythtv/NuppelVideoRecorder.h 10 Jan 2004 18:11:05 -0000
@@ -262,6 +262,8 @@
ChannelBase *channelObj;
bool setorigaudio;
+
+ bool isradio;
};
#endif
Index: mythtv/libs/libmythtv/channel.cpp
===================================================================
RCS file: /var/lib/mythcvs/mythtv/libs/libmythtv/channel.cpp,v
retrieving revision 1.60
diff -u -r1.60 channel.cpp
--- mythtv/libs/libmythtv/channel.cpp 9 Jan 2004 21:02:12 -0000 1.60
+++ mythtv/libs/libmythtv/channel.cpp 10 Jan 2004 18:11:05 -0000
@@ -22,6 +22,7 @@
{
device = videodevice;
isopen = false;
+ isradio = false;
videofd = -1;
curList = 0;
defaultFreqTable = 1;
@@ -117,11 +118,26 @@
inputChannel[vin.index] = "";
inputTuneTo[vin.index] = "";
externalChanger[vin.index] = "";
+ inputRadio[vin.index] = "";
vin.index++;
capchannels = vin.index;
}
+ // if there is a radio on this card
+ {
+ QString msg = QString("Probed: %1 - Radio").arg(device);
+ VERBOSE(VB_CHANNEL, msg);
+ channelnames[vin.index] = "Radio";
+ inputChannel[vin.index] = "";
+ inputTuneTo[vin.index] = "";
+ externalChanger[vin.index] = "";
+ inputRadio[vin.index] = ""; // Will be filled in later
+ vin.index++;
+
+ capchannels = vin.index;
+ }
+
if (fmt == "NTSC")
videomode = V4L2_STD_NTSC;
else if (fmt == "ATSC")
@@ -140,7 +156,7 @@
videomode = V4L2_STD_NTSC_M_JP;
pParent->RetrieveInputChannels(inputChannel, inputTuneTo,
- externalChanger);
+ externalChanger, inputRadio);
return;
}
@@ -189,8 +205,20 @@
inputChannel[i] = "";
inputTuneTo[i] = "";
externalChanger[i] = "";
+ inputRadio[i] = "";
}
+ // if there is a radio on this card
+ {
+ QString msg = QString("Probed: %1 - Radio").arg(device);
+ VERBOSE(VB_CHANNEL, msg);
+ channelnames[capchannels] = "Radio";
+ inputChannel[capchannels] = "";
+ inputTuneTo[capchannels] = "";
+ externalChanger[capchannels] = "";
+ inputRadio[capchannels] = ""; // Will be filled in later
+ capchannels++;
+ }
struct video_channel vc;
memset(&vc, 0, sizeof(vc));
ioctl(videofd, VIDIOCGCHAN, &vc);
@@ -199,7 +227,7 @@
videomode = mode;
- pParent->RetrieveInputChannels(inputChannel, inputTuneTo,
externalChanger);
+ pParent->RetrieveInputChannels(inputChannel, inputTuneTo,
externalChanger, inputRadio);
}
int Channel::SetDefaultFreqTable(const QString &name)
@@ -254,6 +282,11 @@
return -1;
}
+bool Channel::GetCurrentInputRadio(void)
+{
+ return isradio;
+}
+
bool Channel::ChannelUp(void)
{
if (ChannelBase::ChannelUp())
@@ -369,6 +402,7 @@
// Tune
if (externalChanger[currentcapchannel].isEmpty())
{
+ cerr << "Requesting " << freqid << "\n";
if (!TuneTo(freqid, finetune))
return false;
}
@@ -392,18 +426,29 @@
bool Channel::TuneTo(const QString &channum, int finetune)
{
- int i = GetCurrentChannelNum(channum);
- if (i == -1)
- return false;
-
- int frequency = curList[i].freq * 16 / 1000 + finetune;
+ int frequency;
+ if (isradio)
+ {
+ frequency = channum.toInt() * 16;
+ cerr << "Tuning to " << frequency << "\n";
+ }
+ else
+ {
+ int i = GetCurrentChannelNum(channum);
+ if (i == -1)
+ return false;
+ frequency = curList[i].freq * 16 / 1000 + finetune;
+ }
if (usingv4l2)
{
struct v4l2_frequency vf;
memset(&vf, 0, sizeof(vf));
vf.frequency = frequency;
- vf.type = V4L2_TUNER_ANALOG_TV;
+ if (isradio)
+ vf.type = V4L2_TUNER_RADIO;
+ else
+ vf.type = V4L2_TUNER_ANALOG_TV;
if (ioctl(videofd, VIDIOC_S_FREQUENCY, &vf) < 0)
{
@@ -424,23 +469,53 @@
void Channel::SwitchToInput(int newcapchannel, bool setstarting)
{
- if (usingv4l2)
+ if (!inputRadio[newcapchannel].isEmpty())
{
- if (ioctl(videofd, VIDIOC_S_INPUT, &newcapchannel) < 0)
- perror("VIDIOC_S_INPUT");
-
- if (ioctl(videofd, VIDIOC_S_STD, &videomode) < 0)
- perror("VIDIOC_S_STD");
+ close(videofd);
+ videofd = open(inputRadio[newcapchannel].ascii(), O_RDWR);
+ if (videofd > 0)
+ isradio = true;
+ else
+ {
+ cerr << "Channel::SwitchToInput(): Can't open: " <<
inputRadio[newcapchannel] << endl;
+ perror(inputRadio[newcapchannel].ascii());
+ return;
+ }
+ } else
+ if (isradio)
+ {
+ close(videofd);
+ videofd = open(device.ascii(), O_RDWR);
+ if (videofd > 0)
+ isradio = false;
+ else
+ {
+ cerr << "Channel::SwitchToInput(): Can't open: " << device <<
endl;
+ perror(device.ascii());
+ return;
+ }
}
- else
+
+ if (!isradio)
{
- struct video_channel set;
- memset(&set, 0, sizeof(set));
- ioctl(videofd, VIDIOCGCHAN, &set);
- set.channel = newcapchannel;
- set.norm = videomode;
- if (ioctl(videofd, VIDIOCSCHAN, &set) < 0)
- perror("VIDIOCSCHAN");
+ if (usingv4l2)
+ {
+ if (ioctl(videofd, VIDIOC_S_INPUT, &newcapchannel) < 0)
+ perror("VIDIOC_S_INPUT");
+
+ if (ioctl(videofd, VIDIOC_S_STD, &videomode) < 0)
+ perror("VIDIOC_S_STD");
+ }
+ else
+ {
+ struct video_channel set;
+ memset(&set, 0, sizeof(set));
+ ioctl(videofd, VIDIOCGCHAN, &set);
+ set.channel = newcapchannel;
+ set.norm = videomode;
+ if (ioctl(videofd, VIDIOCSCHAN, &set) < 0)
+ perror("VIDIOCSCHAN");
+ }
}
currentcapchannel = newcapchannel;
@@ -476,6 +551,9 @@
QString field_name = name;
int field = pParent->GetChannelValue(field_name, this, curchannelname);
+ if (isradio)
+ return;
+
if (usingv4l2)
{
struct v4l2_control ctrl;
Index: mythtv/libs/libmythtv/channel.h
===================================================================
RCS file: /var/lib/mythcvs/mythtv/libs/libmythtv/channel.h,v
retrieving revision 1.26
diff -u -r1.26 channel.h
--- mythtv/libs/libmythtv/channel.h 9 Jan 2004 21:02:12 -0000 1.26
+++ mythtv/libs/libmythtv/channel.h 10 Jan 2004 18:11:05 -0000
@@ -41,8 +41,9 @@
void SetHue();
void SwitchToInput(int newcapchannel, bool setstarting);
-
+
void SetFd(int fd);
+ bool GetCurrentInputRadio(void);
private:
int GetCurrentChannelNum(const QString &channame);
@@ -53,6 +54,7 @@
QString device;
bool isopen;
+ bool isradio;
int videofd;
struct CHANLIST *curList;
Index: mythtv/libs/libmythtv/channelbase.cpp
===================================================================
RCS file: /var/lib/mythcvs/mythtv/libs/libmythtv/channelbase.cpp,v
retrieving revision 1.6
diff -u -r1.6 channelbase.cpp
--- mythtv/libs/libmythtv/channelbase.cpp 12 Sep 2003 16:49:53 -0000
1.6
+++ mythtv/libs/libmythtv/channelbase.cpp 10 Jan 2004 18:11:05 -0000
@@ -70,6 +70,11 @@
return currentcapchannel;
}
+bool ChannelBase::GetCurrentInputRadio(void)
+{
+ return false;
+}
+
void ChannelBase::ToggleInputs(void)
{
int newcapchannel = currentcapchannel;
Index: mythtv/libs/libmythtv/channelbase.h
===================================================================
RCS file: /var/lib/mythcvs/mythtv/libs/libmythtv/channelbase.h,v
retrieving revision 1.3
diff -u -r1.3 channelbase.h
--- mythtv/libs/libmythtv/channelbase.h 7 Aug 2003 17:37:41 -0000 1.3
+++ mythtv/libs/libmythtv/channelbase.h 10 Jan 2004 18:11:05 -0000
@@ -55,6 +55,7 @@
virtual QString GetCurrentInput(void);
virtual int GetCurrentInputNum(void);
+ virtual bool GetCurrentInputRadio(void);
virtual void SetFd(int fd) { (void)fd; }
@@ -69,6 +70,7 @@
map<int, QString> inputChannel;
map<int, QString> inputTuneTo;
map<int, QString> externalChanger;
+ map<int, QString> inputRadio;
// returns index of channame (channel.channum) in curList
QString channelorder;
Index: mythtv/libs/libmythtv/tv_rec.cpp
===================================================================
RCS file: /var/lib/mythcvs/mythtv/libs/libmythtv/tv_rec.cpp,v
retrieving revision 1.126
diff -u -r1.126 tv_rec.cpp
--- mythtv/libs/libmythtv/tv_rec.cpp 9 Jan 2004 21:02:13 -0000
1.126
+++ mythtv/libs/libmythtv/tv_rec.cpp 10 Jan 2004 18:11:06 -0000
@@ -2072,14 +2072,16 @@
void TVRec::RetrieveInputChannels(map<int, QString> &inputChannel,
map<int, QString> &inputTuneTo,
- map<int, QString> &externalChanger)
+ map<int, QString> &externalChanger,
+ map<int, QString> &inputRadio)
{
pthread_mutex_lock(&db_lock);
MythContext::KickDatabase(db_conn);
QString query = QString("SELECT inputname, trim(externalcommand), "
"if(tunechan='', 'Undefined', tunechan), "
- "if(startchan, startchan, '') "
+ "if(startchan, startchan, ''), "
+ "radiodevice "
"FROM capturecard, cardinput "
"WHERE capturecard.cardid = %1 "
"AND capturecard.cardid = cardinput.cardid;")
@@ -2104,6 +2106,7 @@
externalChanger[cap] = result.value(1).toString();
inputTuneTo[cap] = result.value(2).toString();
inputChannel[cap] = result.value(3).toString();
+ inputRadio[cap] = result.value(4).toString();
}
}
Index: mythtv/libs/libmythtv/tv_rec.h
===================================================================
RCS file: /var/lib/mythcvs/mythtv/libs/libmythtv/tv_rec.h,v
retrieving revision 1.47
diff -u -r1.47 tv_rec.h
--- mythtv/libs/libmythtv/tv_rec.h 30 Dec 2003 07:05:23 -0000 1.47
+++ mythtv/libs/libmythtv/tv_rec.h 10 Jan 2004 18:11:06 -0000
@@ -75,7 +75,8 @@
void RetrieveInputChannels(map<int, QString> &inputChannel,
map<int, QString> &inputTuneTo,
- map<int, QString> &externalChanger);
+ map<int, QString> &externalChanger,
+ map<int, QString> &inputRadio);
void StoreInputChannels(map<int, QString> &inputChannel);
bool IsBusy(void);
More information about the mythtv-dev
mailing list