Skip to content

Instantly share code, notes, and snippets.

@kascote
Created November 7, 2024 22:59
Show Gist options
  • Save kascote/fe1421646cdb2da885bed75aab9b98fa to your computer and use it in GitHub Desktop.
Save kascote/fe1421646cdb2da885bed75aab9b98fa to your computer and use it in GitHub Desktop.
BufferedOutputStream for Dart -
// example code, take care
// https://github.com/dart-lang/sdk/issues/32874#issuecomment-1467905810
class BufferingIOSink implements IOSink {
static const int _defaultBufferSize = 2048;
final Sink<List<int>> _sink;
Uint8List _buffer;
// Current live bytes in buffer.
int _start = 0;
int _end = 0;
Encoding _encoding;
BufferingIOSink(Sink<List<int>> output, {Encoding? encoding, Uint8List? buffer, int? bufferSize})
: _sink = output,
_encoding = encoding ?? (output is IOSink ? output.encoding : utf8),
_buffer = buffer ?? Uint8List(bufferSize ?? _defaultBufferSize);
void _flushBuffer() {
if (_start >= _end) return;
_sink.add(Uint8List.sublistView(_buffer, _start, _end));
_start = _end;
var capacity = _buffer.length;
if ((capacity - _end) * 4 < capacity) { // Reallocate if less that 25% free after flush.
_buffer = Uint8List(capacity);
_start = _end = 0;
}
}
Future<void> flush() {
_flushBuffer();
var sink = _sink;
if (sink is IOSink) return sink.flush();
return Future.value(null);
}
void add(List<int> bytes) {
var totalCapacity = _buffer.length;
var capacity = totalCapacity - _end;
var bytesCursor = 0;
while (bytesCursor + capacity < bytes.length) {
_buffer.setRange(_end, totalCapacity, bytes, bytesCursor);
_bytesCursor += capacity;
_flushBuffer();
capacity = totalCapacity - _end;
}
_buffer.setRange(_end, _end + bytes.length - bytesCursor, bytes, bytesCursor);
}
// All the other methods.
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment