Carpet

Carpet

2M Downloads

Support for reading arbitrary files

altrisi opened this issue ยท 1 comments

commented

There could be functions (after reading a file in a new mode, maybe custom, and getting its handle) to read values from the file by calls specified from the program. For example, readNext(file_handle, 'int') would read the next data as an int. Same for shorts, doubles, bytes, maybe their unsigned versions too, and of course, Strings (by bytes, like readNext(file_handle, 'string', 8)), and others if I've missed any, that I probably have. Those could be all converted into Scarpet's Values, no need to keep their specific types.

The endianness of the file should probably be specified somewhere too.

Maybe also a way to write custom files, by using functions very similar to the above ones, but that work the other way around.

Would require to be used with caution, since the file handles would need to be closed at some point to prevent leaking, but that's another point. May need to keep track of all file handles somewhere in case the app crashes or is unloaded, to make sure all handles are closed.

This would allow for Scarpet apps to read any arbitrary file, allowing some cool user-defined Scarpet libraries to load and interact with files without implementing code in every app, maybe even finding unexpected files being used in Scarpet.

Relates slightly to #599.

Example of how reading the metadata of a NBS v4 song could look like (written in the browser, overcomplicated example):

file = read_file('song.nbs','custom');

if(readNext(file, 'short') != 0), return("File is very outdated"));
if(readNext(file, 'byte') != 4), return("File is outdated"));

instrumentsCount = readNext(file, 'byte');
tickLength = readNext(file, 'short');
layerCount = readNext(file, 'short');

name = readNext(file, 'string', readNext(file, 'int') );
author = readNext(file, 'string', readNext(file, 'int') );
originalAuthor = readNext(file, 'string', readNext(file, 'int') );
description = readNext(file, 'string', readNext(file, 'int') );

tempo = readNext(file, 'short')/100;

close_file(file);

if(originalAuthor != '', 
  by = ' by '+originalAuthor+', ported by '+author;
,
  by = ' by '+author;
)

print('Loaded song '+name+by+', with a length of '+(tickLength/tempo)+' seconds.');
print(description);

Just a suggestion to allow defining any file from Scarpet itself instead of adding Java handlers for each. As always, discussable.

commented

well, it relates quite substantially to #599 since if we had support of array types, it could read binary files as byte arrays, then all the functions you just wrote could be one internally as interpreters of the byte data. Not sure if that's super necessary to build a complicated fileIO api if the assumption is that all read files would be small in size anyways.