jump method

Future<bool> jump(
  1. int position
)

jump to song in the playlist

@param position - the new position (0-based)

Implementation

Future<bool> jump(int position) async {
  Completer<bool> completer = Completer<bool>();
  // reject the promise if mpv is not running
  if (!running) {
    throw _errorHandler.errorMessage(8, 'jump()');
  }
  // get the size of the playlist, to check if the desired position is within the playlist
  int size = await getPlaylistSize();
  if (position >= 0 && position < size) {
    // get the filename of the song that is being jumped to, for a better error message if it could
    // not be loaded
    String filename =
        await getProperty<String>("playlist/$position/filename");
    // continue the skipping process
    // get the next song in the playlist for possible error messages

    Socket observeSocket = await Socket.connect(
        InternetAddress(socketURI, type: InternetAddressType.unix), 0);

    await setProperty('playlist-pos', position);
    // timeout
    int timeout = 0;
    // check if the file was started
    bool started = false;

    observeSocket.listen((event) {
      timeout += 1;
      List<String> messages = utf8.decode(event).split('\n');
      // check every message
      for (var message in messages) {
        // ignore empty messages
        if (message.isNotEmpty) {
          Map msgMap = jsonDecode(message);
          if (msgMap.containsKey("event")) {
            if (msgMap["event"] == 'start-file') {
              started = true;
            }
            // when the file has successfully been loaded resolve the promise
            else if (msgMap["event"] == 'playback-restart' &&
                started &&
                !completer.isCompleted) {
              observeSocket.destroy();
              // resolve the promise
              completer.complete(true);
            }
            // when the track has changed we don't need a seek event
            else if (msgMap["event"] == 'end-file' && started) {
              observeSocket.destroy();
              // get the filename of the not playable song
              completer.completeError(_errorHandler
                  .errorMessage(0, 'changePlaylistPos()', args: [filename]));
            }
          }
        }
      }
      // reject the promise if it took to long until the playback-restart happens
      // to prevent having sockets listening forever
      if (timeout > 10) {
        observeSocket.destroy();
        completer.completeError(
            _errorHandler.errorMessage(5, 'changePlaylistPos()'));
      }
    });
  } else {
    if (!completer.isCompleted) completer.complete(false);
  }
  return completer.future;
}