简体   繁体   English

ExoPlayer,如何加载远程音频文件的更大部分

[英]ExoPlayer, how to load bigger parts of remote audio files

I'm using ExoPlayer 2 to play remote tracks.我正在使用 ExoPlayer 2 播放远程曲目。 By default the player loads tracks piece by piece (ie about 20 seconds, then other 20 seconds while the track is playing).默认情况下,播放器逐个加载曲目(即大约 20 秒,然后在曲目播放时加载其他 20 秒)。

Since tracks are loaded from a remote server, it happens that if connection goes down, the player is not able to load anymore.由于曲目是从远程服务器加载的,因此如果连接中断,播放器将无法再加载。 Is there a way to say to ExoPlayer to load bigger parts of the audio file (also the full track at once)?有没有办法让 ExoPlayer 加载音频文件的更大部分(也是一次完整的轨道)?

I tried to see around ExtractorMediaSource , DataSource.Factory and DefaultExtractorsFactory but I've found nothing to solve my problem.我试图查看ExtractorMediaSourceDataSource.FactoryDefaultExtractorsFactory但我找不到任何可以解决我的问题的方法。

val audioSource = ExtractorMediaSource(
        Uri.parse(videoUrl),
        mDataSourceFactory,    // DataSource.Factory
        mExtractor,    // DefaultExtractorsFactory
        null,
        null
)

mExoPlayer.prepare(audioSource)
mExoPlayer.playWhenReady = true

(it is Kotlin, but it seems to be understandable also by Java programmers) (它是 Kotlin,但 Java 程序员似乎也可以理解)

I've found the solution.我找到了解决方案。 Since I'm not finding other related questions, I'll answer to my question (I hope someone will need it in the future):由于我没有找到其他相关问题,我将回答我的问题(我希望将来有人需要它):

The right object to configure is the LoadControl passed to the ExoPlayerFactory when creating the ExoPlayer object:要配置的正确对象是在创建ExoPlayer对象时传递给ExoPlayerFactoryLoadControl

Original answer (deprecated):原始答案(已弃用):

val loadControl = DefaultLoadControl(
            DefaultAllocator(true, C.DEFAULT_BUFFER_SEGMENT_SIZE),
            5 * 60 * 1000, // this is it!
            10 * 60 * 1000,
            DefaultLoadControl.DEFAULT_BUFFER_FOR_PLAYBACK_MS.toLong(),
            DefaultLoadControl.DEFAULT_BUFFER_FOR_PLAYBACK_AFTER_REBUFFER_MS.toLong()
)
exoPlayer = ExoPlayerFactory.newSimpleInstance(this, trackSelector, loadControl)

The updated answer:更新的答案:

val bandwidthMeter = DefaultBandwidthMeter.Builder(context).build()
val trackSelectionFactory = AdaptiveTrackSelection.Factory()
val trackSelector = DefaultTrackSelector(trackSelectionFactory)

val loadControl = DefaultLoadControl.Builder()
        .setAllocator(DefaultAllocator(true, C.DEFAULT_BUFFER_SEGMENT_SIZE))
        .setBufferDurationsMs(
            5 * 60 * 1000, // this is it!
            10 * 60 * 1000,
            DefaultLoadControl.DEFAULT_BUFFER_FOR_PLAYBACK_MS,
            DefaultLoadControl.DEFAULT_BUFFER_FOR_PLAYBACK_AFTER_REBUFFER_MS
        )
        .setTargetBufferBytes(DefaultLoadControl.DEFAULT_TARGET_BUFFER_BYTES)
        .setPrioritizeTimeOverSizeThresholds(DefaultLoadControl.DEFAULT_PRIORITIZE_TIME_OVER_SIZE_THRESHOLDS)
        .createDefaultLoadControl()

exoPlayer = ExoPlayerFactory.newSimpleInstance(
        context,
        DefaultRenderersFactory(context),
        trackSelector,
        loadControl,
        null,
        bandwidthMeter)

The doc where it is explained.解释它的文档

Answer of @Massimo is correct but the way is deprecated @Massimo 的答案是正确的,但方法已被弃用

use something like this使用这样的东西

DefaultLoadControl.Builder()
            .setBufferDurationsMs(
                DefaultLoadControl.DEFAULT_MIN_BUFFER_MS, 
                30_000, 
                DefaultLoadControl.DEFAULT_BUFFER_FOR_PLAYBACK_MS,
                DefaultLoadControl.DEFAULT_BUFFER_FOR_PLAYBACK_AFTER_REBUFFER_MS
            )

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM