drumstick  1.0.1
netmidiinput_p.cpp
1 /*
2  Drumstick RT (realtime MIDI In/Out)
3  Copyright (C) 2009-2015 Pedro Lopez-Cabanillas <plcl@users.sf.net>
4 
5  This program is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation; either version 2 of the License, or
8  (at your option) any later version.
9 
10  This program is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  GNU General Public License for more details.
14 
15  You should have received a copy of the GNU General Public License along
16  with this program; if not, write to the Free Software Foundation, Inc.,
17  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18 */
19 
20 #include <QObject>
21 #include <QDebug>
22 
23 #include "netmidiinput_p.h"
24 #include "netmidiinput.h"
25 
26 namespace drumstick {
27 namespace rt {
28 
29 static QString DEFAULT_PUBLIC_NAME(QLatin1String("MIDI In"));
30 
31 NetMIDIInputPrivate::NetMIDIInputPrivate(QObject *parent) : QObject(parent),
32  m_inp(qobject_cast<NetMIDIInput *>(parent)),
33  m_out(0),
34  m_socket(0),
35  m_parser(0),
36  m_thruEnabled(false),
37  m_port(0),
38  m_publicName(DEFAULT_PUBLIC_NAME),
39  m_groupAddress(QHostAddress(STR_ADDRESS))
40 {
41  for(int i=MULTICAST_PORT; i<LAST_PORT; ++i) {
42  m_inputDevices << QString::number(i);
43  }
44 }
45 
46 void NetMIDIInputPrivate::open(QString portName)
47 {
48  int p = m_inputDevices.indexOf(portName);
49  if (p > -1)
50  {
51  m_socket = new QUdpSocket();
52  m_parser = new MIDIParser(m_inp);
53  m_port = MULTICAST_PORT + p;
54  m_currentInput = portName;
55  m_socket->bind(QHostAddress::AnyIPv4, m_port, QUdpSocket::ShareAddress);
56  m_socket->setSocketOption(QAbstractSocket::MulticastLoopbackOption, 0);
57  m_socket->setSocketOption(QAbstractSocket::MulticastTtlOption, 1);
58  if (m_iface.isValid()) {
59  m_socket->joinMulticastGroup(m_groupAddress, m_iface);
60  } else {
61  m_socket->joinMulticastGroup(m_groupAddress);
62  }
63  connect(m_socket, SIGNAL(readyRead()), this, SLOT(processIncomingMessages()));
64  //qDebug() << Q_FUNC_INFO << portName;
65  }
66 }
67 
68 void NetMIDIInputPrivate::close()
69 {
70  delete m_socket;
71  delete m_parser;
72  m_socket = 0;
73  m_parser = 0;
74  m_currentInput.clear();
75 }
76 
77 void NetMIDIInputPrivate::initialize(QSettings *settings)
78 {
79  if (settings != 0) {
80  settings->beginGroup("Network");
81  QString ifaceName = settings->value("interface", QString()).toString();
82  QString address = settings->value("address", STR_ADDRESS).toString();
83  settings->endGroup();
84  if (!ifaceName.isEmpty()) {
85  m_iface = QNetworkInterface::interfaceFromName(ifaceName);
86  }
87  if (!address.isEmpty()) {
88  m_groupAddress.setAddress(address);
89  }
90  }
91 }
92 
93 void NetMIDIInputPrivate::setMIDIThruDevice(MIDIOutput* device)
94 {
95  m_out = device;
96  if (m_parser != 0) {
97  m_parser->setMIDIThruDevice(device);
98  }
99 }
100 
101 void NetMIDIInputPrivate::processIncomingMessages()
102 {
103  while (m_socket->hasPendingDatagrams()) {
104  QByteArray datagram;
105  datagram.resize(m_socket->pendingDatagramSize());
106  m_socket->readDatagram(datagram.data(), datagram.size());
107  if (m_parser != 0) {
108  m_parser->parse(datagram);
109  }
110  }
111 }
112 
113 }}
The QObject class is the base class of all Qt objects.