Ticket #199: channelgroup.diff

File channelgroup.diff, 49.1 KB (added by Bill <level42@…>, 18 years ago)

Updated for SVN15419; NOTE MYSQL CHANGES HAVE CHANGED SEE NOTE BELOW

  • libs/libmythtv/channelgroup.cpp

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/channelgroup.cpp mythtv/libs/libmythtv/channelgroup.cpp
    old new  
     1#include "libmyth/mythcontext.h"
     2#include "libmyth/mythdbcon.h"
     3#include <qsqldatabase.h>
     4#include <qheader.h>
     5#include <qcursor.h>
     6#include <qlayout.h>
     7#include <iostream>
     8#include "channelutil.h"
     9#include "channelgroup.h"
     10
     11#define LOC QString("Channel Group: ")
     12#define LOC_ERR QString("Channel Group, Error: ")
     13
     14// Storage class for channel group editor in settings
     15class ChannelGroupStorage : public Storage
     16{
     17  public:
     18    ChannelGroupStorage(Setting *_setting,
     19                    uint _chanid, QString _grpname) :
     20        setting(_setting), chanid(_chanid), grpname(_grpname) {}
     21    virtual ~ChannelGroupStorage() {};
     22
     23    virtual void load(void);
     24    virtual void save(void);
     25    virtual void save(QString destination);
     26
     27  protected:
     28    Setting *setting;
     29    uint    chanid;
     30    QString grpname;
     31    int     grpid;
     32};
     33
     34void ChannelGroupStorage::load(void)
     35{
     36    setting->setValue("0");
     37    setting->setUnchanged();
     38   
     39    MSqlQuery query(MSqlQuery::InitCon());
     40   
     41    QString qstr = "SELECT grpid FROM channelgroupnames WHERE name = :GRPNAME";
     42   
     43    query.prepare(qstr);
     44    query.bindValue(":GRPNAME", grpname);
     45
     46    if (!query.exec() || !query.isActive())
     47        MythContext::DBError("ChannelGroupStorage::load", query);
     48    else
     49    {
     50      query.next();
     51      grpid = query.value(0).toUInt();
     52   
     53      qstr = "SELECT * FROM channelgroup WHERE grpid = :GRPID AND chanid = :CHANID";
     54      query.prepare(qstr);
     55      query.bindValue(":GRPID",  grpid);
     56      query.bindValue(":CHANID", chanid);
     57
     58      if (!query.exec() || !query.isActive())
     59          MythContext::DBError("ChannelGroupStorage::load", query);
     60      else if (query.size() > 0)
     61        setting->setValue("1");
     62    }
     63}
     64
     65void ChannelGroupStorage::save(void)
     66{
     67    if (!setting->isChanged())
     68      return;
     69   
     70    QString value = setting->getValue();
     71   
     72    if (value == "1")
     73        ChannelGroup::ToggleChannel(chanid, grpid, false);
     74    else
     75        ChannelGroup::ToggleChannel(chanid, grpid, true);   
     76}
     77
     78void ChannelGroupStorage::save(QString destination)
     79{
     80    save();
     81}
     82
     83ChannelGroupItem& ChannelGroupItem::operator=(const ChannelGroupItem &other)
     84{
     85    grpid     = other.grpid;
     86    name      = QDeepCopy<QString>(other.name);
     87 
     88    return *this;
     89}
     90
     91ChannelGroupItem::ChannelGroupItem(const ChannelGroupItem &other)
     92{
     93    (*this) = other;
     94}
     95
     96inline bool lt_group(const ChannelGroupItem &a, const ChannelGroupItem &b)
     97{
     98    return QString::localeAwareCompare(a.name, b.name) < 0;
     99}
     100
     101bool ChannelGroup::ToggleChannel(uint chanid,int changrpid, int delete_chan)
     102{
     103    // Check if it already exists for that chanid...
     104    MSqlQuery query(MSqlQuery::InitCon());
     105    query.prepare(
     106        "SELECT channelgroup.id "
     107        "FROM channelgroup "
     108        "WHERE channelgroup.chanid = :CHANID AND "
     109        "channelgroup.grpid = :GRPID "
     110        "LIMIT 1");
     111    query.bindValue(":CHANID", chanid);
     112    query.bindValue(":GRPID", changrpid);
     113
     114    if (!query.exec() || !query.isActive())
     115    {
     116        MythContext::DBError("ChannelGroup::ToggleChannel", query);
     117        return false;
     118    }
     119    else if ((query.size() > 0) && delete_chan)
     120    {
     121        // We have a record...Remove it to toggle...
     122        query.next();
     123        QString id = query.value(0).toString();
     124        query.prepare(
     125            QString("DELETE FROM channelgroup "
     126                    "WHERE id = '%1'").arg(id));
     127        query.exec();
     128        VERBOSE(VB_IMPORTANT, LOC + QString("Removing channel with id=%1.").arg(id));
     129    }
     130    else if (query.size() == 0)
     131    {
     132        // We have no record...Add one to toggle...
     133        query.prepare(
     134            QString("INSERT INTO channelgroup (chanid,grpid) "
     135                    "VALUES ('%1','%2')").arg(chanid).arg(changrpid));
     136        query.exec();
     137        VERBOSE(VB_IMPORTANT, LOC + QString("Adding channel %1 to group %2.").arg(chanid).arg(changrpid));
     138    }
     139
     140    return true;
     141}
     142
     143ChannelGroupList ChannelGroup::GetChannelGroups(void)
     144{
     145    ChannelGroupList list;
     146   
     147    MSqlQuery query(MSqlQuery::InitCon());
     148   
     149    QString qstr = "SELECT grpid, name FROM channelgroupnames";
     150   
     151    query.prepare(qstr);
     152
     153    if (!query.exec() || !query.isActive())
     154        MythContext::DBError("ChannelGroup::GetChannelGroups", query);
     155    else
     156    {
     157        while (query.next())
     158        {
     159           ChannelGroupItem group(query.value(0).toUInt(),
     160                              query.value(1).toString());
     161           list.push_back(group);
     162        }
     163    }
     164   
     165    stable_sort(list.begin(), list.end(), lt_group);
     166
     167    return list;
     168}
     169
     170// Cycle through the available groups, then all channels
     171// Will cycle through to end then return -1
     172// To signify all channels.
     173int ChannelGroup::GetNextChannelGroup(const ChannelGroupList &sorted, int grpid)
     174{
     175    // If no groups return -1 for all channels
     176    if (sorted.empty())
     177      return -1;
     178   
     179    // If grpid is all channels (-1), then return the first grpid 
     180    if (grpid == -1)
     181      return sorted[0].grpid;
     182     
     183    ChannelGroupList::const_iterator it = find(sorted.begin(), sorted.end(), grpid);
     184
     185    // If grpid is not in the list, return -1 for all channels
     186    if (it == sorted.end())
     187        return -1;
     188
     189    ++it;
     190
     191    // If we reached the end, the next option is all channels (-1)
     192    if (it == sorted.end())
     193       return -1;
     194
     195    return it->grpid;
     196}
     197
     198QString ChannelGroup::GetChannelGroupName(const ChannelGroupList &sorted, int grpid)
     199{
     200    // All Channels
     201    if (grpid == -1)
     202      return "All Channels";
     203
     204    ChannelGroupList::const_iterator it = find(sorted.begin(), sorted.end(), grpid);
     205       
     206    // If grpid wasn't found, return blank.   
     207    if (it == sorted.end())
     208       return "";
     209    else
     210       return it->name;
     211}
     212
     213class ChannelCheckBox : public CheckBoxSetting, public ChannelGroupStorage
     214{
     215  public:
     216    ChannelCheckBox(const ChannelGroupConfig& _parent, const uint chanid, const QString channum,
     217               const QString channame, const QString grpname):
     218        CheckBoxSetting(this),
     219        ChannelGroupStorage(this, chanid, grpname)
     220    {
     221        setLabel(QObject::tr(QString("%1 %2").arg(channum).arg(channame)));
     222        setHelpText(QObject::tr("Select/Unselect channels for this channel group"));
     223    };
     224};
     225
     226ChannelGroupConfig::ChannelGroupConfig(QString _name)
     227    : name(_name)
     228{
     229    VerticalConfigurationGroup   *cgroup;
     230    HorizontalConfigurationGroup *columns;
     231
     232    DBChanList chanlist = ChannelUtil::GetChannels(0, true, "channum, callsign");
     233    ChannelUtil::SortChannels(chanlist, "channum", true);
     234
     235    DBChanList::iterator it = chanlist.begin();
     236    int i,j = 0;
     237    int p = 1;
     238    int pages = (int)((float)chanlist.size() / 8.0 / 3.0 + 0.5);
     239   
     240    do
     241    { 
     242        columns = new HorizontalConfigurationGroup(false,false,false,false);
     243        columns->setLabel(getName() + " " +
     244                          QObject::tr("Channel Group - Page ") +
     245                          QObject::tr(QString("%1 of %2").arg(p).arg(pages)));
     246       
     247        for (j = 0; ((j < 3) && (it < chanlist.end())); ++j)
     248        {
     249            cgroup = new VerticalConfigurationGroup(false,false,false,false);
     250           
     251            for (i = 0; ((i < 8) && (it < chanlist.end())); ++i)
     252            {
     253                cgroup->addChild(new ChannelCheckBox(*this, it->chanid, it->channum, it->name, _name));
     254                ++it;
     255            }
     256            columns->addChild(cgroup);
     257        }
     258       
     259        ++p;
     260        addChild(columns);
     261    } while (it < chanlist.end());
     262
     263}
     264
     265ChannelGroupEditor::ChannelGroupEditor(void) :
     266    listbox(new ListBoxSetting(this)), lastValue("__CREATE_NEW_GROUP__")
     267{
     268    listbox->setLabel(tr("Channel Groups"));
     269    addChild(listbox);
     270}
     271
     272void ChannelGroupEditor::open(QString name)
     273{
     274    lastValue = name;
     275    bool created = false;
     276
     277    if (name == "__CREATE_NEW_GROUP__")
     278    {
     279        name = "";
     280       
     281        bool ok = MythPopupBox::showGetTextPopup(gContext->GetMainWindow(),
     282            tr("Create New Channel Group"),
     283            tr("Enter group name or press SELECT to enter text via the "
     284               "On Screen Keyboard"), name);
     285        if (!ok)
     286            return;
     287
     288        MSqlQuery query(MSqlQuery::InitCon());
     289        query.prepare("INSERT INTO channelgroupnames (name) VALUES (:NAME);");
     290        query.bindValue(":NAME", name.utf8());
     291        if (!query.exec())
     292            MythContext::DBError("ChannelGroupEditor::open", query);
     293        else
     294            created = true;
     295    }
     296   
     297    ChannelGroupConfig group(name);
     298   
     299    if (group.exec() == QDialog::Accepted || !created)
     300        lastValue = name;
     301
     302};
     303
     304void ChannelGroupEditor::doDelete(void)
     305{
     306    QString name = listbox->getValue();
     307    if (name == "__CREATE_NEW_GROUP__")
     308        return;
     309
     310    QString message = tr("Delete '%1' Channel group?").arg(name);
     311   
     312    DialogCode value = MythPopupBox::Show2ButtonPopup(
     313        gContext->GetMainWindow(),
     314        "", message,
     315        tr("Yes, delete group"),
     316        tr("No, Don't delete group"), kDialogCodeButton1);
     317
     318    if (kDialogCodeButton0 == value)
     319    {
     320        MSqlQuery query(MSqlQuery::InitCon());
     321
     322        // Find out channel group id
     323        query.prepare("SELECT grpid FROM channelgroupnames WHERE name = :NAME;");
     324        query.bindValue(":NAME", name.utf8());
     325        if (!query.exec())
     326            MythContext::DBError("ChannelGroupEditor::doDelete", query);
     327        query.next();
     328        uint grpid = query.value(0).toUInt();
     329
     330        // Delete channels from this group
     331        query.prepare("DELETE FROM channelgroup WHERE grpid = :GRPID;");
     332        query.bindValue(":GRPID", grpid);
     333        if (!query.exec())
     334            MythContext::DBError("ChannelGroupEditor::doDelete", query);
     335       
     336        // Now delete the group from channelgroupnames
     337        query.prepare("DELETE FROM channelgroupnames WHERE name = :NAME;");
     338        query.bindValue(":NAME", name.utf8());
     339        if (!query.exec())
     340            MythContext::DBError("ChannelGroupEditor::doDelete", query);
     341
     342        lastValue = "__CREATE_NEW_GROUP__";
     343        load();
     344    }
     345
     346    listbox->setFocus();
     347}
     348
     349void ChannelGroupEditor::load(void)
     350{
     351    listbox->clearSelections();
     352   
     353    ChannelGroupList changrplist;
     354
     355    changrplist = ChannelGroup::GetChannelGroups();
     356
     357    ChannelGroupList::iterator it;
     358
     359    for (it = changrplist.begin(); it < changrplist.end(); ++it)
     360       listbox->addSelection(it->name);
     361       
     362    listbox->addSelection(tr("(Create new group)"), "__CREATE_NEW_GROUP__");
     363
     364    listbox->setValue(lastValue);
     365}
     366
     367DialogCode ChannelGroupEditor::exec(void)
     368{
     369    while (ConfigurationDialog::exec() == kDialogCodeAccepted)
     370        open(listbox->getValue());
     371
     372    return kDialogCodeRejected;
     373}
     374
     375MythDialog* ChannelGroupEditor::dialogWidget(MythMainWindow* parent,
     376                                          const char* widgetName)
     377{
     378    dialog = ConfigurationDialog::dialogWidget(parent, widgetName);
     379    connect(dialog, SIGNAL(menuButtonPressed()), this, SLOT(doDelete()));
     380    connect(dialog, SIGNAL(deleteButtonPressed()), this, SLOT(doDelete()));
     381    return dialog;
     382}
  • libs/libmythtv/channelgroup.h

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/channelgroup.h mythtv/libs/libmythtv/channelgroup.h
    old new  
     1#ifndef CHANNELGROUP_H
     2#define CHANNELGROUP_H
     3
     4#include "qstringlist.h"
     5#include "libmyth/settings.h"
     6#include "libmyth/mythwidgets.h"
     7
     8class ChannelGroupItem
     9{
     10  public:
     11    ChannelGroupItem(const ChannelGroupItem&);
     12    ChannelGroupItem(const uint _grpid,
     13                  const QString &_name) :
     14        grpid(_grpid), name(_name) {}
     15
     16    bool operator == (uint _grpid) const
     17        { return grpid == _grpid; }
     18
     19    ChannelGroupItem& operator=(const ChannelGroupItem&);
     20
     21  public:
     22    uint    grpid;
     23    QString name;
     24};
     25typedef vector<ChannelGroupItem> ChannelGroupList;
     26
     27/** \class ChannelGroup
     28*/
     29class MPUBLIC ChannelGroup
     30{
     31  public:
     32    // ChannelGroup
     33    static ChannelGroupList  GetChannelGroups(void);
     34    static bool              ToggleChannel(uint chanid,int changrpid, int delete_chan);
     35    static int               GetNextChannelGroup(const ChannelGroupList &sorted, int grpid);
     36    static QString           GetChannelGroupName(const ChannelGroupList &sorted, int grpid);
     37
     38   
     39  private:
     40
     41};
     42
     43class MPUBLIC ChannelGroupConfig: public ConfigurationWizard
     44{
     45 public:
     46    ChannelGroupConfig(QString _name);
     47    QString getName(void) const { return name; }
     48
     49 private:
     50    QString name;
     51};
     52
     53class MPUBLIC ChannelGroupEditor : public QObject, public ConfigurationDialog
     54{
     55    Q_OBJECT
     56
     57  public:
     58    ChannelGroupEditor(void);
     59    virtual DialogCode exec(void);
     60    virtual void load(void);
     61    virtual void save(void) { };
     62    virtual void save(QString) { };
     63    virtual MythDialog* dialogWidget(MythMainWindow* parent,
     64                                     const char* widgetName=0);
     65
     66  protected slots:
     67    void open(QString name);
     68    void doDelete(void);
     69
     70  protected:
     71    ListBoxSetting *listbox;
     72    QString         lastValue;
     73};
     74
     75#endif
  • libs/libmythtv/channelutil.cpp

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/channelutil.cpp mythtv/libs/libmythtv/channelutil.cpp
    old new  
    12961296                           dvb_transportid, dvb_networkid, dtv_si_std);
    12971297}
    12981298
    1299 DBChanList ChannelUtil::GetChannels(uint sourceid, bool vis_only, QString grp)
     1299DBChanList ChannelUtil::GetChannels(uint sourceid, bool vis_only, QString grp, int changrpid)
    13001300{
    13011301    DBChanList list;
    1302     QMap<uint,uint> favorites;
    13031302    MSqlQuery query(MSqlQuery::InitCon());
    1304     query.prepare(
    1305         "SELECT chanid, favid "
    1306         "FROM favorites");
    1307     if (!query.exec() || !query.isActive())
    1308         MythContext::DBError("get channels -- favorites", query);
    1309     else
    1310     {
    1311         while (query.next())
    1312             favorites[query.value(0).toUInt()] = query.value(1).toUInt();
     1303   
     1304    QString qstr = "SELECT channum, callsign, channel.chanid, "
     1305           "       atsc_major_chan, atsc_minor_chan, "
     1306           "       name, icon, visible "
     1307           "FROM channel";
     1308
     1309
     1310    if (changrpid > -1)
     1311    {
     1312       // Select only channels from the specified channel group
     1313       
     1314       if (sourceid)
     1315           qstr += QString(",channelgroup WHERE sourceid='%1' AND ").arg(sourceid);
     1316       else
     1317           qstr += ",cardinput,capturecard,channelgroup "
     1318                   "WHERE cardinput.sourceid = channel.sourceid   AND "
     1319                   "      cardinput.cardid   = capturecard.cardid AND ";
     1320                   
     1321       qstr += QString("channel.chanid = channelgroup.chanid AND channelgroup.grpid ='%1' ").arg(changrpid);
    13131322    }
    1314 
    1315     QString qstr =
    1316         "SELECT channum, callsign, chanid, "
    1317         "       atsc_major_chan, atsc_minor_chan, "
    1318         "       name, icon, visible "
    1319         "FROM channel ";
    1320 
    1321     if (sourceid)
    1322         qstr += QString("WHERE sourceid='%1' ").arg(sourceid);
    13231323    else
    1324         qstr += ",cardinput,capturecard "
    1325             "WHERE cardinput.sourceid = channel.sourceid   AND "
    1326             "      cardinput.cardid   = capturecard.cardid     ";
     1324    {
     1325       // Select All channels
     1326       
     1327       if (sourceid)
     1328           qstr += QString(" WHERE sourceid='%1' ").arg(sourceid);
     1329       else
     1330           qstr += ",cardinput,capturecard "
     1331                   "WHERE cardinput.sourceid = channel.sourceid   AND "
     1332                   "      cardinput.cardid   = capturecard.cardid     ";
     1333    }
    13271334
    13281335    if (vis_only)
    13291336        qstr += "AND visible=1 ";
     
    13491356            query.value(2).toUInt(),                      /* chanid     */
    13501357            query.value(3).toUInt(),                      /* ATSC major */
    13511358            query.value(4).toUInt(),                      /* ATSC minor */
    1352             favorites[query.value(2).toUInt()],           /* favid      */
     1359            0,                                            /* Was favid, need to remove */
    13531360            query.value(7).toBool(),                      /* visible    */
    13541361            QString::fromUtf8(query.value(5).toString()), /* name       */
    13551362            query.value(6).toString());                   /* icon       */
     
    15251532        } while ((it != start) && skip_non_visible && !it->visible);
    15261533
    15271534    }
    1528     else if (CHANNEL_DIRECTION_UP == direction)
     1535    else if ((CHANNEL_DIRECTION_UP == direction) || (CHANNEL_DIRECTION_FAVORITE == direction))
    15291536    {
    15301537        do
    15311538        {
     
    15341541                it = sorted.begin();
    15351542        } while ((it != start) && skip_non_visible && !it->visible);
    15361543    }
    1537     else if (CHANNEL_DIRECTION_FAVORITE == direction)
    1538     {
    1539         do
    1540         {
    1541             it++;
    1542             if (it == sorted.end())
    1543                 it = sorted.begin();
    1544 
    1545         } while ((it != start) &&
    1546                  (!it->favorite || (skip_non_visible && !it->visible)));
    1547     }
     1544//    else if (CHANNEL_DIRECTION_FAVORITE == direction)
     1545//    {
     1546//        do
     1547//        {
     1548//            it++;
     1549//            if (it == sorted.end())
     1550//                it = sorted.begin();
     1551
     1552//        } while ((it != start) &&
     1553//                 (!it->favorite || (skip_non_visible && !it->visible)));
     1554//    }
    15481555
    15491556    return it->chanid;
    15501557}
  • libs/libmythtv/channelutil.h

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/channelutil.h mythtv/libs/libmythtv/channelutil.h
    old new  
    4343};
    4444typedef vector<DBChannel> DBChanList;
    4545
    46 
    4746/** \class ChannelUtil
    4847 *  \brief Collection of helper utilities for channel DB use
    4948 */
     
    164163    static QString GetVideoFilters(uint sourceid, const QString &channum)
    165164        { return GetChannelValueStr("videofilters", sourceid, channum); }
    166165
    167     static DBChanList GetChannels(uint srcid, bool vis_only, QString grp="");
     166    static DBChanList GetChannels(uint srcid, bool vis_only, QString grp="", int changrpid=-1);
    168167    static void    SortChannels(DBChanList &list, const QString &order,
    169168                                bool eliminate_duplicates = false);
    170169    static void    EliminateDuplicateChanNum(DBChanList &list);
  • libs/libmythtv/guidegrid.cpp

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/guidegrid.cpp mythtv/libs/libmythtv/guidegrid.cpp
    old new  
    2020
    2121#include "mythcontext.h"
    2222#include "mythdbcon.h"
    23 #include "guidegrid.h"
    2423#include "infostructs.h"
    2524#include "programinfo.h"
    2625#include "scheduledrecording.h"
     
    3231#include "customedit.h"
    3332#include "util.h"
    3433#include "remoteutil.h"
    35 #include "channelutil.h"
     34#include "guidegrid.h"
    3635
    3736bool RunProgramGuide(uint &chanid, QString &channum,
    3837                     bool thread, TV *player,
    39                      bool allowsecondaryepg)
     38                     bool allowsecondaryepg, int *changrpid)
    4039{
    4140    bool channel_changed = false;
     41    int  channel_group  = -1;
     42   
     43    if (changrpid != NULL)
     44      channel_group = *changrpid;
    4245
    4346    if (thread)
    4447        qApp->lock();
     
    4750
    4851    GuideGrid *gg = new GuideGrid(gContext->GetMainWindow(),
    4952                                  chanid, channum,
    50                                   player, allowsecondaryepg, "guidegrid");
     53                                  player, allowsecondaryepg, "guidegrid",
     54                                  channel_group);
    5155
    5256    gg->Show();
    5357
     
    7074
    7175    if (thread)
    7276        qApp->lock();
    73 
     77   
     78    if (changrpid != NULL)
     79      *changrpid = gg->GetChanGrp();
     80   
    7481    delete gg;
    7582
    7683    gContext->removeCurrentLocation();
     
    8491GuideGrid::GuideGrid(MythMainWindow *parent,
    8592                     uint chanid, QString channum,
    8693                     TV *player, bool allowsecondaryepg,
    87                      const char *name)
     94                     const char *name, int changrpid)
    8895         : MythDialog(parent, name)
    8996{
    9097    desiredDisplayChans = DISPLAY_CHANS = 6;
    9198    DISPLAY_TIMES = 30;
    9299    int maxchannel = 0;
    93100    m_currentStartChannel = 0;
     101   
     102    m_changrpid = changrpid;
     103    m_changrplist = ChannelGroup::GetChannelGroups();
    94104
    95105    m_player = player;
    96106
     
    105115    infoRect = QRect(0, 0, 0, 0);
    106116    curInfoRect = QRect(0, 0, 0, 0);
    107117    videoRect = QRect(0, 0, 0, 0);
     118    changrpRect = QRect(0, 0, 0, 0);
    108119
    109120    jumpToChannelEnabled = gContext->GetNumSetting("EPGEnableJumpToChannel", 0);
    110121    jumpToChannelActive = false;
     
    125136    if (m_player && m_player->IsRunning() && !allowsecondaryepg)
    126137        videoRect = QRect(0, 0, 1, 1);
    127138
    128     showFavorites = gContext->GetNumSetting("EPGShowFavorites", 0);
    129139    gridfilltype = gContext->GetNumSetting("EPGFillType", UIGuideType::Alpha);
    130140    if (gridfilltype < (int)UIGuideType::Alpha)
    131141    { // update old settings to new fill types
     
    182192            container->SetDrawFontShadow(false);
    183193    }
    184194
     195    container = theme->GetSet("channel_group");
     196    if (container)
     197    {
     198        UITextType *type = (UITextType *)container->GetType("changroup");
     199        QString changroup;
     200       
     201        changroup = ChannelGroup::GetChannelGroupName(m_changrplist, m_changrpid);
     202       
     203        if (type)
     204            type->SetText(changroup);
     205    }
     206
    185207    channelOrdering = gContext->GetSetting("ChannelOrdering", "channum");
    186208    dateformat = gContext->GetSetting("ShortDateFormat", "ddd d");
    187209    unknownTitle = gContext->GetSetting("UnknownTitle", "Unknown");
     
    559581        curInfoRect = area;
    560582    if (name.lower() == "current_video")
    561583        videoRect = area;
     584    if (name.lower() == "channel_group")
     585        changrpRect = area;
    562586}
    563587
    564588QString GuideGrid::GetChanNum(void)
     
    618642    m_channelInfos.clear();
    619643
    620644    DBChanList channels = ChannelUtil::GetChannels(0, true,
    621                                                    "channum, callsign");
     645                                                   "channum, callsign", m_changrpid);
    622646    ChannelUtil::SortChannels(channels, channelOrdering, true);
    623647
    624     if (showFavorites)
    625     {
    626         DBChanList tmp;
    627         for (uint i = 0; i < channels.size(); i++)
    628         {
    629             if (channels[i].favorite)
    630                 tmp.push_back(channels[i]);
    631         }
    632 
    633         if (!tmp.empty())
    634             channels = tmp;
    635     }
    636 
    637648    bool startingset = false;
    638649    for (uint i = 0; i < channels.size(); i++)
    639650    {
     
    646657        val.chanstr  = channels[chan].channum;
    647658        val.chanid   = channels[chan].chanid;
    648659        val.callsign = channels[chan].callsign;
    649         val.favid    = channels[chan].favorite;
     660//        val.favid    = channels[chan].favorite;
    650661        val.channame = channels[chan].name;
    651662        val.iconpath = channels[chan].icon;
    652663        val.iconload = false;
     
    746757    }
    747758}
    748759
     760void GuideGrid::fillChanGroupInfo(void)
     761{
     762    LayerSet   *container = NULL;
     763    UITextType *type = NULL;
     764   
     765    container = theme->GetSet("channel_group");
     766    if (container)
     767    {
     768        type = (UITextType *)container->GetType("changroup");
     769        QString changroup;
     770       
     771        changroup = ChannelGroup::GetChannelGroupName(m_changrplist, m_changrpid);
     772       
     773        if (type)
     774            type->SetText(changroup);
     775    }
     776}
     777
    749778void GuideGrid::fillProgramRowInfos(unsigned int row)
    750779{
    751780    LayerSet *container = NULL;
     
    10221051        paintPrograms(&p);
    10231052    if (r.intersects(curInfoRect))
    10241053        paintCurrentInfo(&p);
     1054    if (r.intersects(changrpRect))
     1055        paintChanGroupInfo(&p);
    10251056
    10261057    // if jumpToChannel has its own rect, use that; otherwise use the date's rect
    10271058    if ((jumpToChannelHasRect && r.intersects(jumpToChannelRect)) ||
     
    11351166    p->drawPixmap(dr.topLeft(), pix);
    11361167}
    11371168
     1169void GuideGrid::paintChanGroupInfo(QPainter *p)
     1170{
     1171    QRect dr = changrpRect;
     1172    QPixmap pix(dr.size());
     1173    pix.fill(this, dr.topLeft());
     1174    QPainter tmp(&pix);
     1175
     1176    LayerSet *container = NULL;
     1177    container = theme->GetSet("channel_group");
     1178    if (container)
     1179    {
     1180        container->Draw(&tmp, 1, m_context);
     1181        container->Draw(&tmp, 2, m_context);
     1182        container->Draw(&tmp, 3, m_context);
     1183        container->Draw(&tmp, 4, m_context);
     1184        container->Draw(&tmp, 5, m_context);
     1185        container->Draw(&tmp, 6, m_context);
     1186        container->Draw(&tmp, 7, m_context);
     1187        container->Draw(&tmp, 8, m_context);
     1188    }
     1189    tmp.end();
     1190    p->drawPixmap(dr.topLeft(), pix);
     1191}
     1192
    11381193void GuideGrid::paintChannels(QPainter *p)
    11391194{
    11401195    QRect cr = channelRect;
     
    11921247        }
    11931248
    11941249        QString tmpChannelFormat = channelFormat;
    1195         if (chinfo->favid > 0)
    1196         {
    1197             tmpChannelFormat.insert(tmpChannelFormat.find('<'), "* ");
    1198             tmpChannelFormat.insert(tmpChannelFormat.find('>') + 1, " *");
    1199         }
     1250//        if (chinfo->favid > 0)
     1251//        {
     1252//            tmpChannelFormat.insert(tmpChannelFormat.find('<'), "* ");
     1253//            tmpChannelFormat.insert(tmpChannelFormat.find('>') + 1, " *");
     1254//        }
    12001255
    12011256        if (type)
    12021257        {
     
    12261281        }
    12271282    }
    12281283
     1284    if (m_channelInfos.size() == 0)
     1285    {
     1286       // if the user has selected a channel group with no channels
     1287       // Reset the text and icon. This will display one blank line
     1288       // to show that the channel group has no channels
     1289       if (type)
     1290       {
     1291         type->SetText(0, "");
     1292         type->ResetImage(0);
     1293       }
     1294    }
     1295
    12291296    if (container)
    12301297    {
    12311298        container->Draw(&tmp, 1, m_context);
     
    13601427
    13611428void GuideGrid::toggleGuideListing()
    13621429{
    1363     showFavorites = (!showFavorites);
    1364     generateListings();
     1430    int oldchangrpid = m_changrpid;
     1431   
     1432    m_changrpid = ChannelGroup::GetNextChannelGroup(m_changrplist, oldchangrpid);
     1433   
     1434    if (oldchangrpid != m_changrpid)
     1435      generateListings();
     1436     
     1437    fillChanGroupInfo();
     1438    update(changrpRect);
    13651439}
    13661440
    13671441void GuideGrid::generateListings()
     
    13801454    update(fullRect);
    13811455}
    13821456
     1457int GuideGrid::SelectChannelGroup()
     1458{
     1459    if (m_changrplist.empty())
     1460    {
     1461      MythPopupBox::showOkPopup(gContext->GetMainWindow(), "",
     1462                                "You don't have any channel groups defined");
     1463
     1464      return -1;
     1465    }
     1466   
     1467    MythPopupBox *popup = new MythPopupBox(gContext->GetMainWindow(), "SelectChannelGroup Popup");
     1468    popup->addLabel("Select Channel Group");
     1469
     1470    for (uint i = 0; i < m_changrplist.size(); i++)
     1471      popup->addButton(m_changrplist[i].name);
     1472
     1473    popup->addButton(tr("Cancel"))->setFocus();
     1474
     1475    DialogCode result = popup->ExecPopup();
     1476   
     1477    popup->deleteLater();
     1478
     1479    // If the user cancelled, return a special value
     1480    if (result == MythDialog::Rejected)
     1481      return -1;
     1482    else
     1483      return m_changrplist[result - kDialogCodeListStart].grpid;
     1484}
     1485
    13831486void GuideGrid::toggleChannelFavorite()
    13841487{
    1385     MSqlQuery query(MSqlQuery::InitCon());
     1488    int grpid;
     1489
     1490    if (m_changrpid == -1)
     1491    {
     1492      grpid = SelectChannelGroup();
     1493     
     1494      if (grpid == -1)
     1495        return;
     1496    }
     1497    else
     1498      grpid = m_changrpid;
    13861499
    13871500    // Get current channel id, and make sure it exists...
    13881501    int chanNum = m_currentRow + m_currentStartChannel;
     
    13931506    if (chanNum < 0)
    13941507        chanNum = 0;
    13951508
    1396     int favid = m_channelInfos[chanNum].favid;
    13971509    int chanid = m_channelInfos[chanNum].chanid;
    1398 
    1399     if (favid > 0)
    1400     {
    1401         query.prepare("DELETE FROM favorites WHERE favid = :FAVID ;");
    1402         query.bindValue(":FAVID", favid);
    1403         query.exec();
    1404     }
    1405     else
    1406     {
    1407         // We have no favorites record...Add one to toggle...
    1408         query.prepare("INSERT INTO favorites (chanid) VALUES (:FAVID);");
    1409         query.bindValue(":FAVID", chanid);
    1410         query.exec();
    1411     }
    1412 
    1413     if (showFavorites)
    1414         generateListings();
     1510   
     1511    if (m_changrpid == -1)
     1512       // If currently viewing all channels, allow to add only not delete
     1513       ChannelGroup::ToggleChannel(chanid, grpid, false);
    14151514    else
    1416     {
    1417         int maxchannel = 0;
    1418         DISPLAY_CHANS = desiredDisplayChans;
    1419         fillChannelInfos(false);
    1420         maxchannel = max((int)m_channelInfos.size() - 1, 0);
    1421         DISPLAY_CHANS = min(DISPLAY_CHANS, maxchannel + 1);
    1422 
    1423         repaint(channelRect, false);
    1424     }
     1515       // Only allow delete if viewing the favorite group in question
     1516       ChannelGroup::ToggleChannel(chanid, grpid, true);
     1517     
     1518    // If viewing favorites, refresh because a channel was removed
     1519    if (m_changrpid != -1)
     1520       generateListings();
    14251521}
    14261522
    14271523void GuideGrid::cursorLeft()
  • libs/libmythtv/guidegrid.h

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/guidegrid.h mythtv/libs/libmythtv/guidegrid.h
    old new  
    1212#include "uitypes.h"
    1313#include "xmlparse.h"
    1414#include "libmythtv/programinfo.h"
     15#include "libmythtv/channelgroup.h"
    1516
    1617using namespace std;
    1718
     
    2930MPUBLIC
    3031bool RunProgramGuide(uint &startChanId, QString &startChanNum,
    3132                     bool thread = false, TV *player = NULL,
    32                      bool allowsecondaryepg = true);
     33                     bool allowsecondaryepg = true, int *changrpid = NULL);
    3334
    3435
    3536class GuideGrid : public MythDialog
     
    3940    GuideGrid(MythMainWindow *parent,
    4041              uint chanid = 0, QString channum = "",
    4142              TV *player = NULL, bool allowsecondaryepg = true,
    42               const char *name = "GuideGrid");
     43              const char *name = "GuideGrid", int changrpid = -1);
    4344   ~GuideGrid();
    4445
    4546    uint    GetChanID(void);
    4647    QString GetChanNum(void);
     48    int     GetChanGrp(void) {return m_changrpid;}
    4749
    4850  protected slots:
    4951    void cursorLeft();
     
    104106    void paintPrograms(QPainter *);
    105107    void paintCurrentInfo(QPainter *);
    106108    void paintInfo(QPainter *);
     109    void paintChanGroupInfo(QPainter *p);
    107110 
    108111    void resizeImage(QPixmap *, QString);
    109112    void LoadWindow(QDomElement &);
     
    128131    QRect infoRect;
    129132    QRect curInfoRect;
    130133    QRect videoRect;
     134    QRect changrpRect;
    131135
    132136    void fillChannelInfos(bool gotostartchannel = true);
    133137
     
    135139
    136140    void fillProgramInfos(void);
    137141    void fillProgramRowInfos(unsigned int row);
     142   
     143    void fillChanGroupInfo(void);
    138144
    139145    void setStartChannel(int newStartChannel);
    140146
    141147    void createProgramLabel(int, int);
     148   
     149    int SelectChannelGroup();
    142150
    143151    vector<ChannelInfo> m_channelInfos;
    144152    TimeInfo *m_timeInfos[MAX_DISPLAY_TIMES];
     
    157165    int m_currentCol;
    158166
    159167    bool selectState;
    160     bool showFavorites;
    161168    bool sortReverse;
    162169    QString channelFormat;
    163170
     
    180187    QTimer *videoRepaintTimer;
    181188
    182189    bool keyDown;
     190   
     191    int  m_changrpid;
     192    ChannelGroupList m_changrplist;
    183193
    184194    void jumpToChannelResetAndHide();
    185195    void jumpToChannelCancel();
  • libs/libmythtv/libmythtv.pro

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/libmythtv.pro mythtv/libs/libmythtv/libmythtv.pro
    old new  
    142142HEADERS += channeleditor.h          channelsettings.h
    143143HEADERS += previewgenerator.h       transporteditor.h
    144144HEADERS += importicons.h
     145HEADERS += channelgroup.h
    145146
    146147SOURCES += programinfo.cpp          proglist.cpp
    147148SOURCES += storagegroup.cpp
     
    165166SOURCES += channeleditor.cpp        channelsettings.cpp
    166167SOURCES += previewgenerator.cpp     transporteditor.cpp
    167168SOURCES += importicons.cpp
     169SOURCES += channelgroup.cpp
    168170
    169171# DiSEqC
    170172HEADERS += diseqc.h                 diseqcsettings.h
  • libs/libmythtv/tv_play.cpp

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/tv_play.cpp mythtv/libs/libmythtv/tv_play.cpp
    old new  
    8383    bool showDialogs = true;
    8484    bool playCompleted = false;
    8585    ProgramInfo *curProgram = NULL;
    86    
    8786
    8887    if (tvrec)
    8988        curProgram = new ProgramInfo(*tvrec);
     
    223222   
    224223    bool allowrerecord = tv->getAllowRerecord();
    225224    bool deleterecording = tv->getRequestDelete();
    226    
     225
     226    tv->SaveChannelGroup();
     227
    227228    delete tv;
    228229   
    229230    if (curProgram)
     
    277278            "in the program guide", "0");
    278279    REG_KEY("TV Frontend", "GUIDE", "Show the Program Guide", "S");
    279280    REG_KEY("TV Frontend", "FINDER", "Show the Program Finder", "#");
    280     REG_KEY("TV Frontend", "NEXTFAV", "Toggle showing all channels or just "
    281             "favorites in the program guide.", "/");
     281    REG_KEY("TV Frontend", "NEXTFAV", "Cycle through channel groups and all channels "
     282            "in the program guide.", "/,S");
    282283    REG_KEY("TV Frontend", "CHANUPDATE", "Switch channels without exiting "
    283284            "guide in Live TV mode.", "X");
    284285    REG_KEY("TV Frontend", "VOLUMEDOWN", "Volume down", "[,{,F10,Volume Down");
     
    616617    stickykeys           = gContext->GetNumSetting("StickyKeys");
    617618    ff_rew_repos         = gContext->GetNumSetting("FFRewReposTime", 100)/100.0;
    618619    ff_rew_reverse       = gContext->GetNumSetting("FFRewReverse", 1);
     620    channel_group_id     = gContext->GetNumSetting("ChannelGroupDefault", -1);
     621    browse_changrp       = gContext->GetNumSetting("BrowseChannelGroup", 0);
     622   
     623    if (browse_changrp && (channel_group_id > -1))
     624    {
     625      m_channellist = ChannelUtil::GetChannels(0, true, "channum, callsign", channel_group_id);
     626      ChannelUtil::SortChannels(m_channellist, "channum", true);
     627    }
     628   
     629    m_changrplist  = ChannelGroup::GetChannelGroups();
     630
    619631    int def[8] = { 3, 5, 10, 20, 30, 60, 120, 180 };
    620632    for (uint i = 0; i < sizeof(def)/sizeof(def[0]); i++)
    621633        ff_rew_speeds.push_back(
     
    779791    }
    780792}
    781793
     794void TV::SaveChannelGroup(void)
     795{
     796    int changrpid             = gContext->GetNumSetting("ChannelGroupDefault", -1);
     797    int remember_last_changrp = gContext->GetNumSetting("ChannelGroupRememberLast", 0);
     798
     799    if (remember_last_changrp && (changrpid != channel_group_id))
     800       gContext->SaveSetting("ChannelGroupDefault", channel_group_id);
     801}
     802
    782803TVState TV::GetState(void) const
    783804{
    784805    if (InStateChange())
     
    41384159
    41394160void TV::ToggleChannelFavorite(void)
    41404161{
    4141     activerecorder->ToggleChannelFavorite();
     4162//    activerecorder->ToggleChannelFavorite();
    41424163}
    41434164
    41444165void TV::ChangeChannel(int direction)
    41454166{
    41464167    bool muted = false;
    41474168
     4169    if ((browse_changrp || (direction == CHANNEL_DIRECTION_FAVORITE)) &&
     4170        (channel_group_id > -1) && (direction != CHANNEL_DIRECTION_SAME))
     4171    {
     4172      uint    chanid;
     4173     
     4174      // Collect channel info
     4175      pbinfoLock.lock();
     4176      uint    old_chanid  = playbackinfo->chanid.toUInt();
     4177      pbinfoLock.unlock();
     4178
     4179      chanid = ChannelUtil::GetNextChannel(m_channellist, old_chanid, direction);
     4180
     4181      ChangeChannel(chanid, "");     
     4182      return;
     4183    } else if (direction == CHANNEL_DIRECTION_FAVORITE)
     4184       direction = CHANNEL_DIRECTION_UP;
     4185
    41484186    if (nvp)
    41494187    {
    41504188        AudioOutput *aud = nvp->getAudioOutput();
     
    51495187
    51505188    bool changeChannel = false;
    51515189    ProgramInfo *nextProgram = NULL;
     5190    int changrpid = channel_group_id;
    51525191
    51535192    if (StateIsLiveTV(GetState()))
    51545193    {
     
    51635202                    allowsecondary = nvp->getVideoOutput()->AllowPreviewEPG();
    51645203
    51655204                // Start up EPG
    5166                 changeChannel = RunProgramGuide(chanid, channum, true, this, allowsecondary);
     5205                changeChannel = RunProgramGuide(chanid, channum, true, this, allowsecondary,
     5206                                                &changrpid);
    51675207                break;
    51685208            }
    51695209            case kPlaybackBox:
     
    52055245        {
    52065246            default:
    52075247            case kScheduleProgramGuide:
    5208                 RunProgramGuide(chanid, channum, true);
     5248                RunProgramGuide(chanid, channum, true, NULL, true, &changrpid);
    52095249                break;
    52105250            case kScheduleProgramFinder:
    52115251                RunProgramFind(true, false);
     
    52555295            DoPause();
    52565296    }
    52575297
     5298    // if channel group was changed in EPG update local info
     5299    if ((changrpid != channel_group_id) && (editType == kScheduleProgramGuide))
     5300    {
     5301      channel_group_id = changrpid;
     5302     
     5303      if (browse_changrp)
     5304      {
     5305          VERBOSE(VB_IMPORTANT, LOC +
     5306             QString("Reloading channel group list for %1").arg(channel_group_id));
     5307     
     5308          m_channellist = ChannelUtil::GetChannels(0, true, "channum, callsign", channel_group_id);
     5309          ChannelUtil::SortChannels(m_channellist, "channum", true);
     5310      }
     5311    }
     5312
    52585313    // Resize the window back to the MythTV Player size
    52595314    if (!using_gui_size_for_tv)
    52605315    {
     
    58765931{
    58775932    if (!browsemode)
    58785933        BrowseStart();
     5934VERBOSE(VB_IMPORTANT,"In BrowseDispInfo");
     5935    // if browsing channel groups is enabled or direction if BROWSE_FAVORITES
     5936    // Then pick the next channel in the channel group list to browse
     5937    // If channel group is ALL CHANNELS (-1), then bypass picking from
     5938    // the channel group list
     5939    if ((browse_changrp || (direction == BROWSE_FAVORITE)) &&
     5940        (channel_group_id > -1) && (direction != BROWSE_SAME) &&
     5941        (direction != BROWSE_RIGHT) && (direction != BROWSE_LEFT))
     5942    {
     5943      uint chanid;
     5944      int  dir;
     5945     
     5946      if ( (direction == BROWSE_UP) || (direction == BROWSE_FAVORITE) )
     5947        dir = CHANNEL_DIRECTION_UP;
     5948      else if (direction == BROWSE_DOWN)
     5949        dir = CHANNEL_DIRECTION_DOWN;
     5950      else // this should never happen, but just in case
     5951        dir = direction;
     5952       
     5953      chanid = ChannelUtil::GetNextChannel(m_channellist, browsechanid.toUInt(), dir);
     5954      VERBOSE(VB_IMPORTANT, QString("Get channel: %1").arg(chanid));
     5955      browsechanid  = QString("%1").arg(chanid);
     5956      browsechannum = QString::null;
     5957      direction     = BROWSE_SAME;
     5958    }
     5959    else if ((channel_group_id == -1) && (direction == BROWSE_FAVORITE))
     5960      direction = BROWSE_UP;
    58795961
    58805962    InfoMap infoMap;
    58815963    QDateTime curtime  = QDateTime::currentDateTime();
     
    66436725    }
    66446726    else if (action == "GUIDE")
    66456727        EditSchedule(kScheduleProgramGuide);
     6728    else if (action.left(10) == "CHANGROUP_")
     6729        processChanGroupEntry(action);
    66466730    else if (action == "FINDER")
    66476731        EditSchedule(kScheduleProgramFinder);
    66486732    else if (action == "SCHEDULE")
     
    67376821    }
    67386822}
    67396823
     6824void TV::processChanGroupEntry(QString action)
     6825{
     6826    if (action == "CHANGROUP_ALL_CHANNELS")
     6827      channel_group_id = -1;
     6828    else
     6829    {
     6830      action.remove("CHANGROUP_");
     6831      channel_group_id = action.toInt();
     6832         
     6833      if (browse_changrp)
     6834      {
     6835         m_channellist = ChannelUtil::GetChannels(0, true, "channum, callsign", channel_group_id);
     6836         ChannelUtil::SortChannels(m_channellist, "channum", true);
     6837      }
     6838    }
     6839}
     6840
    67406841void TV::ShowOSDTreeMenu(void)
    67416842{
    67426843    BuildOSDTreeMenu();
     
    67726873            freeRecorders = RemoteGetFreeRecorderCount();
    67736874
    67746875        item = new OSDGenericTree(treeMenu, tr("Program Guide"), "GUIDE");
     6876        item = new OSDGenericTree(treeMenu, tr("Channel Groups"), "CHANGROUP");
     6877        subitem = new OSDGenericTree(item, tr("All Channels"),
     6878                                     "CHANGROUP_ALL_CHANNELS",
     6879                                     (channel_group_id == -1) ? 1 : 0,
     6880                                     NULL, "CHANNELGROUP");
     6881       
     6882        ChannelGroupList::iterator it;
     6883       
     6884        for (it = m_changrplist.begin(); it != m_changrplist.end(); ++it)
     6885        {
     6886           QString name = QString("CHANGROUP_%1").arg(it->grpid);
     6887           subitem = new OSDGenericTree(item, it->name, name,
     6888                                       ((int)(it->grpid) == channel_group_id) ? 1 : 0,
     6889                                        NULL, "CHANNELGROUP");
     6890        }   
     6891
    67756892        if (!gContext->GetNumSetting("JumpToProgramOSD", 1))
    67766893        {
    67776894            item = new OSDGenericTree(treeMenu, tr("Jump to Program"));
  • libs/libmythtv/tv_play.h

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/libs/libmythtv/tv_play.h mythtv/libs/libmythtv/tv_play.h
    old new  
    1818#include "util.h"
    1919#include "programinfo.h"
    2020#include "videoouttypes.h"
     21#include "channelutil.h"
     22#include "channelgroup.h"
    2123
    2224#include <qobject.h>
    2325
     
    193195    // Used by EPG
    194196    void ChangeVolume(bool up);
    195197    void ToggleMute(void);
     198   
     199    // Channel Groups
     200    void SaveChannelGroup(void);
    196201
    197202  public slots:
    198203    void HandleOSDClosed(int osdType);
     
    360365
    361366    void BuildOSDTreeMenu(void);
    362367    void ShowOSDTreeMenu(void);
     368   
     369    void processChanGroupEntry(QString action);
    363370
    364371    void UpdateLCD(void);
    365372    void ShowLCDChannelInfo(void);
     
    630637    // Network Control stuff
    631638    QValueList<QString> networkControlCommands;
    632639    QMutex ncLock;
     640   
     641    int channel_group_id;
     642    uint browse_changrp;
     643    ChannelGroupList m_changrplist;
     644    DBChanList m_channellist;
    633645};
    634646
    635647#endif
  • programs/mythfrontend/globalsettings.cpp

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/programs/mythfrontend/globalsettings.cpp mythtv/programs/mythfrontend/globalsettings.cpp
    old new  
    28682868    return gc;
    28692869}
    28702870
    2871 static HostCheckBox *EPGShowFavorites()
    2872 {
    2873     HostCheckBox *gc = new HostCheckBox("EPGShowFavorites");
    2874     gc->setLabel(QObject::tr("Only display 'favorite' channels"));
    2875     gc->setHelpText(QObject::tr("If enabled, the EPG will initially display "
    2876                     "only the channels marked as favorites. Pressing "
    2877                     "\"4\" will toggle between displaying favorites and all "
    2878                     "channels."));
    2879     gc->setValue(false);
    2880     return gc;
    2881 }
    28822871
    28832872static HostSpinBox *EPGChanDisplay()
    28842873{
     
    29062895    return gc;
    29072896}
    29082897
     2898static HostCheckBox *ChannelGroupRememberLast()
     2899{
     2900    HostCheckBox *gc = new HostCheckBox("ChannelGroupRememberLast");
     2901    gc->setLabel(QObject::tr("Remember last channel group"));
     2902    gc->setHelpText(QObject::tr("If enabled, the EPG will initially display "
     2903                    "only the channels from the last channel group selected. Pressing "
     2904                    "\"4\" will toggle channel group."));
     2905    gc->setValue(false);
     2906    return gc;
     2907}
     2908
     2909static HostComboBox *ChannelGroupDefault()
     2910{
     2911    HostComboBox *gc = new HostComboBox("ChannelGroupDefault");
     2912    gc->setLabel(QObject::tr("Default channel group"));
     2913
     2914    ChannelGroupList changrplist;
     2915
     2916    changrplist = ChannelGroup::GetChannelGroups();
     2917
     2918    gc->addSelection(QObject::tr("All Channels"), "-1");
     2919
     2920    ChannelGroupList::iterator it;
     2921
     2922    for (it = changrplist.begin(); it < changrplist.end(); ++it)
     2923       gc->addSelection(it->name, QString("%1").arg(it->grpid));
     2924
     2925    gc->setHelpText(QObject::tr("Default channel group to be shown in the the EPG"
     2926                    "Pressing "
     2927                    "\"4\" will toggle channel group."));
     2928    gc->setValue(false);
     2929    return gc;
     2930}
     2931
     2932static HostCheckBox *BrowseChannelGroup()
     2933{
     2934    HostCheckBox *gc = new HostCheckBox("BrowseChannelGroup");
     2935    gc->setLabel(QObject::tr("Browse/Change channels from Channel Group"));
     2936    gc->setHelpText(QObject::tr("If enabled, LiveTV will browse or change channels "
     2937                    "from the selected channel group. \"All Channels\" "
     2938                    "channel group may be selected to browse all channels."));
     2939    gc->setValue(false);
     2940    return gc;
     2941}
     2942
     2943// Channel Group Settings
     2944class ChannelGroupSettings : public TriggeredConfigurationGroup
     2945{
     2946  public:
     2947    ChannelGroupSettings() : TriggeredConfigurationGroup(false, true, false, false)
     2948    {
     2949         setLabel(QObject::tr("Remember last channel group"));
     2950         setUseLabel(false);
     2951
     2952         Setting* RememberChanGrpEnabled = ChannelGroupRememberLast();
     2953         addChild(RememberChanGrpEnabled);
     2954         setTrigger(RememberChanGrpEnabled);
     2955
     2956         ConfigurationGroup* settings = new VerticalConfigurationGroup(false);
     2957         settings->addChild(ChannelGroupDefault());
     2958         addTarget("0", settings);
     2959
     2960         // show nothing if RememberChanGrpEnabled is on
     2961         addTarget("1", new VerticalConfigurationGroup(true));
     2962     };
     2963};
     2964
    29092965// General RecPriorities settings
    29102966
    29112967static GlobalCheckBox *GRSchedMoveHigher()
     
    46214677    general2->addChild(CategoryOverTimeSettings());
    46224678    addChild(general2);
    46234679
     4680    VerticalConfigurationGroup* changrp = new VerticalConfigurationGroup(false);
     4681    changrp->setLabel(QObject::tr("General (Channel Groups)"));
     4682    ChannelGroupSettings *changroupsettings = new ChannelGroupSettings();
     4683    changrp->addChild(changroupsettings);
     4684    changrp->addChild(BrowseChannelGroup());
     4685    addChild(changrp);
    46244686}
    46254687
    46264688EPGSettings::EPGSettings()
    46274689{
    46284690    VerticalConfigurationGroup* epg = new VerticalConfigurationGroup(false);
    4629     epg->setLabel(QObject::tr("Program Guide") + " 1/2");
     4691    epg->setLabel(QObject::tr("Program Guide") + " 1/3");
    46304692    epg->addChild(EPGFillType());
    46314693    epg->addChild(EPGShowCategoryColors());
    46324694    epg->addChild(EPGShowCategoryText());
    46334695    epg->addChild(EPGScrollType());
    46344696    epg->addChild(EPGShowChannelIcon());
    4635     epg->addChild(EPGShowFavorites());
    46364697    epg->addChild(WatchTVGuide());
    46374698    epg->addChild(EPGChanDisplay());
    46384699    epg->addChild(EPGTimeDisplay());
    46394700    addChild(epg);
    46404701
    46414702    VerticalConfigurationGroup* gen = new VerticalConfigurationGroup(false);
    4642     gen->setLabel(QObject::tr("Program Guide") + " 2/2");
     4703    gen->setLabel(QObject::tr("Program Guide") + " 2/3");
    46434704    gen->addChild(UnknownTitle());
    46444705    gen->addChild(UnknownCategory());
    46454706    gen->addChild(DefaultTVChannel());
    46464707    gen->addChild(SelectChangesChannel());
    46474708    gen->addChild(EPGRecThreshold());
    46484709    gen->addChild(EPGEnableJumpToChannel());
    4649     addChild(gen);
     4710    addChild(gen);   
    46504711}
    46514712
    46524713GeneralRecPrioritiesSettings::GeneralRecPrioritiesSettings()
  • programs/mythfrontend/main.cpp

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/programs/mythfrontend/main.cpp mythtv/programs/mythfrontend/main.cpp
    old new  
    5050#include "statusbox.h"
    5151#include "lcddevice.h"
    5252#include "langsettings.h"
     53#include "channelgroup.h"
    5354
    5455#include "libmythui/myththemedmenu.h"
    5556#include "libmythui/myththemebase.h"
     
    405406    {
    406407        EPGSettings settings;
    407408        settings.exec();
     409    }
     410    else if (sel == "settings channelgroups")
     411    {
     412        ChannelGroupEditor editor;
     413        editor.exec();
    408414    }
    409415    else if (sel == "settings generalrecpriorities")
    410416    {
  • programs/mythfrontend/tv_settings.xml

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/programs/mythfrontend/tv_settings.xml mythtv/programs/mythfrontend/tv_settings.xml
    old new  
    8080      <text>Playback OSD</text>
    8181      <action>SETTINGS OSD</action>
    8282   </button>
     83   
     84   <button>
     85      <type>TV_SETTINGS_CHANNEL_GROUP</type>
     86      <text>Channel Groups</text>
     87      <action>SETTINGS CHANNELGROUPS</action>
     88   </button>
    8389
    8490   <button>
    8591      <type>TV_SETTINGS_PLAYBACK_GROUPS</type>
  • themes/classic/tv_settings.xml

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/themes/classic/tv_settings.xml mythtv/themes/classic/tv_settings.xml
    old new  
    6767   </button>
    6868
    6969   <button>
     70      <type>TV_SETTINGS_CHANNEL_GROUP</type>
     71      <text>Channel Groups</text>
     72      <action>SETTINGS CHANNELGROUPS</action>
     73   </button>
     74
     75   <button>
    7076      <type>TV_SETTINGS_PLAYBACK_GROUPS</type>
    7177      <text>Playback Groups</text>
    7278      <text lang="SV">Uppspelningsgrupper</text>
  • themes/DVR/tv_settings.xml

    diff -Naur --exclude='*.orig' --exclude='*.qm' mythtv-orig/themes/DVR/tv_settings.xml mythtv/themes/DVR/tv_settings.xml
    old new  
    7474   </button>
    7575
    7676   <button>
     77      <type>TV_SETTINGS_CHANNEL_GROUP</type>
     78      <text>Channel Groups</text>
     79      <action>SETTINGS CHANNELGROUPS</action>
     80   </button>
     81
     82   <button>
    7783      <type>TV_SETTINGS_PLAYBACK_GROUPS</type>
    7884      <text>Playback Groups</text>
    7985      <text lang="SV">Uppspelningsgrupper</text>