2008/06/26/01.02.53

A Ruby readline-like method for AS3

I’ve missed the readline method from Ruby, so here’s a stab at a readline that returns an array of all the lines you might want from a given file.

These examples of using this method assume some var f in scope that might look like:

var f : File = File.applicationDirectory.resolvePath("temp.txt");

You’d call this method in one of several ways. The simplest would return an array of all the lines in a file.

var lines : Array = readLines( f );

The rest of the examples assume some var r in scope that might look like:

var r : RegExp = new RegExp(/enabled/);

A slightly more complex way would use the filter property to select specific lines out of the file. In this case, lines that returned true for the regex /enabled/.

var lines : Array = readLines( f, r );

You could also flip the filter_accepts parameter to false, and get an array of all the lines that don’t match the regex.

var lines : Array = readLines( f, r, false );

Finally, you could find the first line, after skipping the first two lines, that didn’t match the regex.

var lines : Array = readLines( f, r, false, 1, 2 );

So, after all those wonderfully fun samples, here’s the code:

/**
 * @param … If you supply one extra param it’ll be the number of lines possible.
 *              If you supply two extra params the first’ll be the same and the second’ll be an offset by lines.
 *              Anything past the first two params is ignored.
 */
private function readLines( f : File, line_filter : RegExp = null, filter_accepts : Boolean = true, … params ) : Array {
    var line_offset : Number;
    var lines_possible : Number;
    switch( params.length ){
        case 0:     lines_possible = Number.MAX_VALUE;  line_offset = 0;            break;
        case 1:     lines_possible = params[0];         line_offset = 0;            break;
        default:    lines_possible = params[0];         line_offset = params[1];
    }
    var total_lines_to_be_seen : Number = line_offset + lines_possible;
    var lines : Array = [];
    if( f.size > 0 ){
        var fileStream : FileStream = new FileStream();
        fileStream.open( f, FileMode.READ );
        var char : String;
        var line : String;
        var lines_seen : Number = 0;
        // Read either to the EOF or until we have enough lines
        while( fileStream.bytesAvailable > 0 && lines_seen < total_lines_to_be_seen ){
            line = "";
            char = fileStream.readUTFBytes(1);
            // Keep adding to the line until an EOL
            while( !(char == File.lineEnding) ){
                line += char;
                char = fileStream.readUTFBytes(1);
            }
            // If we’ve hit an EOL and we’re past the offset, then see if it passes the filter.
            if( lines_seen >= line_offset ){
                if( line_filter == null ){
                    lines.push(line);
                }else{
                    if( line_filter.test(line) == filter_accepts ){
                        lines.push(line);
                    }else{
                        lines_seen -= 1;
                    }
                }
            }
            lines_seen += 1;
        }
        fileStream.close();
    }
    return lines;
}

Original post by richard.lyman and software by Elliott Back

Comments are closed.