@Override
  protected void onStart() {
    super.onStart();

    mPlayerController = new AudioPlayerController();
    mPlayerController.registerCallback(mPlayerControllerCallbacks);
    mPlayerController.play(this, mAudioUri);
    mPlayerController.setLooping(false);
  }
 @Override
 public void onClick(View v) {
   PlaybackState playbackState = mPlayerController.getPlaybackState();
   switch (playbackState) {
     case PLAYBACK_STATE_PLAYING:
       mPlayerController.pause();
       break;
     case PLAYBACK_STATE_STOPPED:
     case PLAYBACK_STATE_PAUSED:
       mPlayerController.play();
       break;
     default:
       Log.d(TAG, "onClick with state " + playbackState);
       break;
   }
 }
 @Override
 protected void onDestroy() {
   super.onDestroy();
   stopSeekbarUpdate();
   mExecutorService.shutdown();
   mPlayerController.stop();
 }
  // LrcFragment callback ***************************************************
  @Override
  public void onLrcItemSelected(int lrcRow) {
    int milliseconds = mPlayerController.getCurrentPosition();
    milliseconds -=
        567; // startFullScreenPlayerActivity since human click the item has a little delay, maybe
             // 567ms.
    milliseconds = (milliseconds > 0) ? milliseconds : 0;
    int minutesPart = (milliseconds / 1000) / 60;
    int secondsPart = ((int) (milliseconds / 1000)) % 60;
    int msPart = milliseconds - (minutesPart * 60 + secondsPart) * 1000;
    msPart = msPart > 99 ? 99 : msPart;
    String timestampStr =
        String.format(Locale.US, "[%02d:%02d.%02d]", minutesPart, secondsPart, msPart);
    Log.d(TAG, "onLrcItemSelected: Lrc Row " + lrcRow + ":" + timestampStr);

    mLrcFragment.setTimestampStr(timestampStr);
  }
 @Override
 public void onStopTrackingTouch(SeekBar seekBar) {
   mPlayerController.seekToPosition(seekBar.getProgress());
   scheduleSeekbarUpdate();
 }