Skip to content

Commit

Permalink
Merge pull request obsproject#9 from Alzy/Bidirectional
Browse files Browse the repository at this point in the history
Bidirectional
  • Loading branch information
cpyarger committed May 31, 2020
2 parents 596c275 + 041fb26 commit dff44f1
Show file tree
Hide file tree
Showing 24 changed files with 3,027 additions and 396 deletions.
9 changes: 6 additions & 3 deletions CMakeLists.txt
Expand Up @@ -79,7 +79,9 @@ set(obs-midi_SOURCES
forms/settings-dialog.cpp
forms/configwindow.cpp
obs-midi.cpp

events.cpp
rpc/RpcEvent.cpp

)

list(APPEND obs-midi_HEADERS
Expand All @@ -91,8 +93,9 @@ list(APPEND obs-midi_HEADERS
forms/settings-dialog.h
forms/configwindow.h
obs-midi.h


events.h
rpc/RpcEvent.h

)

add_library(obs-midi MODULE
Expand Down
26 changes: 23 additions & 3 deletions README.md
Expand Up @@ -7,9 +7,7 @@ Currently a WIP
# Installing


1. Grab the zip from the releases page

* https://github.com/Alzy/obs-midi/releases/tag/v0.1.0
1. Grab the zip from the [OBS-Midi Releases Page](https://github.com/Alzy/obs-midi/releases/tag/v0.1.0)

2. Copy the files in the zip to your obs plugins directory.

Expand All @@ -23,3 +21,25 @@ Currently a WIP


Currently There is only a windows build, But as this uses the RTMIDI library, and is cross-platform compatible, we may release a binary for mac or windows.

# Build instructions
in your obs-studio/plugins folder
1. ```git clone --recursive https://github.com/Alzy/obs-midi```
2. Append to CMakeLists.txt
* ```add_subdirectory(obs-midi)```
Go back to your obs Build directory
## windows
1. run ```cmake-gui.exe```
2. click ```configure```
3. click ```generate```
4. click ```open project```
5. in visual studio, right click on the obs-studio solution and click build
## Linux
1. Rerun cmake using your normal options
2. rerun ```make -j4```
3. rerun ```sudo make install``` / ```sudo checkinstall``` depending on which you normally use.
### [More info on building OBS from source](https://github.com/obsproject/obs-studio/wiki/install-instructions)

# Special thanks to the following projects
* [RTMidi17](https://github.com/jcelerier/RtMidi17) An amazing modernized RTMIDI library
* [OBSWebsocket](https://github.com/Palakis/obs-websocket/) from which much code was borrowed for interfacing with obs
101 changes: 93 additions & 8 deletions device-manager.cpp
Expand Up @@ -20,10 +20,13 @@ with this program. If not, see <https://www.gnu.org/licenses/>
DeviceManager::DeviceManager()
{
rtMidi = new rtmidi::midi_in();
MO = new rtmidi::midi_out();
}

DeviceManager::~DeviceManager()
{
rtMidi->~midi_in();
MO->~midi_out();
}

/* Load the Device Manager from saved Config Store data.
Expand All @@ -32,6 +35,7 @@ DeviceManager::~DeviceManager()
void DeviceManager::Load(obs_data_t* data)
{
vector <string> portsList = GetPortsList();
vector<string> outPortsList = GetOutPortsList();
obs_data_array_t* devicesData = obs_data_get_array(data, "devices");
size_t deviceCount = obs_data_array_count(devicesData);
for (size_t i = 0; i < deviceCount; i++)
Expand All @@ -40,14 +44,21 @@ void DeviceManager::Load(obs_data_t* data)
MidiAgent* device = new MidiAgent();
device->Load(deviceData);
midiAgents.push_back(device);

connect(this, SIGNAL(bcast(QString, QString)), device,
SLOT(NewObsEvent(QString, QString)));
if (device->isEnabled())
{
int portNumber = GetPortNumberByDeviceName(device->GetName().c_str());
if (portNumber != -1)
int outPort = GetOutPortNumberByDeviceName(device->GetOutName().c_str());

if (portNumber != -1 )
{
device->OpenPort(portNumber);
}
if (outPort != -1) {
device->OpenOutPort(outPort);
}

}
}
}
Expand All @@ -65,8 +76,23 @@ vector <string> DeviceManager::GetPortsList()
}
return ports;
}

/* Returns the port number of the specified device.
/* Returns vector list of Port Names
*/
vector<string> DeviceManager::GetOutPortsList()
{
opl.clear();
vector<string> outports;
int portCount = MO->get_port_count();
for (int i = 0; i < portCount; i++) {
outports.push_back(MO->get_port_name(i));
opl.append(QString::fromStdString(MO->get_port_name(i)));
}
return outports;
}
QStringList DeviceManager::GetOPL() {
return opl;
}
/* Returns the port number of the specified device.
* If the device isn't found (possibly due to being disconnected), returns -1
*/
int DeviceManager::GetPortNumberByDeviceName(const char* deviceName)
Expand All @@ -81,6 +107,22 @@ int DeviceManager::GetPortNumberByDeviceName(const char* deviceName)
}
}

/* Returns the port number of the specified device.
* If the device isn't found (possibly due to being disconnected), returns -1
*/
int DeviceManager::GetOutPortNumberByDeviceName(const char* deviceName)
{

vector<string> portsList = GetOutPortsList();

auto it = find(portsList.begin(), portsList.end(), deviceName);
if (it != portsList.end()) {
return distance(portsList.begin(), it);
} else {
return -1;
}
}


vector<MidiAgent*> DeviceManager::GetActiveMidiDevices()
{
Expand Down Expand Up @@ -112,12 +154,14 @@ vector <MidiHook*> DeviceManager::GetMidiHooksByDeviceName(const char* deviceNam
/* Registers a midi device.
* Will create, store and enable a midi device.
*/
void DeviceManager::RegisterMidiDevice(int port)
void DeviceManager::RegisterMidiDevice(int port, int outport)
{
MidiAgent* midiIn = new MidiAgent();
midiIn->OpenPort(port);
MidiAgent* midiA = new MidiAgent();
midiA->OpenPort(port);
midiA->OpenOutPort(outport);

midiAgents.push_back(midiA);

midiAgents.push_back(midiIn);
}


Expand All @@ -139,3 +183,44 @@ obs_data_t* DeviceManager::GetData()
return data;
}

void DeviceManager::SendMidi(QString mtype, int channel, int norc, int value)

{

//***Need to add message Deletion here***//

}
void DeviceManager::broadcast(const RpcEvent& event)
{
OBSDataAutoRelease eventData = obs_data_create();

QString updateType = event.updateType();
obs_data_set_string(eventData, "update-type",
updateType.toUtf8().constData());

std::optional<uint64_t> streamTime = event.streamTime();
if (streamTime.has_value()) {
QString streamingTimecode =
Utils::nsToTimestamp(streamTime.value());
obs_data_set_string(eventData, "stream-timecode",
streamingTimecode.toUtf8().constData());
}

std::optional<uint64_t> recordingTime = event.recordingTime();
if (recordingTime.has_value()) {
QString recordingTimecode =
Utils::nsToTimestamp(recordingTime.value());
obs_data_set_string(eventData, "rec-timecode",
recordingTimecode.toUtf8().constData());
}

OBSData additionalFields = event.additionalFields();
if (additionalFields) {
obs_data_apply(eventData, additionalFields);
}



//blog(1, "OBS EVENT %s -- %s", event.updateType().toStdString().c_str(),obs_data_get_json(eventData));
emit bcast(event.updateType(), QString::fromStdString(obs_data_get_json(eventData)));
};
29 changes: 21 additions & 8 deletions device-manager.h
Expand Up @@ -21,30 +21,43 @@ with this program. If not, see <https://www.gnu.org/licenses/>
#include <obs-frontend-api/obs-frontend-api.h>
#include <util/config-file.h>
#include <QtCore/QString>
#include <set>
#include <QtCore/QObject>
#include <QtCore/QMutex>
#include <QtCore/QSharedPointer>
#include <QtCore/QVariantHash>
#include <QtCore/QThreadPool>
#include <vector>
#include "midi-agent.h"

#include "rpc/RpcEvent.h"
using namespace std;

class DeviceManager {
public:
class DeviceManager: public QObject {
Q_OBJECT
public:
DeviceManager();
~DeviceManager();
void Load(obs_data_t* data);

vector <string> GetPortsList();
int GetPortNumberByDeviceName(const char* deviceName);

vector<string> GetOutPortsList();
int GetOutPortNumberByDeviceName(const char* deviceName);
QStringList opl;
vector<MidiAgent*> GetActiveMidiDevices();
MidiAgent* GetMidiDeviceByName(const char* deviceName);
vector <MidiHook *> GetMidiHooksByDeviceName(const char* deviceName);

void RegisterMidiDevice(int port);

QStringList GetOPL();
void RegisterMidiDevice(int port, int outport);
void SendMidi(QString mtype, int channel, int norc,
int value);
obs_data_t* GetData();

void broadcast(const RpcEvent &event);
signals:
void bcast(QString updateType, QString eventData);
private:
rtmidi::midi_in *rtMidi;
rtmidi::midi_out *MO;

vector<MidiAgent*> midiAgents;
};

0 comments on commit dff44f1

Please sign in to comment.