我陷入困境,我正在编写一个流媒体播放器应用程序。到目前为止,我已经完成了直到播放音频,方法是点击RecyclerView中的一个项目并在服务中播放音频。现在我希望从服务发送广播,其ID在后台播放,并在RecyclerView适配器中接收它,并将该id与列表中的id匹配,并更新该项目的背景。
简而言之,目标是将服务中播放的音乐的id与recylerview中的项目ID相匹配,并更改该项目的背景。
这些是我的后台服务代码:
public class AudioPlayerService extends Service implements
MediaPlayer.OnCompletionListener, MediaPlayer.OnPreparedListener,
MediaPlayer.OnErrorListener, MediaPlayer.OnInfoListener, MediaPlayer.OnBufferingUpdateListener, MediaPlayer.OnSeekCompleteListener {
MediaPlayer mediaPlayer = new MediaPlayer();
private final IBinder mBinder = new LocalBinder();
int currentId = 0;
AudioList currentAudio = null;
private NotificationManager notificationManager;
String source = null;
public static int uid = 0;
private Intent notifyIntent;
private TelephonyManager mTelephony;
private PhoneStateListener mStateListerner;
private boolean isPausedinCall = false;
private boolean isPrepared = false;
public static final String BROADCAST_BUFFER = "com.hussaindehgamwala.mumineendownloads.AudioPlayerService.broadcastbuffer";
public static final String BROADCAST_UPDATEAUDIO = "com.hussaindehgamwala.mumineendownloads.AudioPlayerService.broadcastAudio";
Intent bufferIntent;
Intent newaudioIntent;
public AudioPlayerService() {
}
@Override
public void onCreate() {
bufferIntent = new Intent(BROADCAST_BUFFER);
newaudioIntent = new Intent(BROADCAST_UPDATEAUDIO);
mediaPlayer.setOnBufferingUpdateListener(this);
mediaPlayer.setOnErrorListener(this);
mediaPlayer.setOnCompletionListener(this);
mediaPlayer.setOnInfoListener(this);
mediaPlayer.setOnPreparedListener(this);
mediaPlayer.setOnSeekCompleteListener(this);
mediaPlayer.reset();
}
@Override
public IBinder onBind(Intent intent) {
return mBinder;
}
@Override
public void onRebind(Intent intent) {
super.onRebind(intent);
}
@Override
public boolean onUnbind(Intent intent) {
return true;
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
PowerManager mgr = (PowerManager) getApplicationContext().getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wakeLock = mgr.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "MyWakeLock");
wakeLock.acquire();
mTelephony = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
mStateListerner = new PhoneStateListener() {
@Override
public void onCallStateChanged(int state, String incomingNumber) {
switch (state) {
case TelephonyManager.CALL_STATE_OFFHOOK:
case TelephonyManager.CALL_STATE_RINGING:
if (mediaPlayer.isPlaying()) {
mediaPlayer.pause();
isPausedinCall = true;
}
break;
case TelephonyManager.CALL_STATE_IDLE:
if (mediaPlayer != null) {
if (isPausedinCall) {
mediaPlayer.start();
isPausedinCall = false;
}
}
break;
}
}
};
mTelephony.listen(mStateListerner, PhoneStateListener.LISTEN_CALL_STATE);
return START_STICKY;
}
public void showNotification(AudioList audiolist) {
notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
notifyIntent = new Intent(getApplicationContext(), AudioPlayer.class);
NotificationCompat.Builder builder = new NotificationCompat.Builder(getApplicationContext());
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
// This intent is fired when notification is clicked
Intent intent = new Intent(getApplicationContext(), AudioPlayer.class);
PendingIntent pendingIntent = PendingIntent.getActivity(getApplicationContext(), 0, intent, 0);
// Set the intent that will fire when the user taps the notification.
builder.setContentIntent(pendingIntent);
builder.setSmallIcon(R.drawable.ic_play_arrow_24dp);
builder.setContentTitle(audiolist.getTitle());
builder.setContentText(audiolist.getAlbum());
builder.setOngoing(true);
builder.setTicker("Playing Audio");
notificationManager.notify(1, builder.build());
}
}
@Override
public void onDestroy() {
super.onDestroy();
if (mediaPlayer != null) {
if (mediaPlayer.isPlaying()) {
mediaPlayer.stop();
}
mediaPlayer.release();
}
if (mStateListerner != null) {
mTelephony.listen(mStateListerner, PhoneStateListener.LISTEN_NONE);
}
if (isPrepared()) {
notificationManager.cancel(1);
}
}
public String getTitle() {
AudioDB adb = new AudioDB(getApplicationContext());
AudioList m = adb.getSourcefromId(currentId);
return m.getTitle();
}
public void toggleMediaPlayer() {
if (mediaPlayer != null) {
if (mediaPlayer.isPlaying()) {
mediaPlayer.pause();
} else {
mediaPlayer.start();
}
}
}
public void prepareAsync(String source) {
mediaPlayer.reset();
if (!mediaPlayer.isPlaying()) {
try {
mediaPlayer.setDataSource(source);
sendBufferIntentBroadcast();
sendNewAudioSelectedBufferIntent();
mediaPlayer.prepareAsync();
isPrepared = true;
} catch (IllegalArgumentException | IllegalStateException | IOException e) {
e.printStackTrace();
stopSelf();
}
}
}
public void prepareMedia(String source) {
AudioDB audioDB = new AudioDB(getApplicationContext());
int AudioId = audioDB.getAudiobySource(source);
currentId = AudioId;
uid = currentId;
prepareAsync(source);
}
private void sendBufferIntentBroadcast() {
bufferIntent.putExtra("buffering", "1");
sendBroadcast(bufferIntent);
}
// Audio Update Title
public void sendNewAudioSelectedBufferIntent() {
newaudioIntent.putExtra("audioid", "" + currentId + "");
sendBroadcast(newaudioIntent);
}
private void sendCompleteBufferIntent() {
bufferIntent.putExtra("buffering", "0");
sendBroadcast(bufferIntent);
}
@Override
public void onBufferingUpdate(MediaPlayer mp, int percent) {
}
@Override
public void onCompletion(MediaPlayer mp) {
currentId = currentId + 1;
uid = currentId;
AudioDB d = new AudioDB(getApplicationContext());
currentAudio = d.getSourcefromId(currentId);
playNext();
}
public boolean isPrepared() {
if (isPrepared) {
return true;
} else {
return false;
}
}
private void playNext() {
AudioDB a = new AudioDB(getApplicationContext());
AudioList audio = a.getSourcefromId(currentId);
prepareAsync(audio.getSource());
}
@Override
public boolean onError(MediaPlayer mp, int what, int extra) {
return false;
}
@Override
public boolean onInfo(MediaPlayer mp, int what, int extra) {
return false;
}
@Override
public void onPrepared(MediaPlayer mp) {
sendCompleteBufferIntent();
playMedia();
}
private void playMedia() {
if (!mediaPlayer.isPlaying()) {
AudioDB d = new AudioDB(getApplicationContext());
AudioList audio = d.getSourcefromId(currentId);
showNotification(audio);
MainActivity activity = new MainActivity();
AudioPlayer audioact = new AudioPlayer();
activity.UpdateTitle(audio.getTitle(), audio.getAlbum());
audioact.UpdateTitle(audio.getTitle(), audio.getAlbum());
mediaPlayer.start();
}
}
public void upDateTitle() {
MainActivity activity = new MainActivity();
AudioPlayer audioact = new AudioPlayer();
AudioDB d = new AudioDB(getApplicationContext());
AudioList audio = d.getSourcefromId(currentId);
activity.UpdateTitle(audio.getTitle(), audio.getAlbum());
audioact.UpdateTitle(audio.getTitle(), audio.getAlbum());
}
public boolean isPlaying() {
if (mediaPlayer.isPlaying()) {
return true;
} else {
return false;
}
}
@Override
public void onSeekComplete(MediaPlayer mp) {
}
public class LocalBinder extends Binder {
public AudioPlayerService getService() {
// Return this instance of LocalService so clients can call public methods
return AudioPlayerService.this;
}
}
}
我的Recyclerview Adpater课程:
public class AudioAdapter extends RecyclerView.Adapter<AudioAdapter.ViewHolder> {
private ArrayList<AudioList> mDataset;
private Context mContext;
private AudioPlayerService audioPlayerService;
private boolean mBound = false;
private ServiceConnection mConnection;
private MainActivityFragment fragment;
public static String title1 = "";
private ArrayList<AudioList> mDataset1;
@Override
public void registerAdapterDataObserver(RecyclerView.AdapterDataObserver observer) {
super.registerAdapterDataObserver(observer);
}
public AudioAdapter() {
}
// Provide a reference to the views for each data item
// Complex data items may need more than one view per item, and
// you provide access to all the views for a data item in a view holder
public class ViewHolder extends RecyclerView.ViewHolder {
// each data item is just a string in this case
public TextView textView;
public LinearLayout linearLayout;
public ImageView imageView;
public ViewHolder(View v) {
super(v);
textView = (TextView) v.findViewById(R.id.textid);
imageView = (ImageView) v.findViewById(R.id.playImage);
linearLayout = (LinearLayout) v.findViewById(R.id.play);
}
}
public AudioAdapter(Context mContext, ArrayList<AudioList> myDataset, MainActivityFragment fragment) {
this.mDataset = myDataset;
this.mContext = mContext;
this.fragment = fragment;
}
// Create new views (invoked by the layout manager)
@Override
public AudioAdapter.ViewHolder onCreateViewHolder(ViewGroup parent,
int viewType) {
// create a new view
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.audio_list_item, parent, false);
// set the view's size, margins, paddings and layout parameters
ViewHolder vh = new ViewHolder(v);
return vh;
}
// Replace the contents of a view (invoked by the layout manager)
@Override
public void onBindViewHolder(final ViewHolder holder, final int position) {
// - get element from your dataset at this position
// - replace the contents of the view with that element
final AudioList item = mDataset.get(position);
holder.textView.setText(item.getTitle());
holder.linearLayout.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
CheckNetwork checkNetwork = new CheckNetwork(mContext);
boolean isConnected = checkNetwork.isConnectingToInternet();
if (isConnected) {
fragment.removenotConnected();
fragment.playAudio(item.getSource());
MainActivity activity = new MainActivity();
activity.ResetButtonandPlay();
} else {
fragment.showNotConntected();
}
}
});
}
// Return the size of your dataset (invoked by the layout manager)
@Override
public int getItemCount() {
return mDataset.size();
}
public AudioList removeItem(int position) {
final AudioList model = mDataset.remove(position);
notifyItemRemoved(position);
return model;
}
public void addItem(int position, AudioList model) {
mDataset.add(position, model);
notifyItemInserted(position);
}
public void moveItem(int fromPosition, int toPosition) {
final AudioList model = mDataset.remove(fromPosition);
mDataset.add(toPosition, model);
notifyItemMoved(fromPosition, toPosition);
}
public void setFilter(ArrayList<AudioList> countryModels) {
mDataset = new ArrayList<>();
mDataset.addAll(countryModels);
notifyDataSetChanged();
}
public class BroadCastReciver1 extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
}
}
需要解决方案:
These is my activity with recycler view
假设当前第3项正在后台服务中播放。 它应该通过更改其背景或文本颜色或播放图标来暂停图标突出显示,
注意:如果某人有Service Binder的解决方案,则可接受。 提前谢谢。
答案 0 :(得分:1)
例如,AudioList具有布尔变量mIsPlaying。所以需要改变
您可以将布尔变量mIsPlaying
添加到AudioList
中。因此设置AudioList.mIsPlaying true
,并在需要时重置它。并检查onBindViewHolder
中的mIsPlaying,如果是真的设置一个背景,则设置默认背景。
或者您可以在选择器中保存选定的AudioList
ID,并在onBindViewHolder
中检查ID是否等于并根据条件更改背景
@Override
public void onBindViewHolder(final ViewHolder holder, final int position) {
// - get element from your dataset at this position
// - replace the contents of the view with that element
final AudioList item = mDataset.get(position);
if (item.id == selecedId) {
holder.itemView.setBackgroundColor(Color.BLUE);
} else {
holder.itemView.setBackgroundColor(Color.GREEN);
}
holder.textView.setText(item.getTitle());
holder.linearLayout.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
CheckNetwork checkNetwork = new CheckNetwork(mContext);
boolean isConnected = checkNetwork.isConnectingToInternet();
if (isConnected) {
fragment.removenotConnected();
fragment.playAudio(item.getSource());
MainActivity activity = new MainActivity();
activity.ResetButtonandPlay();
} else {
fragment.showNotConntected();
}
}
});
}