Lumen help

Legacy Integration for VOPlayer on Android

Project setup

                repositories {
    maven {
        url 'https://sdk.streamroot.io/android'
    }
}
            
                implementation 'io.streamroot.dna:dna-core:3.23.0'
            
                android {
// Configure only for each module that uses Java 8
// language features (either in its source code or
// through dependencies).
compileOptions {
      sourceCompatibility JavaVersion.VERSION_1_8
      targetCompatibility JavaVersion.VERSION_1_8
  }
}

            

Integrate Lumen SDK

                <meta-data
        android:name="io.streamroot.dna.StreamrootKey"
        android:value="streamrootKey"/>

            
                private DnaClient initStreamroot(VOPlayer voMediaPlayer) {
    DnaClient dnaClient = null
    
    try {
        dnaClient = DnaClient.newBuilder()
            .context(applicationContext)
            .playerInteractor(new VOPlayerInteractor(voMediaPlayer, mLatencyPerChunkCount))
            .start(mMediaUri)
    } catch (e: Exception) {
        Toast.makeText(applicationContext, e.message, Toast.LENGTH_LONG).show()
    }

    return dnaClient
}
            
                dnaClient.getManifestUrl() : <Uri>
            
                import android.os.Looper;
import com.viaccessorca.voplayer.VOPlayer;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import io.streamroot.dna.core.PlayerInteractor;
import io.streamroot.dna.core.TimeRange;

public final class VOPlayerInteractor implements PlayerInteractor {
    private final VOPlayer mPlayer;

    private final int mBufferTarget;

    public VOPlayerInteractor(final VOPlayer player, int latencyPerChunkCount) {
        mPlayer = player;

        mBufferTarget = getBufferTarget(
                VOPlayer.AbrControls.ABR_CONTROLS_MAX_BUFFER_LEVEL_MIN,
                VOPlayer.AbrControls.ABR_CONTROLS_MAX_BUFFER_LEVEL_MAX
        );

        if (latencyPerChunkCount > 0) {
            customizeLatency(latencyPerChunkCount);
        }
        customizeBufferTarget();
    }

    @NotNull
    @Override
    public List<TimeRange> loadedTimeRanges() {
        return new ArrayList<TimeRange>() {{
            add(new TimeRange(
                    mPlayer.getCurrentPositionAbsolute(),
                    mPlayer.getCurrentBufferLevel()));
        }};
    }

    @Nullable
    @Override
    public Looper looper() {
        return Looper.getMainLooper();
    }

    @Override
    public long playbackTime() {
        return mPlayer.getCurrentPositionAbsolute();
    }

    @Override
    public double bufferTarget() {
        return mBufferTarget;
    }

    @Override
    public void setBufferTarget(double v) {
    }

    private int getBufferTarget(int min, int max) {
        return (int) (Math.random() * (max - min) + min);
    }

    private void customizeLatency(int latencyInChunkCount) {
        HashMap<String, Object> customization = new HashMap<>();

        customization.put(VOPlayer.CustomMode.LIVE_LATENCY, latencyInChunkCount);
        mPlayer.setCustomMode(customization);
    }

    private void customizeBufferTarget() {
        VOPlayer.AbrControls abrControls = new VOPlayer.AbrControls();

        abrControls.m_iMaxBufferValue = mBufferTarget;
        mPlayer.setHttpStreamingAbrControlSettings(abrControls);
    }
}
 
            
                import com.viaccessorca.voplayer.VOPlayer;
import io.streamroot.dna.core.BandwidthListener;

public final class VOBandwidthListener implements BandwidthListener {
    private final VOPlayer mPlayer;

    public VOBandwidthListener(final VOPlayer player) {
        mPlayer = player;
    }

    @Override
    public void onBandwidthChange(long l) {
        mPlayer.setHttpStreamingMaximumBitrate((int) l);
    }
}

            
                DnaClient dnaClient = DnaClient.newBuilder()
     .context(<Context>)
     .playerInteractor(new VOPlayerInteractor(voMediaPlayer, mLatencyPerChunkCount))
     ...

     .bandwidthListener(new VOBandwidthListener(voMediaPlayer))

     ...
     .start(<URI>);
            
                import com.viaccessorca.voplayer.VOPlayer;
import io.streamroot.dna.core.PlaybackState;
import io.streamroot.dna.core.QosModule;

public final class VOQoSModule extends QosModule implements
        VOPlayer.OnBufferingUpdateListener,
        VOPlayer.OnCompletionListener,
        VOPlayer.OnSeekCompleteListener,
        VOPlayer.OnErrorListener,
        VOPlayer.OnInfoListener {

    public VOQoSModule(final VOPlayer player) {
        player.setOnBufferingUpdateListener(this);
        player.setOnCompletionListener(this);
        player.setOnSeekCompleteListener(this);
        player.setOnErrorListener(this);
        player.setOnInfoListener(this);
    }

    @Override
    public void onBufferingUpdate(VOPlayer voPlayer, int i) {
        if (i == 100) {
            if (voPlayer.isPlaying()) {
                playbackStateChange(PlaybackState.PLAYING);
            } else {
                playbackStateChange(PlaybackState.PAUSING);
            }
        } else {
            playbackStateChange(PlaybackState.BUFFERING);
        }
    }

    @Override
    public void onCompletion(VOPlayer voPlayer) {
        playbackStateChange(PlaybackState.ENDED);
    }

    @Override
    public void onSeekComplete(VOPlayer voPlayer) {
        playbackStateChange(PlaybackState.SEEKING);
    }

    @Override
    public boolean onError(VOPlayer voPlayer, int i, int i1) {
        playbackErrorOccurred();
        return true;
    }

    @Override
    public boolean onInfo(VOPlayer voPlayer, int what, int extra) {
        if (what == VOPlayer.MEDIA_INFO_HTTP_STREAMING && VOPlayer.MEDIA_INFO_ALTERNATE_CHANGE == extra) {
            trackSwitchOccurred();
        }

        return false;
    }
}

            
                DnaClient dnaClient = DnaClient.newBuilder()
     .context(<Context>)
     .playerInteractor(new VOPlayerInteractor(voMediaPlayer, mLatencyPerChunkCount))
     ...

     .qosModule(new VOQoSModule(voMediaPlayer))
     ...
     .start(<URI>);
            
                dnaClient.close();
            
                <?xml version="1.0" encoding="utf-8"?>
<manifest ...>
    <application
        ...
        android:usesCleartextTraffic="true">
        ...
    </application>
</manifest>
            
                <?xml version="1.0" encoding="utf-8"?>
<network-security-config>
    <domain-config cleartextTrafficPermitted="true">
        <domain includeSubdomains="true">localhost</domain>
    </domain-config>
</network-security-config>
            
                <?xml version="1.0" encoding="utf-8"?>
<manifest ...>
    <application
        ...
        android:networkSecurityConfig="@xml/network_security_config">
        ...
    </application>
</manifest>