Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/386.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 安卓-播放仍在下载的歌曲_Java_Android_Streaming_Android Mediaplayer_Exoplayer - Fatal编程技术网

Java 安卓-播放仍在下载的歌曲

Java 安卓-播放仍在下载的歌曲,java,android,streaming,android-mediaplayer,exoplayer,Java,Android,Streaming,Android Mediaplayer,Exoplayer,我正在创建一个应用程序,在这个应用程序中,多个设备可以在局域网中相互连接,并从彼此的设备播放歌曲 现在,当设备A从设备B请求歌曲时,B通过套接字将歌曲文件发送回A。歌曲下载完成后,A开始使用MediaPlayer播放歌曲 现在的问题是,即使在高速局域网上,也可能需要几秒钟的时间来完成歌曲的获取,因此在选择歌曲和开始播放歌曲之间存在明显的延迟 我想找到一种方法,在歌曲仍在下载时播放它。以下是我找到的一些可能的解决方案,但由于某些原因无法探索: 在MediaPlayer文档中,我注意到一个构造函数采

我正在创建一个应用程序,在这个应用程序中,多个设备可以在局域网中相互连接,并从彼此的设备播放歌曲

现在,当设备A从设备B请求歌曲时,B通过套接字将歌曲文件发送回A。歌曲下载完成后,A开始使用
MediaPlayer
播放歌曲

现在的问题是,即使在高速局域网上,也可能需要几秒钟的时间来完成歌曲的获取,因此在选择歌曲和开始播放歌曲之间存在明显的延迟

我想找到一种方法,在歌曲仍在下载时播放它。以下是我找到的一些可能的解决方案,但由于某些原因无法探索:

  • MediaPlayer
    文档中,我注意到一个构造函数采用了一个实现,允许我在MediaPlayer需要时手动返回媒体文件的一部分,这样我可以推迟返回一个字节,直到它完成下载(如果它还没有完成下载),有效地起到了“缓冲”的作用行动。这似乎是一个解决方案,但不幸的是,我的应用程序的minSdk设置为16,
    mediadasource
    仅适用于23岁及以上,所以我无法尝试

  • 一种选择是使用
    MediaPlayer
    setDataSource(FileDescriptor fd,long offset,long length)
    方法。这将允许我告诉MediaPlayer只播放歌曲的某个字节。这样,我可以等待文件的更多部分(或整个文件)变为可用,然后使用
    setNextMediaPlayer()
    传入一个新的MediaPlayer对象,该对象将准备整个歌曲,并使其搜索到上一个media player对象将停止播放的点,以便实现无缝过渡。 但这还有另一个问题。我需要能够计算在第一个不完整的媒体播放器对象的最后一个指定字节将达到的毫秒位置。否则,我就不知道为了实现无缝过渡,应该在什么位置寻找下一个媒体播放器对象。对于有损格式,这种计算似乎是不可能的

  • 我真的不知道这个选项是否有效,我只是在做假设。我注意到,
    setDataSource()
    接受一个Uri。如果该Uri指向手机上的文件,则媒体播放器仅加载整个文件。但是,如果Uri指向互联网上需要流式传输的音频文件,它会自己计算出来,并处理下载和缓冲的所有细节。所以我想知道的是,是否有可能将设备B上的歌曲作为Uri公开给设备a,以便媒体播放器将其视为互联网上的歌曲?一直以来,我都在使用套接字并手动将文件从一个设备复制到另一个设备,所以我不知道这将如何工作。有人能解释一下这是否可能吗

    事实上,我一直没有探索将歌曲从一台设备“流”到另一台设备的方法是有原因的。这是因为我想将歌曲缓存在设备B上,这样以后如果我切换到另一首歌曲,然后从设备A返回以前播放的歌曲,它就不必再次流式播放。它应该只播放缓存的副本

  • 最后,我遇到了
    ExoPlayer
    。它似乎提供了大量的定制。看起来我可以定制它的类来处理所有的缓冲。但是文档和示例很少,对我来说太复杂了。我不知道该怎么办。对于我想要实现的目标来说,这个解决方案是否过于复杂


  • 希望有人能在这里给我指出正确的方向。

    最后使用了下面的答案:

    此解决方案设置了一个本地服务器,MediaPlayer可以使用该服务器来传输文件。当这些字节可用时,服务器仅向MediaPlayer发送字节。否则,它将阻塞,直到有更多字节可用。因此,MediaPlayer将其缓冲,就好像它是来自web服务器的文件一样

    我选择了答案中提供的同一个课程,只是调整了它以适应我的情况