Writing content of a buffer to a text file

How can I write the content of a buffer into a text file on disk? And on the contrary I also want to write floats from a text file into a buffer, to play it back e.g. with PlayBuf

Use something like loadToFloatArray then write the numbers to a file as a string.

I did the following:

(
b = Buffer.readChannel(s, "/home/xxx/Desktop/pause.wav", channels: [0]);
b.loadToFloatArray(action: {arg arr; ~arr2 = Array.newFrom(arr)});
b.free
)

and then tried to write ~arr2 to a file:

~file = File("/tmp/arr.txt", "w");
~file.write(~arr2);

But the ~file.write line throws this error:

ERROR: Primitive ‘_FileWrite’ failed.
Wrong type.
RECEIVER:
Instance of File { (0x7f8a9b7c4bf8, gc=B0, fmt=00, flg=00, set=02)
instance variables [1]
fileptr : RawPointer 0x5592faa3af50
}
CALL STACK:
MethodError:reportError
arg this =
Nil:handleError
arg this = nil
arg error =
Thread:handleError
arg this =
arg error =
Object:throw
arg this =
Object:primitiveFailed
arg this =
Interpreter:interpretPrintCmdLine
arg this =
var res = nil
var func =
var code = “~file.write(~arr2.asFlatArray);”
var doc = nil
var ideClass =
Process:interpretPrintCmdLine
arg this =
^^ The preceding error dump is for ERROR: Primitive ‘_FileWrite’ failed.
Wrong type.
RECEIVER: a File

You should free after you create the array, putting code after b.loadToFloatArray will mean it is executed before the action not after it (supercollider’s asynchronous code is rather confusing in this way). Move the free into the action.

(
b = Buffer.readChannel(s, "/home/xxx/Desktop/pause.wav", channels: [0]);
b.loadToFloatArray(action: { |arr| 
	~arr2 = Array.newFrom(arr);
	b.free;
});
)

Then you should look at the documentation for File.write

.write(item)
Writes an item to the file.

Arguments: item
one of the following:

Float
Integer
Char
Color
Symbol
   writes the name of the Symbol as a C string.
RawArray
   write the bytes from any RawArray in big endian.

An Array of Floats isn’t an accepted type. You could turn the array into a FloatArray or a String.

A question: How do you need the file to be formatted? Tab-delimited, comma-separated, one float per line? If multichannel, what do you want it to look like?

Then you can iterate over the array accordingly, e.g., one float per line would be:

f = File(path, "w");
protect {
    ~arr2.do { |item|
        f <<< item << "\n";
    };
} {
    f.close
};

hjh

2 Likes