Saving AudioSample as a sound file of any format

please format code with </> button * homework policy * asking questions

Hello,

I am using the sound library to generate sound from existing .wav files. And after looking for a while for a way to save the generated sound to a file, I haven’t found any (simple) solution. It just surprises me that a library such as .sound that enables you to open and manipuate sound files so easily, does not include a save or export function. Am I missing something here? Is it that hard to create sound files?

Thanks for the help!

See previous forum post

1 Like

Thanks for the answer paulgoux.

I knew about minim and Audiorecorder, but it seems like it forces me to actually play the sound to record it which will take a lot of time. This is a problem because i am trying to take a few sound files and turn it into a new file that has the individual sounds with some time between. Since I need to do this thousands of times, having to play the sound before turning it into a file is not ideal. So I was hoping to find a way around it.

If I’m wrong about having to play a sound to record it, or if you know of a different solution please let me know.
Thanks!

Honestly not sure this isn’t a topic I’ve researched in depth just some quick googling however I have worked with fft analysis before to convert an audio file to a spectrogram and I had the same issue, analysis was only available during playback and resolution would be dependant on playback speed. This was using processing sound as opposed to minim, so I think it might be a processing limitation perhaps someone with more knowledge can enlighten us.

Thanks for trying anyway! I guess the code will just have to run for hours haha

i’m also looking for a way to save data directly to sound files.

found this post: https://forum.processing.org/two/discussion/4339/how-to-save-a-wav-file-using-audiosystem-and-audioinputstream-of-javasound

it uses byte array but only creates 8 bit wav files. any suggestions how the code could be modified to save 16 bit sound?

2 Likes

Hey! That post fixed my issue! Thanks!
In my case, quaity isn’t a big deal, so i won’t be trying to figure out the 16bit solution. But if you figure it out, please let me know

I have made changes to be able to generate a 16 bit wav file from a string containing a sequence of float values generated from a mono sound file.

import processing.sound.*;
import javax.sound.sampled.*;
import java.io.*;

processing.sound.AudioSample file;
float[] floatArray;
String[] txt;
byte[] pcm_data;

void setup(){
  // Load string containing float values
  txt = loadStrings("str.txt");
  
  // Create array to transform String to float
  floatArray = new float[txt.length];
  
  // Create pcm array for storing 16 bits values representing the floats
  // 16 bits = 2 bytes, also mono = 1 byte so 2 * 1 * txt.length
  pcm_data= new byte[2 * txt.length];
  
  for(int i = 0; i < txt.length; i++){
    // String to float
    floatArray[i] = float(txt[i]);
    // Convert float32 to 16 bit integer, values between -32768 and 32767 (since -1 < floatArray[i] < 1)
    int aux = floor(32767 * floatArray[i]);
    // 16 bits per iteration, so I need to generate and fill 2 separate bytes per iterarion
    // Convert first 8 bits (+ significant) of the 16 bit int to a byte
    pcm_data[i * 2] = byte(aux); 
    // Convert last 8 bits (- significant) of the 16 bit int to a byte
    pcm_data[(i* 2) + 1] = (byte)((int) aux >> 8);
  }
  
  // Preparing the save PCM ----------------------------
  // Define the AudioFormat to save
  AudioFormat frmt = new AudioFormat(44100, 16, 1, true, false); // Samplerate, Samplesize em Bits, channels, signed, bigendian
  // Buffer for recording the audio
  AudioInputStream ais = new AudioInputStream( 
    new ByteArrayInputStream(pcm_data), 
    frmt, 
    pcm_data.length / frmt.getFrameSize()
  );
  
  // Try to save the file in the current directory
  try {
    AudioSystem.write(ais, AudioFileFormat.Type.WAVE, new
      File(dataPath("") + "audio.wav")
    );
  } 
  catch(Exception e) {
    e.printStackTrace();
  }
  
  noLoop();
}

void draw(){

}