Skip to content

Instantly share code, notes, and snippets.

@fabiancrx
Created January 19, 2024 17:46
Show Gist options
  • Save fabiancrx/28faec18a131c470e22271c54153dbdd to your computer and use it in GitHub Desktop.
Save fabiancrx/28faec18a131c470e22271c54153dbdd to your computer and use it in GitHub Desktop.
Stream POC
import 'dart:async';
import 'package:rxdart/rxdart.dart';
void main() async {
final fakeAdapter = FakeBluetoothAdapter();
final sub = fakeAdapter
.availableDevices()
.listen(print);
// scan needs to be called if not no readings will be emitted
fakeAdapter.scan();
await Future.delayed(const Duration(seconds: 6));
print('Starting second scan');
fakeAdapter.scan();
// Does not drop the initial 500ms of readings
await Future.delayed(const Duration(seconds: 6))
.then((value) => sub.cancel());
}
// Simulates a bluetooth adapter.
class FakeBluetoothAdapter {
final BehaviorSubject<List<int>> deviceIds = BehaviorSubject.seeded([]);
// Emits device id readings for the [duration] of the scan
Future<void> scan({Duration duration = const Duration(seconds: 5)}) async {
lastScanStartTime = DateTime.now();
final timer = Timer.periodic(const Duration(milliseconds: 50), (timer) {
final timePassedSinceScanStarted =
DateTime.now().difference(lastScanStartTime).inMilliseconds;
//simulate device readings
final reading = switch (timePassedSinceScanStarted) {
< 200 => [1],
>= 200 && < 300 => [1, 12],
>= 400 && < 500 => [1, 12, 8],
_ => [1, 12, 8, 27],
};
deviceIds.add(reading);
});
//Stop emitting values
await Future.delayed(duration).then((value) => timer.cancel());
print('Scanning stopped');
}
var lastScanStartTime = DateTime.now();
// amount of time we discard new readings on a new scan
static const _newScanSkpTime = Duration(seconds: 1);
Duration skipDuration() {
var diff = DateTime.now().difference(lastScanStartTime);
var hasEnoughTimePassed = diff > _newScanSkpTime;
final ret = hasEnoughTimePassed ? Duration.zero : diff;
return ret;
}
bool _afterSkipTime() {
return skipDuration() > Duration.zero;
}
Stream<String> availableDevices() async* {
final myDevicesStream = deviceIds.skipWhile((_) => _afterSkipTime()).map(
(results) =>
"${DateTime.now().difference(lastScanStartTime).inMilliseconds} ms => $results");
scan();
yield* myDevicesStream;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment