diff options
| author | Tim E. Real <termtech@rogers.com> | 2011-01-09 21:32:13 +0000 | 
|---|---|---|
| committer | Tim E. Real <termtech@rogers.com> | 2011-01-09 21:32:13 +0000 | 
| commit | 5fa5f8210b4924a1f2ae0100dfb6c0b50c85db81 (patch) | |
| tree | 23f4c7ebe7fe8f506aa5d09bce4262b0040453f2 /muse2/muse | |
| parent | 0e39cb75d7a659322b282a79ca63f10d48fa277a (diff) | |
Completed soloing system. Other fixes - see ChangeLog.
Diffstat (limited to 'muse2/muse')
| -rw-r--r-- | muse2/muse/app.cpp | 332 | ||||
| -rw-r--r-- | muse2/muse/arranger/tlist.cpp | 8 | ||||
| -rw-r--r-- | muse2/muse/audiotrack.cpp | 3 | ||||
| -rw-r--r-- | muse2/muse/ctrl/ctrledit.cpp | 22 | ||||
| -rw-r--r-- | muse2/muse/ctrl/ctrledit.h | 3 | ||||
| -rw-r--r-- | muse2/muse/midiport.cpp | 8 | ||||
| -rw-r--r-- | muse2/muse/mixer/amixer.cpp | 3 | ||||
| -rw-r--r-- | muse2/muse/mixer/astrip.cpp | 374 | ||||
| -rw-r--r-- | muse2/muse/mixer/mstrip.cpp | 5 | ||||
| -rw-r--r-- | muse2/muse/node.cpp | 26 | ||||
| -rw-r--r-- | muse2/muse/route.cpp | 67 | ||||
| -rw-r--r-- | muse2/muse/track.cpp | 78 | ||||
| -rw-r--r-- | muse2/muse/widgets/mtrackinfo.cpp | 15 | ||||
| -rw-r--r-- | muse2/muse/widgets/mtrackinfobase.ui | 18 | 
14 files changed, 633 insertions, 329 deletions
| diff --git a/muse2/muse/app.cpp b/muse2/muse/app.cpp index 1f2edc1a..2c4758a6 100644 --- a/muse2/muse/app.cpp +++ b/muse2/muse/app.cpp @@ -49,6 +49,7 @@  #include "transpose.h"  #include "waveedit.h"  #include "widgets/projectcreateimpl.h" +#include "widgets/menutitleitem.h"  #ifdef DSSI_SUPPORT  #include "dssihost.h" @@ -2188,7 +2189,7 @@ PopupMenu* MusE::getRoutingPopupMenu()  void MusE::updateRouteMenus(Track* track, QObject* master)      { -      // NOTE: The puropse of this routine is to make sure the items actually reflect +      // NOTE: The purpose of this routine is to make sure the items actually reflect        //  the routing status. And with MusE-1 QT3, it was also required to actually        //  check the items since QT3 didn't do it for us.        // But now with MusE-2 and QT4, QT4 checks an item when it is clicked. @@ -2218,9 +2219,84 @@ void MusE::updateRouteMenus(Track* track, QObject* master)        {          // p3.3.50 Ignore the 'toggle' items.          if(imm->second.type == Route::MIDI_PORT_ROUTE &&  -           imm->first >= (MIDI_PORTS * MIDI_CHANNELS) && imm->first < (MIDI_PORTS * MIDI_CHANNELS + MIDI_PORTS))    +           //imm->first >= (MIDI_PORTS * MIDI_CHANNELS) && imm->first < (MIDI_PORTS * MIDI_CHANNELS + MIDI_PORTS))    +           imm->second.channel == (1 << MIDI_CHANNELS) - 1)  // p4.0.14 See if all channels are set, rather than using ID.            continue; +         +        // p4.0.14 TODO FIXME Couldn't quite figure out the logic yet. It should be possible (I hope).  +        // But not really required for now, as per above note. +        if(gIsOutRoutingPopupMenu && track->isMidiTrack() && +          imm->second.type == Route::TRACK_ROUTE && imm->second.track->type() == Track::AUDIO_INPUT) +          return; +        #if 0 +        printf("imm route:\n");  // REMOVE Tim. +        imm->second.dump(); +        if(track->isMidiTrack()) +        { +          if(imm->second.type == Route::TRACK_ROUTE && imm->second.track->type() == Track::AUDIO_INPUT) +          { +            Route &aRoute = imm->second; +            int chbit = aRoute.channel; +            ///Route bRoute(track, chbit); +            ///int mdidx = bRoute.midiPort; +            int port = ((MidiTrack*)track)->outPort(); +            if(port < 0 || port >= MIDI_PORTS) +              continue; +            int tchbit = 1 << ((MidiTrack*)track)->outChannel(); +             +            MidiPort* mp = &midiPorts[port]; +             +            ///Route bRoute(port, chbit); +             +            //int chmask = 0;                    +            bool found = false; +            RouteList* mprl = gIsOutRoutingPopupMenu ? mp->outRoutes() : mp->inRoutes(); +            iRoute ir = mprl->begin(); +            for(; ir != mprl->end(); ++ir)  +            { +              printf("mp route:\n");  // REMOVE Tim. +              ir->dump(); // REMOVE Tim. +              ///if(aRoute.type == Route::TRACK_ROUTE)                                     // Is the map route a track route? +              { +                if(ir->type == Route::TRACK_ROUTE && ir->track == aRoute.track)  // Is the track route a midi port route? +                  //&& (ir->channel & chbit) == chbit)                +                  //&& (ir->channel & tchbit))               // Is the exact channel mask bit(s) set? +                { +                  printf("track matches\n");  // REMOVE Tim. +                  if(ir->channel & tchbit) +                  { +                    found = true; +                    printf("found: bit matches\n");  // REMOVE Tim. +                  }   +                  break; +                } +              } +              ///else +              ///if(*ir == aRoute) +              ///{ +                //found = true; +              ///  break; +              ///} +            } +            //pup->setItemChecked(imm->first, found); +            //printf("MusE::updateRouteMenus setItemChecked\n"); +            // TODO: MusE-2: Convert this, fastest way is to change the routing map, otherwise this requires a lookup. +            //if(pup->isItemChecked(imm->first) != (irl != rl->end())) +            //  pup->setItemChecked(imm->first, irl != rl->end()); +            QAction* act = pup->findActionFromData(imm->first);   +            //printf("set act checked to:%d\n", ir != mprl->end());  // REMOVE Tim. +            //if(act && act->isChecked() != (ir != mprl->end())) +            //  act->setChecked(ir != mprl->end()); +            printf("set act checked to:%d\n", found);  // REMOVE Tim. +            if(act && act->isChecked() != found) +              act->setChecked(found); +             +            //return; +          } +        } +        #endif +                  //bool found = false;          iRoute irl = rl->begin();          for(; irl != rl->end(); ++irl)  @@ -2278,6 +2354,69 @@ void MusE::routingPopupMenuActivated(Track* track, int n)          iRouteMenuMap imm = gRoutingMenuMap.find(n);          if(imm == gRoutingMenuMap.end())            return; +         +        // Support Midi Port to Audio Input track routes. p4.0.14 Tim. +        if(imm->second.type == Route::TRACK_ROUTE) +        { +          //if(gIsOutRoutingPopupMenu)    // Try to avoid splitting like this.  +          { +            Route &aRoute = imm->second; +            int chbit = aRoute.channel; +            int port = ((MidiTrack*)track)->outPort(); +            if(port < 0 || port >= MIDI_PORTS) +              return; +             +            MidiPort* mp = &midiPorts[port]; +            ///MidiDevice* md = mp->device(); +             +            // This is desirable, but could lead to 'hidden' routes unless we add more support +            //  such as removing the existing routes when user changes flags. +            // So for now, just list all valid ports whether read or write. +            ///if(!md) +            ///  return; +            ///if(!(md->rwFlags() & (gIsOutRoutingPopupMenu ? 1 : 2))) +            ///  return; +             +            //int channel = ((MidiTrack*)track->outChannel(); +            Route bRoute(port, chbit); +             +            int chmask = 0;                    +            RouteList* mprl = gIsOutRoutingPopupMenu ? mp->outRoutes() : mp->inRoutes(); +            iRoute ir = mprl->begin(); +            for (; ir != mprl->end(); ++ir)  +            { +              if(ir->type == Route::TRACK_ROUTE && ir->track == aRoute.track)    // Is there already a route to this port? +              { +                    chmask = ir->channel;  // Grab the channel mask. +                    break; +              }       +            } +            //if (iir != rl->end())  +            if ((chmask & chbit) == chbit)             // Is the channel's bit(s) set? +            { +              // disconnect +              if(gIsOutRoutingPopupMenu) +                audio->msgRemoveRoute(bRoute, aRoute); +              else +                audio->msgRemoveRoute(aRoute, bRoute); +            } +            else  +            { +              // connect +              if(gIsOutRoutingPopupMenu) +                audio->msgAddRoute(bRoute, aRoute); +              else +                audio->msgAddRoute(aRoute, bRoute); +            } +             +            audio->msgUpdateSoloStates(); +            song->update(SC_ROUTE); +             +          } +          return; +        } +         +                  if(imm->second.type != Route::MIDI_PORT_ROUTE)            return;          Route &aRoute = imm->second; @@ -2580,45 +2719,71 @@ PopupMenu* MusE::prepareRoutingPopupMenu(Track* track, bool dst)    if(!track)      return 0; -  //QPoint ppt = QCursor::pos(); -      if(track->isMidiTrack())    { +    RouteList* rl = dst ? track->outRoutes() : track->inRoutes(); +    //Route dst(track, -1); -    //QPoint ppt = parent->rect().bottomLeft(); -       -    //if(dst) -    //{ -      // TODO  +    PopupMenu* pup = getRoutingPopupMenu(); +    pup->disconnect(); +    //connect(pup, SIGNAL(activated(int)), SLOT(routingPopupMenuActivated(int))); +    //connect(pup, SIGNAL(aboutToHide()), SLOT(routingPopupMenuAboutToHide())); -    //} -    //else -    //{ -      RouteList* rl = dst ? track->outRoutes() : track->inRoutes(); -      //Route dst(track, -1); +    pup->clear(); +    gRoutingMenuMap.clear(); -      PopupMenu* pup = getRoutingPopupMenu(); -      pup->disconnect(); -      //connect(pup, SIGNAL(activated(int)), SLOT(routingPopupMenuActivated(int))); -      //connect(pup, SIGNAL(aboutToHide()), SLOT(routingPopupMenuAboutToHide())); +    int gid = 0; +    QAction* act = 0; +     +    if(dst)    +    { +      // Support Midi Port to Audio Input track routes. p4.0.14 Tim. +      int port = ((MidiTrack*)track)->outPort(); +      if(port >= 0 && port < MIDI_PORTS) +      { +        MidiPort* mp = &midiPorts[port]; +        RouteList* mprl = mp->outRoutes(); +        int chbits = 1 << ((MidiTrack*)track)->outChannel(); +        //MidiDevice* md = mp->device(); +        //if(!md) +        //  continue; -      int gid = 0; -      //int n;     -      QAction* act = 0; -       -    // Routes can't be re-read until the message sent from msgAddRoute1()  -    //  has had time to be sent and actually affected the routes. -    ///_redisplay: -       -      pup->clear(); -      gRoutingMenuMap.clear(); -      gid = 0; -       -      //MidiInPortList* tl = song->midiInPorts(); -      //for(iMidiInPort i = tl->begin();i != tl->end(); ++i)  +        pup->addSeparator(); +        pup->addAction(new MenuTitleItem(tr("Soloing chain"), pup));  +        PopupMenu* subp = new PopupMenu(pup); +        subp->setTitle(tr("Audio returns"));  +        pup->addMenu(subp); +         +        InputList* al = song->inputs(); +        for (iAudioInput i = al->begin(); i != al->end(); ++i)  +        { +          Track* t = *i; +          QString s(t->name()); +           +          act = subp->addAction(s); +          act->setData(gid); +          act->setCheckable(true); +           +          Route r(t, chbits); +           +          gRoutingMenuMap.insert( pRouteMenuMap(gid, r) ); +           +          for(iRoute ir = mprl->begin(); ir != mprl->end(); ++ir)  +          { +            if(ir->type == Route::TRACK_ROUTE && ir->track == t && (ir->channel & chbits)) +            { +              act->setChecked(true); +              break; +            }   +          } +          ++gid;       +        } +      }      +    } +    else +    {        for(int i = 0; i < MIDI_PORTS; ++i)        { -        //MidiInPort* track = *i;          // NOTE: Could possibly list all devices, bypassing ports, but no, let's stick with ports.          MidiPort* mp = &midiPorts[i];          MidiDevice* md = mp->device(); @@ -2630,10 +2795,6 @@ PopupMenu* MusE::prepareRoutingPopupMenu(Track* track, bool dst)          //printf("MusE::prepareRoutingPopupMenu adding submenu portnum:%d\n", i); -        //QMenu* m = menu->addMenu(track->name()); -        //QPopupMenu* subp = new QPopupMenu(parent); -        //PopupMenu* subp = new PopupMenu(this); -        //PopupMenu* subp = new PopupMenu();          PopupMenu* subp = new PopupMenu(pup);          subp->setTitle(md->name());  @@ -2656,101 +2817,46 @@ PopupMenu* MusE::prepareRoutingPopupMenu(Track* track, bool dst)          for(int ch = 0; ch < MIDI_CHANNELS; ++ch)           { -          //QAction* a = m->addAction(QString("Channel %1").arg(ch+1)); -          //subp->insertItem(QT_TRANSLATE_NOOP("@default", QString("Channel %1").arg(ch+1)), i * MIDI_CHANNELS + ch); -          gid = i * MIDI_CHANNELS + ch; -           -          //printf("MusE::prepareRoutingPopupMenu inserting gid:%d\n", gid); -                      act = subp->addAction(QString("Channel %1").arg(ch+1));            act->setCheckable(true);            act->setData(gid); -          //a->setCheckable(true); -          //Route src(track, ch, RouteNode::TRACK); -          //Route src(md, ch); -          //Route r = Route(src, dst); -          //a->setData(QVariant::fromValue(r)); -          //a->setChecked(rl->indexOf(r) != -1); -          //Route srcRoute(md, ch); -          //Route srcRoute(i, ch);     // p3.3.49 New: Midi port route.            int chbit = 1 << ch;            Route srcRoute(i, chbit);    // p3.3.50 In accordance with new channel mask, use the bit position.            gRoutingMenuMap.insert( pRouteMenuMap(gid, srcRoute) ); -          //for(iRoute ir = rl->begin(); ir != rl->end(); ++ir)   // p3.3.50 Removed. -          //{ -            //if(*ir == dst)  -          //  if(*ir == srcRoute)  -          //  { -          //    subp->setItemChecked(id, true); -          //    break; -          //  } -          //}            if(chanmask & chbit)                  // p3.3.50 Is the channel already set? Show item check mark.              act->setChecked(true); +           +          ++gid;            } -        //subp->insertItem(QString("Toggle all"), 1000+i); -        // p3.3.50 One route with all channel bits set. -        gid = MIDI_PORTS * MIDI_CHANNELS + i;           // Make sure each 'toggle' item gets a unique id. +        //gid = MIDI_PORTS * MIDI_CHANNELS + i;           // Make sure each 'toggle' item gets a unique id.          act = subp->addAction(QString("Toggle all"));          //act->setCheckable(true);          act->setData(gid);          Route togRoute(i, (1 << MIDI_CHANNELS) - 1);    // Set all channel bits.          gRoutingMenuMap.insert( pRouteMenuMap(gid, togRoute) ); -         +        ++gid;          pup->addMenu(subp);        } -           -      /* -      QPopupMenu* pup = new QPopupMenu(iR); -      pup->setCheckable(true); -      //MidiTrack* t = (MidiTrack*)track; -      RouteList* irl = track->inRoutes(); -   -      MidiTrack* t = (MidiTrack*)track; -      int gid = 0; -      for (int i = 0; i < channel; ++i)  -      { -            char buffer[128]; -            snprintf(buffer, 128, "%s %d", tr("Channel").toLatin1().constData(), i+1); -            MenuTitleItem* titel = new MenuTitleItem(QString(buffer)); -            pup->insertItem(titel); -   -            if (!checkAudioDevice()) return; -            std::list<QString> ol = audioDevice->outputPorts(); -            for (std::list<QString>::iterator ip = ol.begin(); ip != ol.end(); ++ip) { -                  int id = pup->insertItem(*ip, (gid * 16) + i); -                  Route dst(*ip, true, i); -                  ++gid; -                  for (iRoute ir = irl->begin(); ir != irl->end(); ++ir) { -                        if (*ir == dst) { -                              pup->setItemChecked(id, true); -                              break; -                              } -                        } -                  } -            if (i+1 != channel) -                  pup->addSeparator(); -      } -      */ -       -      if(pup->actions().isEmpty()) -      { -        gRoutingPopupMenuMaster = 0; -        //pup->clear(); -        //pup->disconnect(); -        gRoutingMenuMap.clear(); -        //oR->setDown(false);      -        return 0; -      } -       -      gIsOutRoutingPopupMenu = dst; -      return pup; +    } +         +    if(pup->actions().isEmpty()) +    { +      gRoutingPopupMenuMaster = 0; +      //pup->clear(); +      //pup->disconnect(); +      gRoutingMenuMap.clear(); +      //oR->setDown(false);      +      return 0;      } -    return 0; +    gIsOutRoutingPopupMenu = dst; +    return pup; +  } +   +  return 0;  }  #if 0 @@ -3145,9 +3251,9 @@ void MusE::startPianoroll(PartList* pl, bool showDefaultCtrls)        {        PianoRoll* pianoroll = new PianoRoll(pl, this, 0, arranger->cursorValue()); -      pianoroll->show();        if(showDefaultCtrls)       // p4.0.12          pianoroll->addCtrl(); +      pianoroll->show();        toplevels.push_back(Toplevel(Toplevel::PIANO_ROLL, (unsigned long)(pianoroll), pianoroll));        connect(pianoroll, SIGNAL(deleted(unsigned long)), SLOT(toplevelDeleted(unsigned long)));        connect(muse, SIGNAL(configChanged()), pianoroll, SLOT(configChanged())); @@ -3215,9 +3321,9 @@ void MusE::startDrumEditor(PartList* pl, bool showDefaultCtrls)        {        DrumEdit* drumEditor = new DrumEdit(pl, this, 0, arranger->cursorValue()); -      drumEditor->show();        if(showDefaultCtrls)       // p4.0.12          drumEditor->addCtrl(); +      drumEditor->show();        toplevels.push_back(Toplevel(Toplevel::DRUM, (unsigned long)(drumEditor), drumEditor));        connect(drumEditor, SIGNAL(deleted(unsigned long)), SLOT(toplevelDeleted(unsigned long)));        connect(muse, SIGNAL(configChanged()), drumEditor, SLOT(configChanged())); diff --git a/muse2/muse/arranger/tlist.cpp b/muse2/muse/arranger/tlist.cpp index 02f742f7..e32d0010 100644 --- a/muse2/muse/arranger/tlist.cpp +++ b/muse2/muse/arranger/tlist.cpp @@ -1027,6 +1027,9 @@ void TList::mousePressEvent(QMouseEvent* ev)                    //if(button == QMouseEvent::LeftButton)                    //  portsPopupMenu(t, x, t->y() - ypos); +                  audio->msgUpdateSoloStates(); // p4.0.14 +                  //song->update(SC_ROUTE);       // +                                      break;              case COL_MUTE:                    // p3.3.29 @@ -1141,7 +1144,10 @@ void TList::mousePressEvent(QMouseEvent* ev)                              // may result in adding/removing mixer strip:                              //song->update(-1);                              //song->update(SC_CHANNELS); -                            song->update(SC_MIDI_TRACK_PROP); +                            //song->update(SC_MIDI_TRACK_PROP); +                            audio->msgUpdateSoloStates();                   // p4.0.14 +                            //song->update(SC_MIDI_TRACK_PROP | SC_ROUTE);  // +                            song->update(SC_MIDI_TRACK_PROP);               //                        }                      }                      else diff --git a/muse2/muse/audiotrack.cpp b/muse2/muse/audiotrack.cpp index 7330e79e..19bbbaf1 100644 --- a/muse2/muse/audiotrack.cpp +++ b/muse2/muse/audiotrack.cpp @@ -860,7 +860,8 @@ void AudioTrack::writeProperties(int level, Xml& xml) const        if (hasAuxSend()) {              int naux = song->auxs()->size();              for (int idx = 0; idx < naux; ++idx) { -                  QString s("<auxSend idx=%1>%2</auxSend>\n"); +                  //QString s("<auxSend idx=%1>%2</auxSend>\n"); +                  QString s("<auxSend idx=\"%1\">%2</auxSend>\n");  // Aux fix from Remon, thanks.                    xml.nput(level, s.arg(idx).arg(_auxSend[idx]).toAscii().constData());                    }              } diff --git a/muse2/muse/ctrl/ctrledit.cpp b/muse2/muse/ctrl/ctrledit.cpp index fe04844d..8842ba97 100644 --- a/muse2/muse/ctrl/ctrledit.cpp +++ b/muse2/muse/ctrl/ctrledit.cpp @@ -132,3 +132,25 @@ void CtrlEdit::setCanvasWidth(int w)  {     canvas->setFixedWidth(w);   } + +void CtrlEdit::setController(int n) +{ +  canvas->setController(n); +} + +void CtrlEdit::setController(const QString& name) +{ +  int portno = canvas->track()->outPort(); +  MidiPort* port = &midiPorts[portno]; +  MidiInstrument* instr = port->instrument(); +  MidiControllerList* mcl = instr->controller(); + +  for (iMidiController ci = mcl->begin(); ci != mcl->end(); ++ci)  +  { +    if (ci->second->name() == name)  +    { +      canvas->setController(ci->second->num()); +      break; +    } +  } +} diff --git a/muse2/muse/ctrl/ctrledit.h b/muse2/muse/ctrl/ctrledit.h index 61bf9b46..eec235b1 100644 --- a/muse2/muse/ctrl/ctrledit.h +++ b/muse2/muse/ctrl/ctrledit.h @@ -37,6 +37,8 @@ class CtrlEdit : public QWidget {        void setXPos(int val)           { canvas->setXPos(val); }        void setXMag(int val)           { canvas->setXMag(val); }        void setCanvasWidth(int w); +      void setController(int /*n*/); +           signals:        void timeChanged(unsigned);        void destroyedCtrl(CtrlEdit*); @@ -48,6 +50,7 @@ class CtrlEdit : public QWidget {           bool expand = false, const char* name = 0);        void readStatus(Xml&);        void writeStatus(int, Xml&); +      void setController(const QString& name);        };  #endif diff --git a/muse2/muse/midiport.cpp b/muse2/muse/midiport.cpp index 02fed8d1..16cfd429 100644 --- a/muse2/muse/midiport.cpp +++ b/muse2/muse/midiport.cpp @@ -62,7 +62,7 @@ MidiPort::MidiPort()        // to make midi mixer operational        //        for (int i = 0; i < MIDI_CHANNELS; ++i) { -            addManagedController(i, CTRL_PROGRAM); +            addManagedController(i, CTRL_PROGRAM);                 addManagedController(i, CTRL_VOLUME);              addManagedController(i, CTRL_PANPOT);              _automationType[i] = AUTO_READ; @@ -1013,8 +1013,10 @@ void MidiPort::writeRouting(int level, Xml& xml) const        {          if(r->type == Route::TRACK_ROUTE && !r->name().isEmpty())          { -          //xml.tag(level++, "Route"); -           +          // Ignore Midi Port to Audio Input routes. Handled by Track route writer. p4.0.14 Tim. +          if(r->track && r->track->type() == Track::AUDIO_INPUT) +            continue; +                        s = QT_TRANSLATE_NOOP("@default", "Route");            if(r->channel != -1 && r->channel != 0)                s += QString(QT_TRANSLATE_NOOP("@default", " channelMask=\"%1\"")).arg(r->channel);  // Use new channel mask. diff --git a/muse2/muse/mixer/amixer.cpp b/muse2/muse/mixer/amixer.cpp index 7fb406f3..e4a82ce8 100644 --- a/muse2/muse/mixer/amixer.cpp +++ b/muse2/muse/mixer/amixer.cpp @@ -538,7 +538,8 @@ void AudioMixerApp::songChanged(int flags)              action = STRIP_INSERTED;        else if (flags & SC_MIDI_TRACK_PROP)              action = UPDATE_MIDI; -      if (action != NO_UPDATE) +      //if (action != NO_UPDATE) +      if (action != NO_UPDATE && action != UPDATE_MIDI)  // p4.0.14 Fix for very slow track prop adjusting.               updateMixer(action);        if (action != UPDATE_ALL) {              StripList::iterator si = stripList.begin(); diff --git a/muse2/muse/mixer/astrip.cpp b/muse2/muse/mixer/astrip.cpp index 1317f63d..a680d302 100644 --- a/muse2/muse/mixer/astrip.cpp +++ b/muse2/muse/mixer/astrip.cpp @@ -68,6 +68,11 @@ QWidget* MenuTitleItem::createWidget(QWidget *parent)  {    QLabel* l = new QLabel(s, parent);    l->setAlignment(Qt::AlignCenter); +  l->setAutoFillBackground(true); +  //QPalette palette; +  //palette.setColor(label->backgroundRole(), c); +  //l->setPalette(palette); +  l->setBackgroundRole(QPalette::Dark);    return l;  } @@ -1542,6 +1547,181 @@ static int nonSyntiTrackAddSyntis(AudioTrack* t, PopupMenu* lb, int id, RouteMen  }  //--------------------------------------------------------- +//   addMidiPorts +//--------------------------------------------------------- + +static int addMidiPorts(AudioTrack* t, PopupMenu* pup, int id, RouteMenuMap& mm, bool isOutput) +{ +  QAction* act; +  for(int i = 0; i < MIDI_PORTS; ++i) +  { +    MidiPort* mp = &midiPorts[i]; +    MidiDevice* md = mp->device(); +     +    // This is desirable, but could lead to 'hidden' routes unless we add more support +    //  such as removing the existing routes when user changes flags. +    // So for now, just list all valid ports whether read or write. +    if(!md) +      continue; +    //if(!(md->rwFlags() & (isOutput ? 1 : 2))) +    //  continue; +           +    RouteList* rl = isOutput ? t->outRoutes() : t->inRoutes(); +     +    PopupMenu* subp = new PopupMenu(pup); +    subp->setTitle(md->name());  +     +    int chanmask = 0; +    // To reduce number of routes required, from one per channel to just one containing a channel mask.  +    // Look for the first route to this midi port. There should always be only a single route for each midi port, now. +    for(iRoute ir = rl->begin(); ir != rl->end(); ++ir)    +    { +      if(ir->type == Route::MIDI_PORT_ROUTE && ir->midiPort == i)  +      { +        // We have a route to the midi port. Grab the channel mask. +        chanmask = ir->channel; +        break; +      } +    } +     +    for(int ch = 0; ch < MIDI_CHANNELS; ++ch)  +    { +      act = subp->addAction(QString("Channel %1").arg(ch+1)); +      act->setCheckable(true); +      act->setData(id); +       +      int chbit = 1 << ch; +      Route srcRoute(i, chbit);    // In accordance with new channel mask, use the bit position. +       +      mm.insert( pRouteMenuMap(id, srcRoute) ); +       +      if(chanmask & chbit)                  // Is the channel already set? Show item check mark. +        act->setChecked(true); +       +      ++id; +    } +     +    //gid = MIDI_PORTS * MIDI_CHANNELS + i;           // Make sure each 'toggle' item gets a unique id. +    act = subp->addAction(QString("Toggle all")); +    //act->setCheckable(true); +    act->setData(id); +    Route togRoute(i, (1 << MIDI_CHANNELS) - 1);    // Set all channel bits. +    mm.insert( pRouteMenuMap(id, togRoute) ); +    ++id; +     +    pup->addMenu(subp); +  }     +  return id;       +} + +//--------------------------------------------------------- +//   routingPopupMenuActivated +//--------------------------------------------------------- + +void AudioStrip::routingPopupMenuActivated(QAction* act) +{ +      if(!track || gRoutingPopupMenuMaster != this || track->isMidiTrack()) +        return; +       +      PopupMenu* pup = muse->getRoutingPopupMenu(); +       +      if(pup->actions().isEmpty()) +        return; +         +      AudioTrack* t = (AudioTrack*)track; +      RouteList* rl = gIsOutRoutingPopupMenu ? t->outRoutes() : t->inRoutes(); +       +      int n = act->data().toInt(); +      if (n == -1)  +        return; +       +      iRouteMenuMap imm = gRoutingMenuMap.find(n); +      if(imm == gRoutingMenuMap.end()) +        return; +         +      if(gIsOutRoutingPopupMenu) +      {   +        Route srcRoute(t, imm->second.channel, imm->second.channels); +        srcRoute.remoteChannel = imm->second.remoteChannel; +         +        Route &dstRoute = imm->second; + +        // check if route src->dst exists: +        iRoute irl = rl->begin(); +        for (; irl != rl->end(); ++irl) { +              if (*irl == dstRoute) +                    break; +              } +        if (irl != rl->end()) { +              // disconnect if route exists +              audio->msgRemoveRoute(srcRoute, dstRoute); +              } +        else { +              // connect if route does not exist +              audio->msgAddRoute(srcRoute, dstRoute); +              } +        audio->msgUpdateSoloStates(); +        song->update(SC_ROUTE); +      }   +      else +      { +        Route &srcRoute = imm->second; +         +        // Support Midi Port to Audio Input routes. p4.0.14 Tim. +        if(track->type() == Track::AUDIO_INPUT && srcRoute.type == Route::MIDI_PORT_ROUTE) +        { +          int chbit = srcRoute.channel; +          Route dstRoute(t, chbit); +          int mdidx = srcRoute.midiPort; +          int chmask = 0;                    +          iRoute iir = rl->begin(); +          for (; iir != rl->end(); ++iir)  +          { +            if(iir->type == Route::MIDI_PORT_ROUTE && iir->midiPort == mdidx)    // Is there already a route to this port? +            { +              chmask = iir->channel;  // Grab the channel mask. +              break; +            }       +          } +           +          if ((chmask & chbit) == chbit)             // Is the channel's bit(s) set? +          { +            //printf("astrip: removing src route ch:%d dst route ch:%d\n", srcRoute.channel, dstRoute.channel);  +            audio->msgRemoveRoute(srcRoute, dstRoute); +          } +          else  +          { +            //printf("astrip: adding src route ch:%d dst route ch:%d\n", srcRoute.channel, dstRoute.channel);  +            audio->msgAddRoute(srcRoute, dstRoute); +          } +           +          audio->msgUpdateSoloStates(); +          song->update(SC_ROUTE); +          return; +        } +         +        Route dstRoute(t, imm->second.channel, imm->second.channels); +        dstRoute.remoteChannel = imm->second.remoteChannel; + +        iRoute irl = rl->begin(); +        for (; irl != rl->end(); ++irl) { +              if (*irl == srcRoute) +                    break; +              } +        if (irl != rl->end()) { +              // disconnect +              audio->msgRemoveRoute(srcRoute, dstRoute); +              } +        else { +              // connect +              audio->msgAddRoute(srcRoute, dstRoute); +              } +        audio->msgUpdateSoloStates(); +        song->update(SC_ROUTE); +      } +} + +//---------------------------------------------------------  //   iRoutePressed  //--------------------------------------------------------- @@ -1564,7 +1744,7 @@ void AudioStrip::iRoutePressed()        QAction* act = 0;        int gid = 0; -      int id = 0; +      //int id = 0;        pup->clear();        gRoutingMenuMap.clear(); @@ -1592,13 +1772,15 @@ void AudioStrip::iRoutePressed()              std::list<QString> ol = audioDevice->outputPorts();              for(std::list<QString>::iterator ip = ol.begin(); ip != ol.end(); ++ip)               { -              id = gid * 16 + i; +              //id = gid * 16 + i;        // IDs removed p4.0.14 Tim.                act = pup->addAction(*ip); -              act->setData(id); +              //act->setData(id); +              act->setData(gid);                act->setCheckable(true);                Route dst(*ip, true, i, Route::JACK_ROUTE); -              gRoutingMenuMap.insert( pRouteMenuMap(id, dst) ); +              //gRoutingMenuMap.insert( pRouteMenuMap(id, dst) ); +              gRoutingMenuMap.insert( pRouteMenuMap(gid, dst) );                ++gid;                for(iRoute ir = irl->begin(); ir != irl->end(); ++ir)                 { @@ -1612,6 +1794,29 @@ void AudioStrip::iRoutePressed()              if(i+1 != channel)                pup->addSeparator();            } +           +          // p4.0.14 +          // +          // Display using separate menus for midi ports and audio outputs: +          // +          pup->addSeparator(); +          pup->addAction(new MenuTitleItem(tr("Soloing chain"), pup));  +          PopupMenu* subp = new PopupMenu(pup); +          subp->setTitle(tr("Audio sends"));  +          pup->addMenu(subp); +          gid = addOutPorts(t, subp, gid, gRoutingMenuMap, -1, -1, false);   +          subp = new PopupMenu(pup); +          subp->setTitle(tr("Midi sends"));  +          pup->addMenu(subp); +          addMidiPorts(t, subp, gid, gRoutingMenuMap, false); +          // +          // Display all in the same menu: +          // +          //pup->addAction(new MenuTitleItem(tr("Audio sends"), pup));  +          //gid = addOutPorts(t, pup, gid, gRoutingMenuMap, -1, -1, false);   +          //pup->addSeparator(); +          //pup->addAction(new MenuTitleItem(tr("Midi sends"), pup));  +          //addMidiPorts(t, pup, gid, gRoutingMenuMap, false);          }          break;          //case Track::AUDIO_OUTPUT: @@ -1661,140 +1866,7 @@ void AudioStrip::iRoutePressed()        pup->popup(ppt);        iR->setDown(false);             } - -//--------------------------------------------------------- -//   routingPopupMenuActivated -//--------------------------------------------------------- - -void AudioStrip::routingPopupMenuActivated(QAction* act) -{ -      if(!track || gRoutingPopupMenuMaster != this || track->isMidiTrack()) -        return; -       -      PopupMenu* pup = muse->getRoutingPopupMenu(); -       -      if(pup->actions().isEmpty()) -        return; -         -      AudioTrack* t = (AudioTrack*)track; -      RouteList* rl = gIsOutRoutingPopupMenu ? t->outRoutes() : t->inRoutes(); -       -      int n = act->data().toInt(); -      if (n == -1)  -        return; -      if(gIsOutRoutingPopupMenu) -      {   -        if(track->type() == Track::AUDIO_OUTPUT) -        { -           -          int chan = n & 0xf; -           -          Route srcRoute(t, chan); -          Route dstRoute(act->text(), true, -1, Route::JACK_ROUTE); -          dstRoute.channel = chan; - -          // check if route src->dst exists: -          iRoute irl = rl->begin(); -          for (; irl != rl->end(); ++irl) { -                if (*irl == dstRoute) -                      break; -                } -          if (irl != rl->end()) { -                // disconnect if route exists -                audio->msgRemoveRoute(srcRoute, dstRoute); -                } -          else { -                // connect if route does not exist -                audio->msgAddRoute(srcRoute, dstRoute); -                } -          audio->msgUpdateSoloStates(); -          song->update(SC_ROUTE); -          return; -        } -         -        iRouteMenuMap imm = gRoutingMenuMap.find(n); -        if(imm == gRoutingMenuMap.end()) -          return; -         -        Route srcRoute(t, imm->second.channel, imm->second.channels); -        srcRoute.remoteChannel = imm->second.remoteChannel; -         -        Route &dstRoute = imm->second; - -        // check if route src->dst exists: -        iRoute irl = rl->begin(); -        for (; irl != rl->end(); ++irl) { -              if (*irl == dstRoute) -                    break; -              } -        if (irl != rl->end()) { -              // disconnect if route exists -              audio->msgRemoveRoute(srcRoute, dstRoute); -              } -        else { -              // connect if route does not exist -              audio->msgAddRoute(srcRoute, dstRoute); -              } -        audio->msgUpdateSoloStates(); -        song->update(SC_ROUTE); -      }   -      else -      { -        if(track->type() == Track::AUDIO_INPUT) -        { -          int chan = n & 0xf; -           -          Route srcRoute(act->text(), false, -1, Route::JACK_ROUTE); -          Route dstRoute(t, chan); -           -          srcRoute.channel = chan; -           -          iRoute irl = rl->begin(); -          for(; irl != rl->end(); ++irl)  -          { -            if(*irl == srcRoute) -              break; -          } -          if(irl != rl->end())  -            // disconnect -            audio->msgRemoveRoute(srcRoute, dstRoute); -          else  -            // connect -            audio->msgAddRoute(srcRoute, dstRoute); -           -          audio->msgUpdateSoloStates(); -          song->update(SC_ROUTE); -          return; -        } -         -        iRouteMenuMap imm = gRoutingMenuMap.find(n); -        if(imm == gRoutingMenuMap.end()) -          return; -         -        Route &srcRoute = imm->second; -         -        Route dstRoute(t, imm->second.channel, imm->second.channels); -        dstRoute.remoteChannel = imm->second.remoteChannel; - -        iRoute irl = rl->begin(); -        for (; irl != rl->end(); ++irl) { -              if (*irl == srcRoute) -                    break; -              } -        if (irl != rl->end()) { -              // disconnect -              audio->msgRemoveRoute(srcRoute, dstRoute); -              } -        else { -              // connect -              audio->msgAddRoute(srcRoute, dstRoute); -              } -        audio->msgUpdateSoloStates(); -        song->update(SC_ROUTE); -      } -} -  //---------------------------------------------------------  //   oRoutePressed  //--------------------------------------------------------- @@ -1817,7 +1889,7 @@ void AudioStrip::oRoutePressed()        QAction* act = 0;        int gid = 0; -      int id = 0; +      //int id = 0;        pup->clear();        gRoutingMenuMap.clear(); @@ -1845,13 +1917,15 @@ void AudioStrip::oRoutePressed()              std::list<QString> ol = audioDevice->inputPorts();              for(std::list<QString>::iterator ip = ol.begin(); ip != ol.end(); ++ip)               { -              id = gid * 16 + i; +              //id = gid * 16 + i;        // IDs removed p4.0.14 Tim.                act = pup->addAction(*ip); -              act->setData(id); +              //act->setData(id); +              act->setData(gid);                act->setCheckable(true);                Route dst(*ip, true, i, Route::JACK_ROUTE); -              gRoutingMenuMap.insert( pRouteMenuMap(id, dst) ); +              //gRoutingMenuMap.insert( pRouteMenuMap(id, dst) ); +              gRoutingMenuMap.insert( pRouteMenuMap(gid, dst) );                ++gid;                for(iRoute ir = orl->begin(); ir != orl->end(); ++ir)                 { @@ -1865,6 +1939,24 @@ void AudioStrip::oRoutePressed()              if(i+1 != channel)                pup->addSeparator();            }       +           +          // p4.0.14 +          // +          // Display using separate menu for audio inputs: +          // +          pup->addSeparator(); +          pup->addAction(new MenuTitleItem(tr("Soloing chain"), pup));  +          PopupMenu* subp = new PopupMenu(pup); +          subp->setTitle(tr("Audio returns"));  +          pup->addMenu(subp); +          gid = addInPorts(t, subp, gid, gRoutingMenuMap, -1, -1, true);   +          // +          // Display all in the same menu: +          // +          //pup->addSeparator(); +          //MenuTitleItem* title = new MenuTitleItem(tr("Audio returns"), pup); +          //pup->addAction(title);  +          //gid = addInPorts(t, pup, gid, gRoutingMenuMap, -1, -1, true);            }          break;          //case Track::AUDIO_INPUT: diff --git a/muse2/muse/mixer/mstrip.cpp b/muse2/muse/mixer/mstrip.cpp index abf37a28..f6e195b0 100644 --- a/muse2/muse/mixer/mstrip.cpp +++ b/muse2/muse/mixer/mstrip.cpp @@ -394,8 +394,9 @@ MidiStrip::MidiStrip(QWidget* parent, MidiTrack* t)        oR->setText(tr("oR"));        oR->setCheckable(false);        // TODO: Works OK, but disabled for now, until we figure out what to do about multiple out routes and display values... -      oR->setEnabled(false); -      oR->setToolTip(tr("output routing")); +      // Enabled (for Midi Port to Audio Input routing). p4.0.14 Tim. +      //oR->setEnabled(false); +      //oR->setToolTip(tr("output routing"));        grid->addWidget(oR, _curGridRow++, 1);        connect(oR, SIGNAL(pressed()), SLOT(oRoutePressed())); diff --git a/muse2/muse/node.cpp b/muse2/muse/node.cpp index 8db0a3d3..114b03d3 100644 --- a/muse2/muse/node.cpp +++ b/muse2/muse/node.cpp @@ -208,9 +208,21 @@ void MidiTrack::updateSoloStates(bool noDec)    if(outPort() >= 0)    { -    MidiDevice *md = midiPorts[outPort()].device(); +    MidiPort* mp = &midiPorts[outPort()]; +    MidiDevice *md = mp->device();      if(md && md->isSynti())        ((SynthI*)md)->updateInternalSoloStates(); +       +    // Support Midi Port -> Audio Input solo chains. p4.0.14 Tim. +    const int chbits = 1 << outChannel(); +    const RouteList* rl = mp->outRoutes(); +    for(ciRoute ir = rl->begin(); ir != rl->end(); ++ir) +    { +      if(ir->type == Route::TRACK_ROUTE && ir->track && ir->track->type() == Track::AUDIO_INPUT && (ir->channel & chbits) ) +      { +        ir->track->updateInternalSoloStates(); +      }   +    }    }  } @@ -245,6 +257,18 @@ void AudioTrack::updateSoloStates(bool noDec)      {        if(ir->type == Route::TRACK_ROUTE)          ir->track->updateInternalSoloStates(); +      else   +      // Support Midi Port -> Audio Input solo chains. p4.0.14 Tim. +      if(ir->type == Route::MIDI_PORT_ROUTE)     +      { +        const MidiTrackList* ml = song->midis(); +        for(ciMidiTrack im = ml->begin(); im != ml->end(); ++im) +        { +          MidiTrack* mt = *im; +          if(mt->outPort() == ir->midiPort && ((1 << mt->outChannel()) & ir->channel) ) +            mt->updateInternalSoloStates(); +        } +      }      }    }      _tmpSoloChainDoIns = false; diff --git a/muse2/muse/route.cpp b/muse2/muse/route.cpp index 19f8d09f..92c32317 100644 --- a/muse2/muse/route.cpp +++ b/muse2/muse/route.cpp @@ -348,6 +348,59 @@ void addRoute(Route src, Route dst)                fprintf(stderr, "addRoute: source is midi port:%d, but destination is not track\n", src.midiPort);                return;              } +             +            // p4.0.14 +            /* +            if(dst.track->type() == Track::AUDIO_INPUT) +            { +              if(src.channel < 1 || src.channel >= (1 << MIDI_CHANNELS)) +              { +                fprintf(stderr, "addRoute: source is midi port:%d, but channel mask:%d out of range\n", src.midiPort, src.channel); +                return; +              } +               +              MidiPort *mp = &midiPorts[src.midiPort]; +              //src.channel = dst.channel = -1; +              RouteList* outRoutes = mp->outRoutes(); +              iRoute ir = outRoutes->begin();                                       +              for ( ; ir != outRoutes->end(); ++ir)  +              { +                //if (*i == dst)    // route already there +                ir->dump(); // REMOVE Tim. +                if (ir->type == Route::TRACK_ROUTE && ir->track == dst.track)     // Does a route to the track exist? +                { +                  //#ifdef ROUTE_DEBUG +                  fprintf(stderr, "addRoute: src midi port:%d dst audio in track:%s out route already exists. ir->channel:%d |= dst.channel:%d\n",  +                    src.midiPort, dst.track->name().toLatin1().constData(), ir->channel, dst.channel);  // REMOVE Tim. +                  //#endif +                  ir->channel |= dst.channel;    // Bitwise OR the desired channel bit with the existing bit mask. +                  break; +                  //return; +                }       +              } +              if(ir == outRoutes->end())    // Only if route not found, add the route, with the requested channel bits as mask to start with.  +                outRoutes->push_back(dst); +             +              RouteList* inRoutes = dst.track->inRoutes(); +               +              ir = inRoutes->begin(); +              for ( ; ir != inRoutes->end(); ++ir)          +              { +                if (ir->type == Route::MIDI_PORT_ROUTE && ir->midiPort == src.midiPort)  // Does a route to the midi port exist? +                { +                  fprintf(stderr, "addRoute: src midi port:%d dst audio in track:%s in route already exists. ir->channel:%d |= src.channel:%d\n",  +                    src.midiPort, dst.track->name().toLatin1().constData(), ir->channel, src.channel);  // REMOVE Tim. +                  ir->channel |= src.channel;    // Bitwise OR the desired channel bit with the existing bit mask. +                  break; +                }       +              } +              if(ir == inRoutes->end())    // Only if route not found, add the route, with the requested channel bits as mask to start with.  +                inRoutes->push_back(src); +             +              return; +            } +            */ +                          if(dst.channel < 1 || dst.channel >= (1 << MIDI_CHANNELS))              {                fprintf(stderr, "addRoute: source is midi port:%d, but destination channel mask:%d out of range\n", src.midiPort, dst.channel); @@ -752,14 +805,18 @@ void removeRoute(Route src, Route dst)            for (iRoute i = outRoutes->begin(); i != outRoutes->end(); ++i)             {              //if (*i == dst)  -            if (i->type == Route::TRACK_ROUTE && i->track == dst.track)  // p3.3.50 Is there a route to the track? +            if(i->type == Route::TRACK_ROUTE && i->track == dst.track)  // p3.3.50 Is there a route to the track?              { +              //printf("i->channel:%x dst.channel:%x\n", i->channel, dst.channel);                   i->channel &= ~dst.channel;        // p3.3.50 Unset the desired channel bits.                if(i->channel == 0)                // Only if there are no channel bits set, erase the route. +              { +                //printf("erasing out route from midi port:%d\n", src.midiPort);                     outRoutes->erase(i); -                 +              }   +                              break;                             // For safety, keep looking and remove any more found. -                                                 // No, must break, else crash. There should only be one route anyway... +                                                  // No, must break, else crash. There should only be one route anyway...              }            }          } @@ -777,9 +834,9 @@ void removeRoute(Route src, Route dst)                i->channel &= ~src.channel;        // p3.3.50 Unset the desired channel bits.                if(i->channel == 0)                // Only if there are no channel bits set, erase the route.                  inRoutes->erase(i); -                 +                              break;                             // For safety, keep looking and remove any more found. -                                                 // No, must break, else crash. There should only be one route anyway... +                                                  // No, must break, else crash. There should only be one route anyway...              }            }          } diff --git a/muse2/muse/track.cpp b/muse2/muse/track.cpp index b4519d8d..5038820e 100644 --- a/muse2/muse/track.cpp +++ b/muse2/muse/track.cpp @@ -739,40 +739,43 @@ bool Track::readProperties(Xml& xml, const QString& tag)  void Track::writeRouting(int level, Xml& xml) const  {        QString s; -              if (type() == Track::AUDIO_INPUT)         {          const RouteList* rl = &_inRoutes;          for (ciRoute r = rl->begin(); r != rl->end(); ++r)           { +          // Support Midi Port to Audio Input track routes. p4.0.14 Tim.  +          if(r->type == Route::MIDI_PORT_ROUTE) +          { +            s = QT_TRANSLATE_NOOP("@default", "Route"); +            if(r->channel != -1 && r->channel != 0)   +              s += QString(QT_TRANSLATE_NOOP("@default", " channelMask=\"%1\"")).arg(r->channel);  // Use new channel mask. +            xml.tag(level++, s.toLatin1().constData()); +             +            xml.tag(level, "source mport=\"%d\"/", r->midiPort); +             +            s = QT_TRANSLATE_NOOP("@default", "dest"); +            s += QString(QT_TRANSLATE_NOOP("@default", " name=\"%1\"/")).arg(Xml::xmlString(name())); +            xml.tag(level, s.toLatin1().constData()); +             +            xml.etag(level--, "Route"); +          } +          else            if(!r->name().isEmpty())            {              s = QT_TRANSLATE_NOOP("@default", "Route");              if(r->channel != -1)                s += QString(QT_TRANSLATE_NOOP("@default", " channel=\"%1\"")).arg(r->channel); -            ///Route dst(name(), true, r->channel); -            //xml.tag(level++, "Route");              xml.tag(level++, s.toAscii().constData());              // p3.3.38 New routing scheme. -            ///xml.strTag(level, "srcNode", r->name()); -            //xml.tag(level, "source type=\"%d\" name=\"%s\"/", r->type, r->name().toLatin1().constData());              s = QT_TRANSLATE_NOOP("@default", "source");              if(r->type != Route::TRACK_ROUTE)                s += QString(QT_TRANSLATE_NOOP("@default", " type=\"%1\"")).arg(r->type); -            //s += QString(QT_TRANSLATE_NOOP("@default", " name=\"%1\"/")).arg(r->name());              s += QString(QT_TRANSLATE_NOOP("@default", " name=\"%1\"/")).arg(Xml::xmlString(r->name()));              xml.tag(level, s.toAscii().constData()); -            ///xml.strTag(level, "dstNode", dst.name()); -             -            //if(r->channel != -1) -            //  xml.tag(level, "dest type=\"%d\" channel=\"%d\" name=\"%s\"/", Route::TRACK_ROUTE, r->channel, name().toLatin1().constData()); -            //else   -            //  xml.tag(level, "dest type=\"%d\" name=\"%s\"/", Route::TRACK_ROUTE, name().toLatin1().constData()); - -            //xml.tag(level, "dest name=\"%s\"/", name().toLatin1().constData());              xml.tag(level, "dest name=\"%s\"/", Xml::xmlString(name()).toLatin1().constData());              xml.etag(level--, "Route"); @@ -783,16 +786,13 @@ void Track::writeRouting(int level, Xml& xml) const        const RouteList* rl = &_outRoutes;        for (ciRoute r = rl->begin(); r != rl->end(); ++r)         { -        //if(!r->name().isEmpty()) +        // p4.0.14 Ignore Audio Output to Audio Input routes.  +        // They are taken care of by Audio Input in the section above. +        if(r->type == Route::TRACK_ROUTE && r->track && r->track->type() == Track::AUDIO_INPUT)  +          continue; +                      if(r->midiPort != -1 || !r->name().isEmpty()) // p3.3.49          { -          ///QString src(name()); -          ///if (type() == Track::AUDIO_OUTPUT)  -          ///{  -                ///Route s(src, false, r->channel); -                ///src = s.name(); -          ///} -                      s = QT_TRANSLATE_NOOP("@default", "Route");            if(r->type == Route::MIDI_PORT_ROUTE)  // p3.3.50            { @@ -809,45 +809,11 @@ void Track::writeRouting(int level, Xml& xml) const            if(r->remoteChannel != -1)              s += QString(QT_TRANSLATE_NOOP("@default", " remch=\"%1\"")).arg(r->remoteChannel); -          //xml.tag(level++, "Route");            xml.tag(level++, s.toAscii().constData()); -          ///xml.strTag(level, "srcNode", src); -          //if(r->channel != -1) -                      // Allow for a regular mono or stereo track to feed a multi-channel synti.  -          // thisChannel is the 'starting' channel of this source if feeding a regular track. -          //if(r->type == Route::TRACK_ROUTE && r->track->isSynti() && r->channel != -1) -          //if(isSynti() && r->thisChannel != -1) -            //xml.tag(level, "source type=\"%d\" channel=\"%d\" name=\"%s\"/", Route::TRACK_ROUTE, r->channel, name().toLatin1().constData()); -          //  xml.tag(level, "source type=\"%d\" channel=\"%d\" name=\"%s\"/", Route::TRACK_ROUTE, r->thisChannel, name().toLatin1().constData()); -          //else -           -          //if(r->channel != -1) -          //  xml.tag(level, "source type=\"%d\" channel=\"%d\" name=\"%s\"/", Route::TRACK_ROUTE, r->channel, name().toLatin1().constData()); -          //else   -          //  xml.tag(level, "source type=\"%d\" name=\"%s\"/", Route::TRACK_ROUTE, name().toLatin1().constData()); -          //xml.tag(level, "source name=\"%s\"/", name().toLatin1().constData());            xml.tag(level, "source name=\"%s\"/", Xml::xmlString(name()).toLatin1().constData()); -          ///xml.strTag(level, "dstNode", r->name()); -          //if(r->channel != -1) -          //  xml.tag(level, "dest type=\"%d\" channel=\"%d\" name=\"%s\"/", r->type, r->channel, r->name().toLatin1().constData()); -          //else   -          //  xml.tag(level, "dest type=\"%d\" name=\"%s\"/", r->type, r->name().toLatin1().constData()); -           -          // Allow for a regular mono or stereo track to feed a multi-channel synti.  -          // Channel is the 'starting' channel of the destination. -          //if(r->type == Route::TRACK_ROUTE && r->track->isSynti() && r->channel != -1) -           -          //if(r->type == Route::TRACK_ROUTE && r->track->type() == Track::AUDIO_SOFTSYNTH && r->remoteChannel != -1) -          //  xml.tag(level, "dest type=\"%d\" channel=\"%d\" name=\"%s\"/", r->type, r->remoteChannel, r->name().toLatin1().constData()); -          //else   -          //if(r->type == Route::MIDI_DEVICE_ROUTE) -          //  xml.tag(level, "dest devtype=\"%d\" name=\"%s\"/", r->device->deviceType(), r->name().toLatin1().constData()); -          //else   -          //  xml.tag(level, "dest type=\"%d\" name=\"%s\"/", r->type, r->name().toLatin1().constData()); -                      s = QT_TRANSLATE_NOOP("@default", "dest");            //if(r->type == Route::MIDI_DEVICE_ROUTE)                                      // p3.3.49 Obsolete since 1.1-RC2     diff --git a/muse2/muse/widgets/mtrackinfo.cpp b/muse2/muse/widgets/mtrackinfo.cpp index f9903037..04911b02 100644 --- a/muse2/muse/widgets/mtrackinfo.cpp +++ b/muse2/muse/widgets/mtrackinfo.cpp @@ -154,9 +154,10 @@ MidiTrackInfo::MidiTrackInfo(QWidget* parent, Track* sel_track) : QWidget(parent    connect(iRButton, SIGNAL(pressed()), SLOT(inRoutesPressed()));    // TODO: Works OK, but disabled for now, until we figure out what to do about multiple out routes and display values... +  // Enabled (for Midi Port to Audio Input routing). p4.0.14 Tim.    //oRButton->setEnabled(false);    //oRButton->setVisible(false); -  //connect(oRButton, SIGNAL(pressed()), SLOT(outRoutesPressed())); +  connect(oRButton, SIGNAL(pressed()), SLOT(outRoutesPressed()));    connect(song, SIGNAL(songChanged(int)), SLOT(songChanged(int)));    connect(muse, SIGNAL(configChanged()), SLOT(configChanged())); @@ -541,7 +542,10 @@ void MidiTrackInfo::iOutputChannelChanged(int channel)              // may result in adding/removing mixer strip:              //song->update(-1); -            song->update(SC_MIDI_TRACK_PROP); +            //song->update(SC_MIDI_TRACK_PROP); +            audio->msgUpdateSoloStates();                   // p4.0.14 +            //song->update(SC_MIDI_TRACK_PROP | SC_ROUTE);  // +            song->update(SC_MIDI_TRACK_PROP);               //              }        } @@ -563,7 +567,10 @@ void MidiTrackInfo::iOutputPortChanged(int index)        track->setOutPortAndUpdate(index);        audio->msgIdle(false); -      song->update(SC_MIDI_TRACK_PROP);   +      //song->update(SC_MIDI_TRACK_PROP);   +      audio->msgUpdateSoloStates();                   // p4.0.14 +      //song->update(SC_MIDI_TRACK_PROP | SC_ROUTE);  // +      song->update(SC_MIDI_TRACK_PROP);               //        }  //--------------------------------------------------------- @@ -652,7 +659,7 @@ void MidiTrackInfo::outRoutesPressed()    connect(pup, SIGNAL(triggered(QAction*)), SLOT(routingPopupMenuActivated(QAction*)));    connect(pup, SIGNAL(aboutToHide()), muse, SLOT(routingPopupMenuAboutToHide()));    pup->popup(QCursor::pos()); -  ///oRButton->setDown(false);      +  oRButton->setDown(false);         return;  } diff --git a/muse2/muse/widgets/mtrackinfobase.ui b/muse2/muse/widgets/mtrackinfobase.ui index 1649b1d5..3437b97e 100644 --- a/muse2/muse/widgets/mtrackinfobase.ui +++ b/muse2/muse/widgets/mtrackinfobase.ui @@ -131,11 +131,27 @@          <string>input routing</string>         </property>         <property name="text"> -        <string>In</string> +        <string>iR</string>         </property>        </widget>       </item>       <item> +       <widget class="QToolButton" name="oRButton"> +         <property name="sizePolicy"> +           <sizepolicy hsizetype="Minimum" vsizetype="Minimum"> +             <horstretch>0</horstretch> +             <verstretch>0</verstretch> +           </sizepolicy> +         </property> +         <property name="toolTip"> +           <string>output routing</string> +         </property> +         <property name="text"> +           <string>oR</string> +         </property> +       </widget> +     </item> +     <item>        <widget class="QLabel" name="iChanDetectLabel">         <property name="sizePolicy">          <sizepolicy hsizetype="Maximum" vsizetype="Fixed"> | 
