jesse-scam / algorithmic-beat-mapping-unity

Real-time and Preprocessed Audio Analysis for Onset Detection (Beat Mapping) Using Spectral Flux
MIT License
139 stars 33 forks source link

Logging peak and flux points over time? #1

Closed dza6549 closed 5 years ago

dza6549 commented 5 years ago

Hi thanks for the script. It works great.

This is not really an issue but a question about how I might send peak and flux points with a timestamp to a text file.

I'm hoping to use this info in a Unity timeline and kludge up a .playable file.

I've tried Debug.Log(pointInfo[i].spectralFlux); in updatePlot and I can see a logSample function in the Spectral.cs script but it is not plugged in.

Thanks for any suggestions. Cheers

jesse-scam commented 5 years ago

Sure.

Basically what you'll want to do is reduce the SpectralFluxAnalyzer::spectralFluxSamples to only contain the information you want to store to a file.

At the point where the full audio file has been processed: https://github.com/jesse-scam/algorithmic-beat-mapping-unity/blob/master/Assets/Lib/Internal/SongController.cs#L143

You are guaranteed that the public member SpectralFluxAnalyzer::spectralFluxSamples has all of the information you are looking for.

Now, you can loop through that List, picking out which items you care about. If you only care about peaks, you could do this when the peak is detected, but we'll assume that you want to pull information after the processing has completed.

You could do something like:

  1. Loop over preProcessedSpectralFluxAnalyzer.spectralFluxSamples, storing the string time of each sample you want to save.
    List<string> timeStrings = new List<string> ();
    foreach (SpectralFluxInfo info in preProcessedSpectralFluxAnalyzer.spectralFluxSamples) {
    if (info.is_peak) {
        timeStrings.Add(info.time.ToString());
    }
    }

    Pseudo-code, but you get the idea.

Then write all strings of this List to a file: https://docs.microsoft.com/en-us/dotnet/api/system.io.file.writealllines?view=netframework-4.7.2#System_IO_File_WriteAllLines_System_String_System_String___

If it isn't quite the format that you want, you could build a string in the loop instead of adding to a List, or you could store the information you want to save in a Serializable struct or class, and save the serialization to the file.

Quite a few choices. Let me know what you come up with!

dza6549 commented 5 years ago

Wow thanks @jesse-scam. Do you home deliver hot food to Australia as well? :)

I'm very much a newb and quite in the dark. Originally I thought the Timeline would be the way to approach this but as I've read a bit more about how things work in Unity I'm thinking I could process the samples and extract a number of "tracks" based on various properties and then feed those "tracks" into a procedural routine that animates various GameObjects in the scene. Sort of like number of differently EQ'd and effected sub-busses on an audio mixing deck. I think this might enable me to, for example, apply LocalScale to a number of different objects at different timings but still be "holistically" in time/visually synced with events in the audio track.

I'll give these ideas a shot and let you know.

Thanks again. Cheers