Browse Source

WinMME: Try to use MIDI in timestamps in the sanest way I can think of. This should eliminate jitter introduced by the code, but might create some latency.

tags/1.9.8
Devin Anderson 14 years ago
parent
commit
2d4542b24d
3 changed files with 15 additions and 21 deletions
  1. +6
    -6
      windows/winmme/JackWinMMEInputPort.cpp
  2. +9
    -12
      windows/winmme/JackWinMMEInputPort.h
  3. +0
    -3
      windows/winmme/JackWinMMEOutputPort.cpp

+ 6
- 6
windows/winmme/JackWinMMEInputPort.cpp View File

@@ -138,10 +138,11 @@ JackWinMMEInputPort::~JackWinMMEInputPort()
} }


void void
JackWinMMEInputPort::EnqueueMessage(jack_nframes_t time, size_t length,
JackWinMMEInputPort::EnqueueMessage(DWORD timestamp, size_t length,
jack_midi_data_t *data) jack_midi_data_t *data)
{ {
switch (thread_queue->EnqueueEvent(time, length, data)) {
jack_nframes_t frame = GetFramesFromTime(start_time + (timestamp * 1000));
switch (thread_queue->EnqueueEvent(frame, length, data)) {
case JackMidiWriteQueue::BUFFER_FULL: case JackMidiWriteQueue::BUFFER_FULL:
jack_error("JackWinMMEInputPort::EnqueueMessage - The thread queue " jack_error("JackWinMMEInputPort::EnqueueMessage - The thread queue "
"cannot currently accept a %d-byte event. Dropping event.", "cannot currently accept a %d-byte event. Dropping event.",
@@ -192,8 +193,6 @@ void
JackWinMMEInputPort::ProcessWinMME(UINT message, DWORD param1, DWORD param2) JackWinMMEInputPort::ProcessWinMME(UINT message, DWORD param1, DWORD param2)
{ {
set_threaded_log_function(); set_threaded_log_function();
jack_nframes_t current_frame = GetCurrentFrame();

switch (message) { switch (message) {
case MIM_CLOSE: case MIM_CLOSE:
jack_info("JackWinMMEInputPort::ProcessWinMME - MIDI device closed."); jack_info("JackWinMMEInputPort::ProcessWinMME - MIDI device closed.");
@@ -229,7 +228,7 @@ JackWinMMEInputPort::ProcessWinMME(UINT message, DWORD param1, DWORD param2)
"status byte."); "status byte.");
return; return;
} }
EnqueueMessage(current_frame, (size_t) length, message_buffer);
EnqueueMessage(dwParam2, (size_t) length, message_buffer);
break; break;
} }
case MIM_LONGDATA: { case MIM_LONGDATA: {
@@ -246,7 +245,7 @@ JackWinMMEInputPort::ProcessWinMME(UINT message, DWORD param1, DWORD param2)
jack_error("JackWinMMEInputPort::ProcessWinMME - Discarding " jack_error("JackWinMMEInputPort::ProcessWinMME - Discarding "
"%d-byte sysex chunk.", byte_count); "%d-byte sysex chunk.", byte_count);
} else { } else {
EnqueueMessage(current_frame, byte_count, data);
EnqueueMessage(dwParam2, byte_count, data);
} }
// Is this realtime-safe? This function isn't run in the JACK thread, // Is this realtime-safe? This function isn't run in the JACK thread,
// but we still want it to perform as quickly as possible. Even if // but we still want it to perform as quickly as possible. Even if
@@ -272,6 +271,7 @@ bool
JackWinMMEInputPort::Start() JackWinMMEInputPort::Start()
{ {
if (! started) { if (! started) {
start_time = GetMicroSeconds();
MMRESULT result = midiInStart(handle); MMRESULT result = midiInStart(handle);
started = result == MMSYSERR_NOERROR; started = result == MMSYSERR_NOERROR;
if (! started) { if (! started) {


+ 9
- 12
windows/winmme/JackWinMMEInputPort.h View File

@@ -37,30 +37,27 @@ namespace Jack {
DWORD param1, DWORD param2); DWORD param1, DWORD param2);


void void
EnqueueMessage(jack_nframes_t time, size_t length,
jack_midi_data_t *data);
EnqueueMessage(DWORD timestamp, size_t length, jack_midi_data_t *data);


void
GetInErrorString(MMRESULT error, LPTSTR text);


void void
ProcessWinMME(UINT message, DWORD param1, DWORD param2); ProcessWinMME(UINT message, DWORD param1, DWORD param2);


void
WriteInError(const char *jack_func, const char *mm_func,
MMRESULT result);

HMIDIIN handle; HMIDIIN handle;
jack_midi_event_t *jack_event; jack_midi_event_t *jack_event;
jack_time_t start_time;
bool started;
jack_midi_data_t *sysex_buffer; jack_midi_data_t *sysex_buffer;
MIDIHDR sysex_header; MIDIHDR sysex_header;
JackMidiAsyncQueue *thread_queue; JackMidiAsyncQueue *thread_queue;
JackMidiBufferWriteQueue *write_queue; JackMidiBufferWriteQueue *write_queue;


bool started;


void
WriteInError(const char *jack_func, const char *mm_func,
MMRESULT result);

void
GetInErrorString(MMRESULT error, LPTSTR text);

public: public:


JackWinMMEInputPort(const char *alias_name, const char *client_name, JackWinMMEInputPort(const char *alias_name, const char *client_name,


+ 0
- 3
windows/winmme/JackWinMMEOutputPort.cpp View File

@@ -217,7 +217,6 @@ JackWinMMEOutputPort::Execute()
} }


} }
stop_execution:
return false; return false;
} }


@@ -262,7 +261,6 @@ JackWinMMEOutputPort::ProcessJack(JackMidiBuffer *port_buffer,
jack_nframes_t frames) jack_nframes_t frames)
{ {
read_queue->ResetMidiBuffer(port_buffer); read_queue->ResetMidiBuffer(port_buffer);

for (jack_midi_event_t *event = read_queue->DequeueEvent(); event; for (jack_midi_event_t *event = read_queue->DequeueEvent(); event;
event = read_queue->DequeueEvent()) { event = read_queue->DequeueEvent()) {


@@ -369,4 +367,3 @@ JackWinMMEOutputPort::WriteOutError(const char *jack_func, const char *mm_func,
GetOutErrorString(result, error_message); GetOutErrorString(result, error_message);
jack_error("%s - %s: %s", jack_func, mm_func, error_message); jack_error("%s - %s: %s", jack_func, mm_func, error_message);
} }


Loading…
Cancel
Save