aboutsummaryrefslogtreecommitdiffstats
path: root/daemon/src
diff options
context:
space:
mode:
Diffstat (limited to 'daemon/src')
-rw-r--r--daemon/src/connection_manager.cpp38
-rw-r--r--daemon/src/connection_manager.h15
-rw-r--r--daemon/src/main.cpp30
-rw-r--r--daemon/src/message.h25
-rw-r--r--daemon/src/routing.cpp5
-rw-r--r--daemon/src/routing.h8
-rw-r--r--daemon/src/sender.h17
-rw-r--r--daemon/src/submitter.h15
-rw-r--r--daemon/src/types.h19
9 files changed, 115 insertions, 57 deletions
diff --git a/daemon/src/connection_manager.cpp b/daemon/src/connection_manager.cpp
index 3b2d7da..f6a02c1 100644
--- a/daemon/src/connection_manager.cpp
+++ b/daemon/src/connection_manager.cpp
@@ -1,17 +1,33 @@
#include "connection_manager.h"
+#include "sender.h"
+
#include <iostream>
#include <rtmidi/RtMidi.h>
namespace midi_router
{
-struct Device_Connection
+struct Device_Connection : public Sender
{
- Device_Id source_id;
- std::function<void(Message const &)> const & submit;
+ Device_Connection(Device_Id const & source_id, Submitter & submitter):
+ source_id(source_id),
+ submitter(submitter)
+ {}
+
+ Device_Id const & source_id;
+ Submitter & submitter;
RtMidiIn midi_in {};
RtMidiOut midi_out {};
+
+ void
+ send(std::array<std::uint8_t, 3> const & payload) override
+ {
+ if (midi_out.isPortOpen())
+ {
+ midi_out.sendMessage(payload.data(), 3);
+ }
+ }
};
static void
@@ -25,17 +41,17 @@ callback(double time_stamp, std::vector<unsigned char> *raw, void *user_data)
}
Message message { &device->source_id, {raw->at(0), raw->at(1), raw->at(2)} };
- device->submit(message);
+ device->submitter.submit(message);
}
-Connection_Manager::Connection_Manager(Device_Map const & device_map, std::function<void(Message const &)> const & submit):
+Connection_Manager::Connection_Manager(Device_Map const & device_map, Submitter & submitter):
m_device_map(device_map),
- m_submit(submit),
+ m_submitter(submitter),
m_connections{}
{
for (auto const & [name, id] : device_map)
{
- m_connections[id] = std::make_unique<Device_Connection>(id, submit);
+ m_connections[id] = std::make_unique<Device_Connection>(id, submitter);
auto & connection = m_connections[id];
connection->midi_in.setCallback(&callback, connection.get());
@@ -50,12 +66,18 @@ Connection_Manager::Connection_Manager(Device_Map const & device_map, std::funct
{
std::cerr << "Output port not found for device " << name << "\n";
}
-
+
}
}
Connection_Manager::~Connection_Manager() = default;
+Sender &
+Connection_Manager::get_sender(Device_Id const & device) const
+{
+ return *m_connections.at(device);
+}
+
bool
Connection_Manager::open_port(RtMidi* const midi, std::string const & name)
{
diff --git a/daemon/src/connection_manager.h b/daemon/src/connection_manager.h
index 240e436..e15eaaa 100644
--- a/daemon/src/connection_manager.h
+++ b/daemon/src/connection_manager.h
@@ -1,12 +1,12 @@
#pragma once
#include "types.h"
-#include "message.h"
+#include "submitter.h"
+#include "sender.h"
-#include <functional>
#include <string>
-#include <map>
#include <memory>
+#include <map>
class RtMidi;
@@ -18,17 +18,20 @@ struct Device_Connection;
class Connection_Manager
{
public:
- Connection_Manager(Device_Map const & device_map, std::function<void(Message const &)> const & submit);
+ Connection_Manager(Device_Map const & device_map, Submitter & submitter);
~Connection_Manager();
+ Sender &
+ get_sender(Device_Id const & device) const;
+
private:
static bool
open_port(RtMidi* const midi, std::string const & name);
Device_Map const & m_device_map;
- std::function<void(Message const &)> m_submit;
- std::map<std::string, std::unique_ptr<Device_Connection>> m_connections;
+ Submitter & m_submitter;
+ std::map<Device_Id, std::unique_ptr<Device_Connection>> m_connections;
};
} // namespace midi_router
diff --git a/daemon/src/main.cpp b/daemon/src/main.cpp
index dc72433..008fd2a 100644
--- a/daemon/src/main.cpp
+++ b/daemon/src/main.cpp
@@ -1,5 +1,5 @@
#include "connection_manager.h"
-#include "configuration.h"
+#include "types.h"
#include "routing.h"
#include <iostream>
@@ -10,17 +10,29 @@ using namespace midi_router;
int main()
{
- Configuration const config {{
- {"Deluge MIDI 1", "deluge"},
- {"MPK mini Plus MIDI 1", "mpk"},
- }};
-
+ // LTG: move configuration to TOML file
+ Device_Map const devices {
+ { "Deluge MIDI 1", "deluge" },
+ { "MPK mini Plus MIDI 1", "mpk" },
+ { "Xjam MIDI 1", "xjam" },
+ { "OP-1 MIDI 1", "op1" },
+ };
+
Router router {};
- Connection_Manager cm { config.devices, [&](Message const & m){ router.submit(m); } }; // works
- //Connection_Manager cm { config.devices, std::bind(&Router::submit, &router, std::placeholders::_1) }; // why doesn't this work?
+ Connection_Manager cm { devices, router };
+
+ Route_Map const routes {
+ { "mpk",
+ {
+ { Message_Type::NOTE_ON, { cm.get_sender("deluge"), cm.get_sender("op1") } },
+ { Message_Type::NOTE_OFF, { cm.get_sender("deluge"), cm.get_sender("op1")} },
+ }
+ },
+ };
while(true)
{
- std::this_thread::sleep_for(std::chrono::seconds(1));
+ router.route(routes);
+ //std::this_thread::sleep_for(std::chrono::milliseconds(500));
}
}
diff --git a/daemon/src/message.h b/daemon/src/message.h
deleted file mode 100644
index 4668e0c..0000000
--- a/daemon/src/message.h
+++ /dev/null
@@ -1,25 +0,0 @@
-#pragma once
-
-#include "types.h"
-
-#include <string>
-#include <cstdint>
-#include <array>
-
-namespace midi_router
-{
-
-struct Message
-{
- Device_Id const * source_id;
- std::array<std::uint8_t, 3> bytes;
-
- Message_Type
- type() const
- {
- if (bytes[0] & 0xF0 == 0xF0) return static_cast<Message_Type>(bytes[0]);
- else return static_cast<Message_Type>(bytes[0] >> 4);
- }
-};
-
-} // namespace midi_router
diff --git a/daemon/src/routing.cpp b/daemon/src/routing.cpp
index 15ae555..ac15eff 100644
--- a/daemon/src/routing.cpp
+++ b/daemon/src/routing.cpp
@@ -17,9 +17,10 @@ Router::route(Route_Map const & config)
return;
}
+ // LTG: at least one of these map accesses can be avoided
for (auto const & target: config.at(*m.source_id).at(m.type()))
{
- target(m.bytes);
+ target.get().send(m.bytes);
}
}
}
@@ -29,7 +30,7 @@ Router::submit(Message const & message)
{
if (!m_queue.try_enqueue(message))
{
- std::cout << "Failed to enqueue message from " << message.source_id << "\n";
+ std::cerr << "Failed to enqueue message from " << *message.source_id << "\n";
}
}
diff --git a/daemon/src/routing.h b/daemon/src/routing.h
index c7cd243..592606d 100644
--- a/daemon/src/routing.h
+++ b/daemon/src/routing.h
@@ -1,21 +1,21 @@
#pragma once
-#include "message.h"
-#include "configuration.h"
+#include "types.h"
+#include "submitter.h"
#include "concurrentqueue/blockingconcurrentqueue.h"
namespace midi_router
{
-class Router
+class Router : public Submitter
{
public:
void
route(Route_Map const & config);
void
- submit(Message const & message);
+ submit(Message const & message) override;
private:
moodycamel::BlockingConcurrentQueue<Message> m_queue {};
diff --git a/daemon/src/sender.h b/daemon/src/sender.h
new file mode 100644
index 0000000..b7437c5
--- /dev/null
+++ b/daemon/src/sender.h
@@ -0,0 +1,17 @@
+#pragma once
+
+#include <cstdint>
+#include <array>
+
+namespace midi_router
+{
+
+class Sender
+{
+public:
+ virtual void
+ send(std::array<std::uint8_t, 3> const & payload) = 0;
+};
+
+} // namespace midi_router
+
diff --git a/daemon/src/submitter.h b/daemon/src/submitter.h
new file mode 100644
index 0000000..6f8756b
--- /dev/null
+++ b/daemon/src/submitter.h
@@ -0,0 +1,15 @@
+#pragma once
+
+#include "types.h"
+
+namespace midi_router
+{
+
+class Submitter
+{
+public:
+ virtual void
+ submit(Message const & message) = 0;
+};
+
+} // namespace midi_router
diff --git a/daemon/src/types.h b/daemon/src/types.h
index 2942c0b..a5c6165 100644
--- a/daemon/src/types.h
+++ b/daemon/src/types.h
@@ -1,5 +1,7 @@
#pragma once
+#include "sender.h"
+
#include <cstdint>
#include <array>
#include <string>
@@ -29,9 +31,20 @@ enum class Message_Type
using Device_Id = std::string;
using Device_Map = std::map<std::string, Device_Id>;
-
-using Send_Callback = std::function<void(std::array<std::uint8_t, 3> const & payload)>;
-using Target_List = std::vector<Send_Callback>;
+using Target_List = std::vector<std::reference_wrapper<Sender>>;
using Route_Map = std::map<Device_Id, std::map<Message_Type, Target_List>>;
+struct Message
+{
+ Device_Id const * source_id;
+ std::array<std::uint8_t, 3> bytes;
+
+ Message_Type
+ type() const
+ {
+ if ((bytes[0] & 0xF0) == 0xF0) return static_cast<Message_Type>(bytes[0]);
+ else return static_cast<Message_Type>(bytes[0] >> 4);
+ }
+};
+
} // namespace midi_router