Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 73d344a6 authored by TreeHugger Robot's avatar TreeHugger Robot Committed by Android (Google) Code Review
Browse files

Merge "SessionPlaylistAgent: Handle setDataSource" into pi-dev

parents a1c392eb d8c3b38b
Loading
Loading
Loading
Loading
+63 −3
Original line number Diff line number Diff line
@@ -23,6 +23,7 @@ import android.media.DataSourceDesc;
import android.media.MediaItem2;
import android.media.MediaMetadata2;
import android.media.MediaPlayerBase;
import android.media.MediaPlayerBase.PlayerEventCallback;
import android.media.MediaPlaylistAgent;
import android.media.MediaSession2.OnDataSourceMissingHelper;
import android.util.ArrayMap;
@@ -47,8 +48,8 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {

    private final Object mLock = new Object();
    private final MediaSession2Impl mSessionImpl;
    private final MyPlayerEventCallback mPlayerCallback;

    // TODO: Set data sources properly into mPlayer (b/74090741)
    @GuardedBy("mLock")
    private MediaPlayerBase mPlayer;
    @GuardedBy("mLock")
@@ -69,6 +70,22 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
    @GuardedBy("mLock")
    private PlayItem mCurrent;

    // Called on session callback executor.
    private class MyPlayerEventCallback extends PlayerEventCallback {
        public void onCurrentDataSourceChanged(@NonNull MediaPlayerBase mpb,
                @Nullable DataSourceDesc dsd) {
            if (mPlayer != mpb) {
                return;
            }
            synchronized (mLock) {
                if (dsd == null && mCurrent != null) {
                    mCurrent = getNextValidPlayItemLocked(mCurrent.shuffledIdx, 1);
                    updateCurrentIfNeededLocked();
                }
            }
        }
    }

    private class PlayItem {
        int shuffledIdx;
        DataSourceDesc dsd;
@@ -127,14 +144,23 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
        }
        mSessionImpl = sessionImpl;
        mPlayer = player;
        mPlayerCallback = new MyPlayerEventCallback();
        mPlayer.registerPlayerEventCallback(mSessionImpl.getCallbackExecutor(), mPlayerCallback);
    }

    public void setPlayer(MediaPlayerBase player) {
    public void setPlayer(@NonNull MediaPlayerBase player) {
        if (player == null) {
            throw new IllegalArgumentException("player shouldn't be null");
        }
        synchronized (mLock) {
            if (player == mPlayer) {
                return;
            }
            mPlayer.unregisterPlayerEventCallback(mPlayerCallback);
            mPlayer = player;
            mPlayer.registerPlayerEventCallback(
                    mSessionImpl.getCallbackExecutor(), mPlayerCallback);
            updatePlayerDataSourceLocked();
        }
    }

@@ -172,6 +198,7 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {

            mMetadata = metadata;
            mCurrent = getNextValidPlayItemLocked(END_OF_PLAYLIST, 1);
            updatePlayerDataSourceLocked();
        }
        notifyPlaylistChanged();
    }
@@ -210,6 +237,7 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
            }
            if (!hasValidItem()) {
                mCurrent = getNextValidPlayItemLocked(END_OF_PLAYLIST, 1);
                updatePlayerDataSourceLocked();
            } else {
                updateCurrentIfNeededLocked();
            }
@@ -249,6 +277,7 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
            mPlaylist.set(index, item);
            if (!hasValidItem()) {
                mCurrent = getNextValidPlayItemLocked(END_OF_PLAYLIST, 1);
                updatePlayerDataSourceLocked();
            } else {
                updateCurrentIfNeededLocked();
            }
@@ -291,7 +320,7 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
    @Override
    public void skipToNextItem() {
        synchronized (mLock) {
            if (!hasValidItem()) {
            if (!hasValidItem() || mCurrent == mEopPlayItem) {
                return;
            }
            PlayItem next = getNextValidPlayItemLocked(mCurrent.shuffledIdx, 1);
@@ -318,6 +347,23 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
                return;
            }
            mRepeatMode = repeatMode;
            switch (repeatMode) {
                case MediaPlaylistAgent.REPEAT_MODE_ONE:
                    if (mCurrent != null && mCurrent != mEopPlayItem) {
                        mPlayer.loopCurrent(true);
                    }
                    break;
                case MediaPlaylistAgent.REPEAT_MODE_ALL:
                case MediaPlaylistAgent.REPEAT_MODE_GROUP:
                    if (mCurrent == mEopPlayItem) {
                        mCurrent = getNextValidPlayItemLocked(END_OF_PLAYLIST, 1);
                        updatePlayerDataSourceLocked();
                    }
                    // pass through
                case MediaPlaylistAgent.REPEAT_MODE_NONE:
                    mPlayer.loopCurrent(false);
                    break;
            }
        }
        notifyRepeatModeChanged();
    }
@@ -339,6 +385,7 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
            }
            mShuffleMode = shuffleMode;
            applyShuffleModeLocked();
            updateCurrentIfNeededLocked();
        }
        notifyShuffleModeChanged();
    }
@@ -373,6 +420,7 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
        return dsd;
    }

    // TODO: consider to call updateCurrentIfNeededLocked inside (b/74090741)
    private PlayItem getNextValidPlayItemLocked(int curShuffledIdx, int direction) {
        int size = mPlaylist.size();
        if (curShuffledIdx == END_OF_PLAYLIST) {
@@ -414,9 +462,21 @@ public class SessionPlaylistAgent extends MediaPlaylistAgent {
                mCurrent = getNextValidPlayItemLocked(mCurrent.shuffledIdx, 1);
            }
        }
        updatePlayerDataSourceLocked();
        return;
    }

    private void updatePlayerDataSourceLocked() {
        if (mCurrent == null || mCurrent == mEopPlayItem) {
            return;
        }
        if (mPlayer.getCurrentDataSource() != mCurrent.dsd) {
            mPlayer.setDataSource(mCurrent.dsd);
            mPlayer.loopCurrent(mRepeatMode == MediaPlaylistAgent.REPEAT_MODE_ONE);
        }
        // TODO: Call setNextDataSource (b/74090741)
    }

    private void applyShuffleModeLocked() {
        mShuffledList.clear();
        mShuffledList.addAll(mPlaylist);
+36 −0
Original line number Diff line number Diff line
@@ -24,6 +24,7 @@ import android.media.DataSourceDesc;
import android.media.MediaItem2;
import android.media.MediaMetadata2;
import android.media.MediaPlayerBase;
import android.media.MediaPlayerBase.PlayerEventCallback;
import android.media.MediaPlaylistAgent;
import android.media.MediaSession2;
import android.media.MediaSession2.OnDataSourceMissingHelper;
@@ -35,6 +36,7 @@ import android.test.AndroidTestCase;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.mockito.Matchers;

import java.util.ArrayList;
import java.util.List;
@@ -56,6 +58,7 @@ public class SessionPlaylistAgentTest extends AndroidTestCase {
    private Context mContext;
    private MediaSession2Impl mSessionImpl;
    private MediaPlayerBase mPlayer;
    private PlayerEventCallback mPlayerEventCallback;
    private SessionPlaylistAgent mAgent;
    private OnDataSourceMissingHelper mDataSourceHelper;
    private MyPlaylistEventCallback mEventCallback;
@@ -229,6 +232,12 @@ public class SessionPlaylistAgentTest extends AndroidTestCase {
        };

        mPlayer = mock(MockPlayer.class);
        doAnswer(invocation -> {
            Object[] args = invocation.getArguments();
            mPlayerEventCallback = (PlayerEventCallback) args[1];
            return null;
        }).when(mPlayer).registerPlayerEventCallback(Matchers.any(), Matchers.any());

        mSessionImpl = mock(MediaSession2Impl.class);
        mDataSourceHelper = new MyDataSourceHelper();
        mAgent = new SessionPlaylistAgent(mContext, mSessionImpl, mPlayer);
@@ -567,6 +576,33 @@ public class SessionPlaylistAgentTest extends AndroidTestCase {
        assertEquals(SessionPlaylistAgent.END_OF_PLAYLIST, mAgent.getCurShuffledIndex());
    }

    @Test
    public void testPlaylistAfterOnCurrentDataSourceChanged() throws Exception {
        int listSize = 2;
        verify(mPlayer).registerPlayerEventCallback(Matchers.any(), Matchers.any());

        createAndSetPlaylist(listSize);
        assertEquals(0, mAgent.getCurShuffledIndex());

        mPlayerEventCallback.onCurrentDataSourceChanged(mPlayer, null);
        assertEquals(1, mAgent.getCurShuffledIndex());
        mPlayerEventCallback.onCurrentDataSourceChanged(mPlayer, null);
        assertEquals(SessionPlaylistAgent.END_OF_PLAYLIST, mAgent.getCurShuffledIndex());

        mAgent.skipToNextItem();
        assertEquals(SessionPlaylistAgent.END_OF_PLAYLIST, mAgent.getCurShuffledIndex());

        mAgent.setRepeatMode(MediaPlaylistAgent.REPEAT_MODE_ONE);
        assertEquals(SessionPlaylistAgent.END_OF_PLAYLIST, mAgent.getCurShuffledIndex());

        mAgent.setRepeatMode(MediaPlaylistAgent.REPEAT_MODE_ALL);
        assertEquals(0, mAgent.getCurShuffledIndex());
        mPlayerEventCallback.onCurrentDataSourceChanged(mPlayer, null);
        assertEquals(1, mAgent.getCurShuffledIndex());
        mPlayerEventCallback.onCurrentDataSourceChanged(mPlayer, null);
        assertEquals(0, mAgent.getCurShuffledIndex());
    }

    private List<MediaItem2> createAndSetPlaylist(int listSize) throws Exception {
        List<MediaItem2> items = new ArrayList<>();
        for (int i = 0; i < listSize; ++i) {