[mythtv] [PATCH] MythTV Previous Channel functionality

Dan M dan at milkcarton.com
Wed Apr 16 19:10:08 EDT 2003


Attached is a patch for MythTV to provide channel history.  To use it 
press the "H" key.  That will go to the previous channel.  If you press 
"H" twice, it will go to the channel you were on two channel changes 
ago.  etc etc.   Pressing "H" once will make it perform just like the 
'Previous Channel' functionality we're all used to on a standard TV.

I'm not entirely happy with the implimentation.  The only way I could 
get it to change the channel was to call TV::ChannelKey(int key) with 
the ascii code for the channel and waiting for the default OSD timeout 
for the channel to change.  I tried to use 
TV::ChangeChannelByString(QString &name) but found that would lock up in 
NuppelVideoPlayer::Pause  (I traced it down to the usleep loop).

I'm releasing it in this state in hopes that someone else can take a 
look at it and point out how to get around this issue.

Patch is made against CVS as of 1730 AKDT (-0900) 16-Apr-2003

If any changes need to be made (other then the issue identified above) 
to get this committed, please let me know.

-dan
-------------- next part --------------
Index: libs/libmythtv/tv_play.cpp
===================================================================
RCS file: /var/lib/cvs/MC/libs/libmythtv/tv_play.cpp,v
retrieving revision 1.43
diff -u -d -r1.43 tv_play.cpp
--- libs/libmythtv/tv_play.cpp	12 Apr 2003 16:12:30 -0000	1.43
+++ libs/libmythtv/tv_play.cpp	17 Apr 2003 00:27:43 -0000
@@ -7,6 +7,7 @@
 #include <qapplication.h>
 #include <qregexp.h>
 #include <qfile.h>
+#include <qtimer.h>

 #include <iostream>
 using namespace std;
@@ -122,6 +123,13 @@

     deinterlace_mode = DEINTERLACE_NONE;
     gContext->addListener(this);
+
+    PrevChannelVector channame_vector( 0 );
+
+    //Create and connect our timer
+    prevChannelTimer = new QTimer(this);
+
+    connect( prevChannelTimer, SIGNAL(timeout()), SLOT(SetPreviousChannel()) );
 }

 void TV::Init(void)
@@ -998,6 +1006,8 @@

             case 'x': ChangeDeinterlacer(); break;

+            case 'H': case 'h': PreviousChannel(); break;
+
             default: break;
         }
     }
@@ -1380,10 +1390,17 @@
     while (!activenvp->GetPause())
         usleep(5);
 
+    //Save the channel if this is the first time
+    if ( channame_vector.size() == 0 )
+        AddPreviousChannel();
+
     activerecorder->Pause();
     activerbuffer->Reset();
     activerecorder->ChangeChannel(direction);
 
+    //Save the channel
+    AddPreviousChannel();
+
     activenvp->ResetPlaying();
     while (!activenvp->ResetYet())
         usleep(5);
@@ -1467,10 +1484,17 @@
     while (!activenvp->GetPause())
         usleep(5);
 
+    //Save the channel if this is the first time
+    if ( channame_vector.size() == 0 )
+        AddPreviousChannel();
+
     activerecorder->Pause();
     activerbuffer->Reset();
     activerecorder->SetChannel(name);
 
+    //Save the new chan
+    AddPreviousChannel();
+
     activenvp->ResetPlaying();
     while (!activenvp->ResetYet())
         usleep(5);
@@ -1481,6 +1505,52 @@
         UpdateOSD();
 
     activenvp->Unpause();
+}
+
+void TV::AddPreviousChannel(void)
+{
+    //Get the current channel and add it to the vector
+    QString dummy;
+    QString chan_name;
+
+    activerecorder->GetChannelInfo( dummy, dummy, dummy, dummy,
+                                    dummy, dummy, dummy, dummy,
+                                    chan_name, dummy);
+
+    //This method builds the stack of previous channels
+    channame_vector.push_back(chan_name);
+}
+
+void TV::PreviousChannel(void)
+{
+    //Increment the times_pressed counter so we know how far to jump
+    times_pressed++;
+
+    //Reset the timer
+    prevChannelTimer->stop();
+    prevChannelTimer->start(750);
+}
+
+void TV::SetPreviousChannel()
+{
+    //Stop the timer
+    prevChannelTimer->stop();
+
+    int vector = (channame_vector.size()) - times_pressed - 1;
+    if ( vector < 0 )
+        vector = 0;
+
+    //Stop the timer
+    prevChannelTimer->stop();
+
+    //Reset the times_pressed counter
+    times_pressed = 0;
+    QString chan = 0;
+
+    for(uint i = 0; i < channame_vector[vector].length(); i++)
+    {
+        ChannelKey( (int ) *channame_vector[vector].mid(i, 1).latin1() );
+    }
 }
 
 void TV::UpdateOSD(void)
Index: libs/libmythtv/tv_play.h
===================================================================
RCS file: /var/lib/cvs/MC/libs/libmythtv/tv_play.h,v
retrieving revision 1.25
diff -u -d -r1.25 tv_play.h
--- libs/libmythtv/tv_play.h	8 Apr 2003 00:59:13 -0000	1.25
+++ libs/libmythtv/tv_play.h	17 Apr 2003 00:27:43 -0000
@@ -3,7 +3,9 @@
 
 #include <qstring.h>
 #include <pthread.h>
+#include <qvaluevector.h>
 
+#include "tv.h"
 #include <qobject.h>
 
 class QSqlDatabase;
@@ -17,7 +19,8 @@
 
 class TV : public QObject
 {
- public:
+Q_OBJECT
+public:
     TV(QSqlDatabase *db);
    ~TV(void);
 
@@ -56,6 +59,9 @@
     void ProcessKeypress(int keypressed);
     void customEvent(QCustomEvent *e);
 
+    void AddPreviousChannel(void);
+    void PreviousChannel(void);
+
  protected:
     void doLoadMenu(void);
     static void *MenuHandler(void *param);
@@ -175,6 +181,14 @@
 
     unsigned int embedid;
     int embx, emby, embw, embh;
+
+    typedef QValueVector<QString> PrevChannelVector;
+    PrevChannelVector channame_vector;
+    unsigned int times_pressed;
+    QTimer *prevChannelTimer;
+
+protected slots:
+    void SetPreviousChannel();
 };
 
 #endif


More information about the mythtv-dev mailing list