B4A Library Midi Driver Lib

Android have still not allowed streaming Midi to the internal Midi device so for those interested in trying out streaming midi data to the onboard Sonivox midi device, here is a wrapper for BillTheFarmers Midi Driver. This is the first of a few things I will be posting over the next week or two that are Midi Related.

Be aware that performance will vary greatly depending on the device it is used on.

The wrapper is pretty light with very few modifications. It has been working pretty well while I have been developing other things (to be released soon) so I thought I'd share it sooner rather than later.

Unfortunately the Midi Driver Lib is too large to upload to the Forum as it contains the Sonivox Library even though it uses a fraction of it (see link below).

The Midi Piano project attached is what is says it is, a graphic of a piano that sends midi note on, note off and patch change messages to the driver.

If you do not know anything about the Midi standards I suggest you do some research before starting to try to program it. Two very good resources are:

http://www.sonicspot.com/guide/midifiles.html

and

http://www.somascape.org/midi/tech/mfile.html

You should be able to get most of the information you need from these.

I am hoping that I can soon release a port of a large portion of the Javax.Midi classes, written entirely in B4a which will support MidiEvents, Sequence ,RealTimeSequencer and Recording which may also be of interest.

The Midi Piano app depends on JavaObject and Gestures Libraries and of course the MidiDriver Lib available below. Unzip the jar and XML files and copy them to your additional Libraries folder.

The biggest downside is that we are stuck with the reverb, apparently the Sonivox library has disabled the changing of the reverb by conventional means. I am trying to find out their Sysex command structure, but am not having much luck so far. I'll keep you posted on that one.

You can download the Midi Driver V2 Library from my Google Drive here.

This is definitely Beta software, please test it thoroughly and let me know if you find any issues in this thread. It would also be useful to know how usable it is on different devices.

For my part, it's OK on my 2013 Nexus 7.

Update to V2 (Download from the above link) to allow newer android devices to access the mididriver (Requires the MidiSystem2 download from here)

Enjoy
 

Attachments

  • MidiPiano.zip
    14.9 KB · Views: 690
Last edited:

giacomo-italy

Member
Licensed User
Longtime User
Hello stevel05, since you are an expert in sound generation with Android, I can ask you a question?
I need to generate a sound (even a simple sine wave form) and i want to change its frequency and its amplitude in a continuous manner, while the sound is generated.

I tried with AudioStreamer with the code posted by Erel:

B4X:
Sub Process_Globals
Dim streamer As AudioStreamer
Dim timer1 As Timer
Dim freq As Int = 500
End Sub

Sub Globals
End Sub

Sub Activity_Create(FirstTime As Boolean)
If FirstTime Then
streamer.Initialize("streamer", 11025, True, 16, streamer.VOLUME_MUSIC)
streamer.StartPlaying
timer1.Initialize("timer1", 1000)
End If
timer1.Enabled = True
End Sub

Sub Timer1_Tick
Log(freq)
Beep(1000, freq)
freq = freq + 500
End Sub

Sub Beep(Duration As Int, Frequency As Int)
Dim dur As Double = Duration / 10000
Dim sampleRate As Int = 11025
Dim numSamples As Int = sampleRate * dur
Dim snd(2 * numSamples) As Byte
For i = 0To numSamples - 1
Dim d As Double = Sin(2 * cPI * i / (sampleRate / Frequency))Dim val As Short = d * 32767
snd(i * 2) = Bit.AND(0xff, val)
snd(i * 2 + 1) = Bit.ShiftRight(Bit.AND(0xff00, val), 8)Next
streamer.Write(snd)
End Sub

Sub Activity_Pause (UserClosed As Boolean)
timer1.Enabled = False
End Sub

But I can change frequency before each duration.
I tried to reduce the duration of the sound and insert the frequency change in a loop of the same duration,
but the resulting sound is choppy and full of disturbs 'click' and noise.

Is there an alternative way to generate a sound and change frequency and amplitude, in a continuos way,
while the sound is generated (to obtain an effect type like 'theremin')?

Thanks a lot.
 

stevel05

Expert
Licensed User
Longtime User
@giacomo-italy I did see your post but don't currently have the time to look at the problem as it won't be a 10 minute job If it's not sorted when I get more time, I'll take a look.

Please keep library threads for discussions about the relevant libraries.
 

stevel05

Expert
Licensed User
Longtime User
Simple example attached. Hope it helps.
 

Attachments

  • MDT.zip
    12 KB · Views: 395

Marios Chrysikopoulos

New Member
Licensed User
Longtime User
Thank you so very much! Your example helped me understand the logic behind this. How we can specify the duration of a note (between a note on and a note off message?). I searched but I found nothing about it. There is another midi message that passes this information?
 

stevel05

Expert
Licensed User
Longtime User
Yes, a separate message is required.

Note off is defined as 0x80, but it can also be a note on with a zero volume (and more commonly used in midi files), So:

B4X:
Midi.SendMidi(Array As Byte(0x80,0x29,0))

and

Midi.SendMidi(Array As Byte(0x90,0x29,0))

will both achieve the desired result.

Be aware that as we are streaming the data directly using this library, the timing is defined by when the data is sent. You will need to implement any timing logic in your code if it is not playing in real time (i.e. in response to user input).
 

Michael Wenning

Member
Licensed User
Longtime User
Hello Steve,
your Midi Driver Library works great on Samsung A3 with Android 5.0.
Thank's for this great work!!!
After update to Android 7.0 it doesn't work. I have found out that BillTheFarmer
had updated his driver because of this issues to version 1.14.
Can you please update your libary with this driver?
Thank's and regards,
Michael
 

stevel05

Expert
Licensed User
Longtime User
Hi Michael, I tried a quick recompile using the latest Bill the Farmer libs, unfortunately there seem to be some significant changes to the code that will need some investigation.

However, from Android 6, there has been native android support for midi. Documentation is here: https://developer.android.com/reference/android/media/midi/package-summary.html

It is likely that this would provide better performance than Bill the farmers interface code.

I will have a quick look not to see if I can do anything short term, but I don't have time to investigate thoroughly, when I do I will take a better look and see what the best way forward will be.
 

stevel05

Expert
Licensed User
Longtime User
On further investigation the Android midi implementation lacks the message and file classes, which makes it a player and receiver of midi. What I am inclined to do is to rewrite parts of my library to use the android system for the appropriate parts if it's available, otherwise use the existing method of playing the midi.

If you let me know what you are doing with the library I'll schedule to do those areas you need first and make an initial release when done.
 

Michael Wenning

Member
Licensed User
Longtime User
Hello Steve,
I generate new midi sequences, save them in files. Then they are reloaded,
optimized and saved again. So I need this file class. The further advantage of a
updated library would be the downgrade compability up to Android 4.
The time component is secondary.
Thank you for your efforts and help!
 

stevel05

Expert
Licensed User
Longtime User
Can you try the files in the link please.

It includes latest BillTheFarmer driver. It works on android 6, but I don't have 7 to try it on. As his library now includes a wrap of the sonivox lib, it's too large to post on the forums.

Copy the 4 files to you addl libs folder.

https://www.dropbox.com/s/96xb4v4fa36oksg/MidiSystem2.zip?dl=0

Steve.
 
Last edited:

stevel05

Expert
Licensed User
Longtime User
I just tried it on my new phone (I forgot it had 7). And it works. Let me know if you have problems with it.
 

Michael Wenning

Member
Licensed User
Longtime User
Hello Steve,
I tried it and it works perfect on Samsung A3 with Android 7.0 !!!
Thank's for this great work!!!
Best regards from Germany,
Michael
 

Michael Wenning

Member
Licensed User
Longtime User
Hello,
I am using the library version from 31.10.2017.
If i compile it with jdk1.8.0_40\bin\javac.exe no problems.
If i switch to resent jdk-10.0.1\bin\javac.exe i get this error:
"Uncaught translation error: java.lang.IllegalArgumentException: already added: Lcom/stevel05/Utils;"

I tried to rename in my b4a code the class "Utils" to "SharedTools" but whitout success.

What am I doing wrong?

Thank's and regards
Michael
 

stevel05

Expert
Licensed User
Longtime User
Is your app based on one of the examples? If so try changing the package name in build configurations to something other than com.stevel05

I don't think there is a module within the library and it's dependencies called Utils I try to make it so there is no conflicts, so there is one called MidiUtils.

I am still using Java 8 and am not ready to move to 9 or 10 anytime soon. I did try it, but it wreaked havoc with the java installation so I removed it.

It is strange that it works in java 8 but not 10.
 

Michael Wenning

Member
Licensed User
Longtime User
Thank you for information. I have changed build configuration before.

If I have found a solution, I will contact you.

Best regards
Michael
 
Top