Android本地及网络音乐播放器-播放本地音乐(一)

news/2024/10/23 9:26:20/

 入职没多久,自学了一段时间的安卓基础知识,抱着巩固下基础以及学会对知识点的基本运用的初衷写了一个音乐播放器,因此用到的东西都是很基础的,功能什么的大部分都是按照自己的想法来实现的,如果看完感觉哪些地方写的不行或有好的建议欢迎给我留言.
  该Android音乐播放器代码量稍微有点多,这里我将以实现功能的顺序为参考将音乐播放器分为几篇博客发布.该播放器实现的主要功能如下(结尾将会附上源代码下载地址):
  
1.本地音乐的播放及控制;
2.音乐播放界面的展示;
3.在线音乐的搜索及展示(包含使用json解析数据);
4.在线音乐的试听及下载;
5.下载控制界面-下载歌曲的暂停/继续/删除(可以查看并删除已下载音乐);
6.播放界面歌手专辑图片及歌词的下载和显示;
7.歌词的滚动显示以及滑动歌词改变音乐进度的监听;
8.音乐的断点下载;
9.基于PopupWindow的弹出式菜单(支持透明度修改和自定义背景);
10.后台任务栏显示与控制音乐的播放;
本地音乐列表            
本地音乐列表
          
音乐播放界面            
音乐播放界面

搜索网络音乐            
搜索网络音乐

网络音乐的试听和下载             
网络音乐的试听和下载

音乐下载控制界面            
音乐下载控制界面

已下载音乐的查看和删除            
已下载音乐的查看和删除

播放界面专辑图片的加载            
播放界面专辑图片的加载

播放界面歌词的加载            
播放界面歌词的加载

基于popupwindow的menu            
基于popupwindow的menu

基于popupwindow的menu            
基于popupwindow的menu

基于popupwindow的menu            
基于popupwindow的menu

后台任务栏显示与控制播放            
后台任务栏显示与控制播放

下面讲述项目需要实现的第一步功能-本地音乐播放的实现
这里主要涉及三个类:
1.MainActivity.java 负责整个项目的业务控制,包括滑动切换Fragment,控制音乐播放,呼出菜单等;
2.MusicListFragment.java 第一个Fragment展示在用户面前,主要展示本地音乐提供给用户点击播放;
3.MusicService.java 负责后台运行播放MediaPlayer
主要业务代码如下:
1MainActivity.java

package com.example.comfortmusic_1;import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Random;import com.example.comfortmusic_1.fragment.DownloadFragment;
import com.example.comfortmusic_1.fragment.MusicListFragment;
import com.example.comfortmusic_1.fragment.NetFragment;
import com.example.comfortmusic_1.service.MusicService;import android.app.ActionBar;
import android.app.AlertDialog;
import android.app.ActionBar.Tab;
import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.SharedPreferences;
import android.database.Cursor;
import android.app.FragmentTransaction;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.provider.MediaStore;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentPagerAdapter;
import android.support.v4.app.NavUtils;
import android.support.v4.view.ViewPager;
import android.support.v4.view.ViewPager.OnPageChangeListener;
import android.text.method.ScrollingMovementMethod;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.GestureDetector;
import android.view.GestureDetector.OnGestureListener;
import android.view.Gravity;
import android.view.KeyEvent;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.MeasureSpec;
import android.view.View.OnClickListener;
import android.view.View.OnTouchListener;
import android.view.ViewGroup;
import android.view.ViewGroup.LayoutParams;
import android.view.WindowManager;
import android.view.animation.Animation;
import android.view.animation.TranslateAnimation;
import android.widget.ImageButton;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.PopupWindow;
import android.widget.RemoteViews;
import android.widget.SeekBar;
import android.widget.TextView;
import android.widget.Toast;public class MainActivity extends FragmentActivity implements MusicListFragment.Callbacks {public static boolean isPlaying = false;//全局变量,表征当前是否在播放/*** 当前播放音乐的信息*/public static int currentMusicPosition;public static String currentMusicTitle;public static String currentMusicArtist;public static String currentMusicDuration;  public static String currentMusicUrl;/*** 循环控制-CYCLE表示当前循环模式*/public static final int CYCLE_LIST = 1;public static final int CYCLE_RANDOM = 2;public static final int CYCLE_SINGLE = 3;public static int CYCLE = CYCLE_LIST;/*** 发送给MusicService的播放信息MSG:从头开始播放/暂停/继续播放/换歌*/public static final int MSG_PLAY = 0;public static final int MSG_PAUSE = 1;public static final int MSG_CONTINUEPLAYING = 2;public static final int MSG_CHANGESONG = 3;public static int MSG = MSG_PLAY;//屏幕的长度和宽度public static int screenWidth;public static int screenHeight;//上一首歌曲位置,用来判断是从头播放还是继续播放,若prePosition=currentMusicPosition则继续播放,反之从头播放public static int prePosition;//程序启动时获取音频数据库中的音乐信息并保存到dbMusic中public static List<Map<String, Object>> dbMusic = new ArrayList<Map<String, Object>>();public static String TAG = "MainActivity";//activity切换fragment的工具SectionsPagerAdapter mSectionsPagerAdapter;ViewPager mViewPager;ActionBar actionBar;//tv1, tv2, tv3分别显示三个fragment的标题TextView tv1, tv2, tv3, currentMusic;//三个fragment的标题下动态表征切换页面的红条,红条宽度-bottomLine=screenWidth/页面数LinearLayout bottomLine;int bottomLineWidth;//下方播放区域,音乐图标,上一曲,播放/暂停/下一曲LinearLayout playArea;ImageView playTag;ImageButton buttonPre, buttonPlayAndPause, buttonNext;//启动MusicService的intentIntent ServiceIntent = null;//当前页面/fragmentint currentItem = 0;@Overrideprotected void onCreate(Bundle savedInstanceState) {Toast.makeText(MainActivity.this, "CYCLE=" + CYCLE, 300).show();super.onCreate(savedInstanceState);setContentView(R.layout.main);actionBar = getActionBar();       actionBar.hide();mSectionsPagerAdapter = new SectionsPagerAdapter(getSupportFragmentManager());getScreenWidth();initTab();initView();       bottomLine = (LinearLayout) findViewById(R.id.bottomline);bottomLine.setX(bottomLineWidth);mViewPager = (ViewPager) findViewById(R.id.pager);mViewPager.setAdapter(mSectionsPagerAdapter);mViewPager.setOnPageChangeListener(new OnPageChangeListener() {@Overridepublic void onPageScrollStateChanged(int arg0) {            }@Overridepublic void onPageScrolled(int item, float percent, int offset) {bottomLine.setX(item * bottomLineWidth +  offset/3);}@Overridepublic void onPageSelected(int position) {currentItem = position;changeTabState(position);}           });mViewPager.setCurrentItem(0);registerMyReceiver();ServiceIntent = new Intent(this, MusicService.class);startService(ServiceIntent);}private void registerMyReceiver() {IntentFilter intentFilter = new IntentFilter();  intentFilter.addAction("action.nextsong");intentFilter.addAction("action.play"); intentFilter.addAction("action.pause"); intentFilter.addAction("action.pre"); intentFilter.addAction("action.next"); registerReceiver(completeReceiver, intentFilter);       }//获取屏幕的长度和高度private void getScreenWidth() {DisplayMetrics dm = new DisplayMetrics();this.getWindowManager().getDefaultDisplay().getMetrics(dm);screenWidth = dm.widthPixels;screenHeight = dm.heightPixels;bottomLineWidth = dm.widthPixels / (mSectionsPagerAdapter.getCount());}//标红当前fragment标题并添加监听点击即可跳转到对应fragmentprivate void initTab() {tv1 = (TextView) findViewById(R.id.tab1);tv1.setTextColor(Color.RED);tv2 = (TextView) findViewById(R.id.tab2);tv3 = (TextView) findViewById(R.id.tab3);tv1.setOnClickListener(new MyOnClickListener(0));tv2.setOnClickListener(new MyOnClickListener(1));tv3.setOnClickListener(new MyOnClickListener(2));       }public void initView() {playArea = (LinearLayout) findViewById(R.id.playarea);currentMusic = (TextView) findViewById(R.id.currentmusic);currentMusic.setTextColor(Color.RED);buttonPre = (ImageButton) findViewById(R.id.pre);buttonPlayAndPause = (ImageButton) findViewById(R.id.playandpause);buttonNext = (ImageButton) findViewById(R.id.next);playArea.setOnClickListener(new MyPlayListener());playArea.setPaddingRelative(0, 0, 0, 0);playTag = (ImageView)findViewById(R.id.playtag);buttonPre.setOnClickListener(new MyPlayListener());buttonPlayAndPause.setOnClickListener(new MyPlayListener());buttonNext.setOnClickListener(new MyPlayListener());getMusicFromDb();//开始默认将dbMusic中的第一首歌设置为当前歌曲if(dbMusic.size() != 0) {Map<String, Object> map = dbMusic.get(currentMusicPosition);currentMusicTitle = (String)map.get("title");currentMusicArtist = (String)map.get("artist");currentMusicUrl = (String)map.get("url");currentMusicDuration =(String)map.get("duration");currentMusic.setText(currentMusicTitle + "—" + currentMusicArtist);}}@Overridepublic boolean onCreateOptionsMenu(Menu menu) {Log.d(TAG, "onCreateOptionsMenu");getMenuInflater().inflate(R.menu.main, menu);return true;}public class SectionsPagerAdapter extends FragmentPagerAdapter {public SectionsPagerAdapter(FragmentManager fm) {super(fm);}@Overridepublic Fragment getItem(int position) {Fragment fragment = null;switch (position) {case 0:fragment = new MusicListFragment();break;case 1:fragment = new NetFragment();break;case 2:fragment = new DownloadFragment();break;}return fragment;}@Overridepublic int getCount() {return 3;}@Overridepublic CharSequence getPageTitle(int position) {Locale l = Locale.getDefault();switch (position) {case 0:return getString(R.string.title_section1).toUpperCase(l);//R.string.title_section1 = "本地音乐"case 1:return getString(R.string.title_section2).toUpperCase(l);//R.string.title_section1 = "网络音乐"case 2:return getString(R.string.title_section3).toUpperCase(l);//R.string.title_section1 = "下载列表"}return null;}}//从手机音乐数据库中提取音乐并保存到dbMusic中private void getMusicFromDb() {if (dbMusic.size() > 0) dbMusic.clear();//从sd卡读取歌曲Cursor musicCursor1 = this.getContentResolver().query(MediaStore.Audio.Media.EXTERNAL_CONTENT_URI,null, null, null, MediaStore.Audio.Media.DEFAULT_SORT_ORDER);getMusic(musicCursor1);//从手机内存中读取歌曲Cursor musicCursor2 = this.getContentResolver().query(MediaStore.Audio.Media.INTERNAL_CONTENT_URI,null, null, null, MediaStore.Audio.Media.DEFAULT_SORT_ORDER);getMusic(musicCursor2);}private void getMusic(Cursor musicCursor) {while (musicCursor.moveToNext()) {Map<String, Object> item = new HashMap<String, Object>();long id = musicCursor.getLong(musicCursor.getColumnIndex(MediaStore.Audio.Media._ID));String title = musicCursor.getString(musicCursor.getColumnIndex(MediaStore.Audio.Media.TITLE));String artist = musicCursor.getString(musicCursor.getColumnIndex(MediaStore.Audio.Media.ARTIST));if (artist != null && artist.equals("<unknown>")) {continue;}long duration = musicCursor.getLong(musicCursor.getColumnIndex(MediaStore.Audio.Media.DURATION));long size = musicCursor.getLong(musicCursor.getColumnIndex(MediaStore.Audio.Media.SIZE));String url = musicCursor.getString(musicCursor.getColumnIndex(MediaStore.Audio.Media.DATA));int isMusic = musicCursor.getInt(musicCursor.getColumnIndex(MediaStore.Audio.Media.IS_MUSIC));if (isMusic != 0) {item.put("id", id);item.put("title", title);item.put("artist", artist);item.put("duration", formatDuration(duration));item.put("size", size);item.put("url", url);Log.d("MainActivity", "MusicTitle = " + title);Log.d("MainActivity", "MusicArtist = " + artist);Log.d("MainActivity", "MusicUrl = " + url);dbMusic.add(item);}}}//将毫秒形式的音乐时长信息转化为00:00形式public static String formatDuration(long dur) {long totalSecond = dur / 1000;String minute = totalSecond / 60 + "";if (minute.length() < 2) minute = "0" + minute ;String second = totalSecond % 60 + "";if (second.length() < 2) second = "0" + second;return minute + ":" + second;}           //音乐控制按钮的监听private class MyPlayListener implements View.OnClickListener {@Overridepublic void onClick(View v) {int id = v.getId();switch (id) {case R.id.pre:pre();break;case R.id.playandpause:if (isPlaying) {pause();} else {play();}break;case R.id.next:next();break;case R.id.playarea:break;default:break;}}       }//通信后台MusicService更新播放信息public void notifyPlayService() {Log.d("MainActivity", "notifyPlayService");Toast.makeText(this, "notify play service" + "position = " + currentMusicPosition , 300).show();Log.d("MainActivity", "dbMusic.size() = " + dbMusic.size());if (dbMusic.size() == 0) return;Map<String, Object> map = dbMusic.get(currentMusicPosition);currentMusicTitle = (String)map.get("title");currentMusicArtist = (String)map.get("artist");currentMusicUrl = (String)map.get("url");Log.d("MainActivity", "url = " + currentMusicUrl);currentMusicDuration =(String)map.get("duration");Intent musicIntent = new Intent();musicIntent.setAction("action.changesong");this.sendBroadcast(musicIntent);    refreshPlayState();}//上一首public void pre() {Log.d("MainActivity", "pre");if (dbMusic.size() == 0) return;if (CYCLE == CYCLE_RANDOM) {currentMusicPosition = new Random().nextInt(dbMusic.size() - 1);}  else if (CYCLE == CYCLE_SINGLE|| CYCLE == CYCLE_LIST) {if (currentMusicPosition == 0) {currentMusicPosition = dbMusic.size() - 1;} else {currentMusicPosition--;}}isPlaying = true;MSG = MSG_PLAY;notifyPlayService();}//播放public void play() {Log.d("MainActivity", "play");if (prePosition != 0 && prePosition == currentMusicPosition) {MSG = MSG_CONTINUEPLAYING;} else {MSG = MSG_PLAY;}isPlaying = true;notifyPlayService();}//暂停public void pause() {Log.d("MainActivity", "pause");MSG = MSG_PAUSE;prePosition = currentMusicPosition;isPlaying = false;notifyPlayService();}//下一首public void next() {
Log.d("MainActivity", "next");if (dbMusic.size() == 0) return;if (CYCLE == CYCLE_RANDOM) {currentMusicPosition = new Random().nextInt(dbMusic.size() - 1);}  else if (CYCLE == CYCLE_SINGLE|| CYCLE == CYCLE_LIST) {if (currentMusicPosition == dbMusic.size() - 1) {currentMusicPosition = 0;} else {currentMusicPosition++;}}isPlaying = true;MSG = MSG_PLAY;notifyPlayService();}//接收到MusicService播放完之后的广播后自动播放下一首private void autoChangeSong() {Log.d("MainActivity", "autoChangeSong");Toast.makeText(MainActivity.this, "MainActivity_autoChangeSong_CYCLE = " + CYCLE, 300).show();if (CYCLE == CYCLE_RANDOM) {currentMusicPosition = new Random().nextInt(dbMusic.size() - 1);}  else if (CYCLE == CYCLE_LIST) {if (currentMusicPosition == dbMusic.size() - 1) {currentMusicPosition = 0;} else {currentMusicPosition++;}           }isPlaying = true;MSG = MSG_PLAY;notifyPlayService();}//更新播放界面状态public void refreshPlayState() {Log.d("MainActivity", "refreshPlayState");currentMusic.setText(currentMusicTitle + "—" + currentMusicArtist);currentMusic.requestFocus();currentMusic.setMovementMethod(ScrollingMovementMethod.getInstance());if (isPlaying) {buttonPlayAndPause.setImageResource(android.R.drawable.ic_media_pause);//animationTranslateAnimation animation= new TranslateAnimation(-playTag.getWidth()-currentMusic.getWidth(),-currentMusic.getWidth(),0,  0);animation.setDuration(10000);animation.setRepeatCount(Animation.INFINITE);animation.setRepeatMode(Animation.RESTART);
//          currentMusic.startAnimation(animation);} else {buttonPlayAndPause.setImageResource(android.R.drawable.ic_media_play);//clear animationcurrentMusic.clearAnimation();}}   //页面/fragment标题的监听类public class MyOnClickListener implements View.OnClickListener {int item;public MyOnClickListener(int item) {this.item = item;}@Overridepublic void onClick(View v) {mViewPager.setCurrentItem(item);changeTabState(item);currentItem = item;}}     //标红当前页面标题public void changeTabState(int item) {
//      Toast.makeText(this, "current item = " + currentItem, 300).show();switch (item) {case 0:tv1.setTextColor(Color.RED);tv2.setTextColor(Color.BLACK);tv3.setTextColor(Color.BLACK);break;case 1:tv2.setTextColor(Color.RED);tv3.setTextColor(Color.BLACK);tv1.setTextColor(Color.BLACK);          break;case 2:tv3.setTextColor(Color.RED);tv1.setTextColor(Color.BLACK);tv2.setTextColor(Color.BLACK);          break;}
//      Toast.makeText(this, "item = " + item, 300).show();}@Overridepublic void onItemSelected(Integer id) {//实现MusicListFragment的回调接口Log.d("MainActivity", "onItemSelected");Log.d("MainActivity", "item" + id + " clicked!");notifyPlayService();}//接受广播并改变播放状态private BroadcastReceiver completeReceiver = new BroadcastReceiver() {@Overridepublic void onReceive(Context context, Intent intent) {String action = intent.getAction();  if (action.equals("action.nextsong")) {  autoChangeSong();} else if (action.equals("action.pre")) {pre();} else if (action.equals("action.play")) {play();} else if (action.equals("action.pause")) {pause();} else if (action.equals("action.next")) {next();} else if (action.equals("action.exit")) {closeApplication();}}};@Overridepublic boolean onKeyDown(int keyCode, KeyEvent event) {//返回按键监听if (keyCode == KeyEvent.KEYCODE_BACK  && event.getAction() == KeyEvent.ACTION_DOWN) {           if (mViewPager.getCurrentItem() != 0) {mViewPager.setCurrentItem(mViewPager.getCurrentItem()-1);return false;} else {closeApplication();return false;} }  return super.onKeyDown(keyCode, event);}   private void closeApplication() {MainActivity.this.finish();}//转到手机桌面public void toHomeTable(){Intent intent = new Intent();intent.setAction("android.intent.action.MAIN");intent.addCategory("android.intent.category.HOME");startActivity(intent);}   @Overrideprotected void onStop() {Log.d("MainActivity", "onStop");super.onStop();}@Overrideprotected void onDestroy() {Log.d("MainActivity", "onStop");this.unregisterReceiver(completeReceiver);MainActivity.this.stopService(ServiceIntent);isPlaying = false;super.onDestroy();}@Overrideprotected void onRestart() {super.onRestart();}}

2.MusicListFragment.java

package com.example.comfortmusic_1.fragment;import java.util.Map;import com.example.comfortmusic_1.MainActivity;
import com.example.comfortmusic_1.R;import android.app.Activity;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.graphics.Color;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.util.Log;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemLongClickListener;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.AbsListView.LayoutParams;
import android.widget.AdapterView.OnItemClickListener;public class MusicListFragment extends Fragment {private Callbacks mCallbacks;public static ListView musicList;//音乐列表BaseAdapter musicListAdapter;//音乐列表适配器@Overridepublic void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);IntentFilter intentFilter = new IntentFilter();  intentFilter.addAction("action.refreshmusiclistFragment");this.getActivity().registerReceiver(refreshReceiver, intentFilter);}   @Overridepublic View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {View rootView = inflater.inflate(R.layout.musiclist_main, container, false);musicList = (ListView) rootView.findViewById(R.id.musiclist);musicListAdapter = getAdapter();musicList.setAdapter(musicListAdapter);musicList.setOnItemClickListener(new OnItemClickListener() {@Overridepublic void onItemClick(AdapterView<?> parent, View view, int position,long id) {//播放选中歌曲MainActivity.currentMusicPosition = position;MainActivity.isPlaying = true;MainActivity.MSG = MainActivity.MSG_PLAY;mCallbacks.onItemSelected(position);//回调实现Callbacks的MainActivity.onItemSelected(position);}           });musicList.setOnItemLongClickListener(new OnItemLongClickListener() {@Overridepublic boolean onItemLongClick(AdapterView<?> arg0, View arg1, int arg2, long arg3) {// TODO Auto-generated method stubreturn false;}});return rootView;}@Overridepublic void onAttach(Activity activity) {super.onAttach(activity);if (!(activity instanceof Callbacks)) {throw new IllegalStateException("activity 必须实现Callbacks接口!");}mCallbacks = (Callbacks)activity;}@Overridepublic void onDetach() {super.onDetach();mCallbacks = null;}public interface Callbacks {public void onItemSelected(Integer id); }public BaseAdapter getAdapter() {BaseAdapter adapter = new BaseAdapter() {@Overridepublic int getCount() {return MainActivity.dbMusic.size();}@Overridepublic Object getItem(int position) {return null;}@Overridepublic long getItemId(int position) {return position;}@Overridepublic View getView(int position, View view, ViewGroup parent) {Map<String, Object> item = MainActivity.dbMusic.get(position);LinearLayout line = new LinearLayout(MusicListFragment.this.getActivity());line.setOrientation(LinearLayout.VERTICAL);LinearLayout upLayout = new LinearLayout(MusicListFragment.this.getActivity());upLayout.setOrientation(LinearLayout.HORIZONTAL);ImageView musicTag = new ImageView(MusicListFragment.this.getActivity());musicTag.setImageResource(R.drawable.music);musicTag.setLayoutParams(new LayoutParams(80,80));TextView musicTitle = new TextView(MusicListFragment.this.getActivity());TextView musicArtist = new TextView(MusicListFragment.this.getActivity());TextView musicDuration = new TextView(MusicListFragment.this.getActivity());musicTitle.setText((String)item.get("title"));musicTitle.setWidth(MainActivity.screenWidth/2);musicTitle.setTextSize(18); musicTitle.setTextColor(Color.MAGENTA);musicTitle.setMaxLines(1);musicDuration.setText((String)item.get("duration"));musicDuration.setWidth(MainActivity.screenWidth/2);musicDuration.setGravity(Gravity.RIGHT);musicDuration.setTextColor(Color.MAGENTA);musicDuration.setPaddingRelative(0, 0, 50, 0);musicDuration.setMaxLines(1);musicArtist.setText((String)item.get("artist"));
//              musicArtist.setWidth(MainActivity.screenWidth/4);musicArtist.setMaxLines(1);
//              musicArtist.setTextColor(Color.argb(50, 255, 100, 0));musicArtist.setPaddingRelative(80, 0, 0, 0);    upLayout.addView(musicTag);upLayout.addView(musicTitle);upLayout.addView(musicDuration);line.addView(upLayout);line.addView(musicArtist);return line;}};return adapter;}           @Overridepublic void onDestroy() {super.onDestroy();this.getActivity().unregisterReceiver(refreshReceiver);}private BroadcastReceiver refreshReceiver = new BroadcastReceiver() {@Overridepublic void onReceive(Context context, Intent intent) {String action = intent.getAction();  if (action.equals("action.refreshmusiclistFragment"))  { Log.d("MusicListFragment", "receive refresh music list!");
//                  Toast.makeText(MusicListFragment.this.getActivity(), "receive update progress!", 200).show();musicList.setAdapter(getAdapter());}               }};}

3.MusicService.java

package com.example.comfortmusic_1.service;import java.io.IOException;
import java.util.Timer;
import java.util.TimerTask;import com.example.comfortmusic_1.MainActivity;import android.app.Service;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.media.MediaPlayer;
import android.media.MediaPlayer.OnCompletionListener;
import android.os.IBinder;
import android.util.Log;
import android.widget.Toast;public class MusicService extends Service {private MediaPlayer musicPlayer = new MediaPlayer();public static int musicPosition;private Timer timer;@Overridepublic IBinder onBind(Intent arg0) {return null;}@Overridepublic int onStartCommand(Intent intent, int flags, int startId) {Toast.makeText(this, "musicservice_onStartCommand",500).show();     Log.d("MusicService", "onStartCommand");return super.onStartCommand(intent, flags, startId);}   @Overridepublic void onCreate() {super.onCreate();Log.d("MusicService", "_onCreate");IntentFilter intentFilter = new IntentFilter();   intentFilter.addAction("action.changesong"); registerReceiver(updateReceiver, intentFilter);timer = new Timer();}//根据播放信息准备播放音乐private void prepareMusic(Intent intent) {Log.d("MusicService", "prepareMusic");if (MainActivity.MSG == MainActivity.MSG_PLAY ) {play();//从头开始播放一首歌} else if (MainActivity.MSG == MainActivity.MSG_PAUSE) {pause();//暂停播放当前歌曲} else if (MainActivity.MSG == MainActivity.MSG_CONTINUEPLAYING) {continuePlaying();//继续播放未完的歌曲}   }//继续播放private void continuePlaying() {Log.d("MusicService", "continuePlaying");musicPlayer.start();}//从头开始播放一首歌private  void play() {new Thread(new Runnable() {@Overridepublic void run() {if (musicPlayer.isPlaying()) {musicPlayer.stop();}try {musicPosition = 0;musicPlayer.reset();musicPlayer.setDataSource(MainActivity.currentMusicUrl);musicPlayer.prepare();musicPlayer.start();musicPlayer.setOnCompletionListener(new OnCompletionListener() {@Overridepublic void onCompletion(MediaPlayer arg0) {Intent completeIntent = new Intent();completeIntent.setAction("action.nextsong");  sendBroadcast(completeIntent);Log.d("MusicService", "sendBroadcast");}               });     } catch (IOException e) {e.printStackTrace();Toast.makeText(MusicService.this, "加载音乐失败,请检查网络链接!",500).show();} catch (Exception e) {e.printStackTrace();}}}).start();}//暂停播放private void pause() {Log.d("MusicService", "pause");musicPlayer.pause();musicPosition = musicPlayer.getCurrentPosition();timer.cancel();}@Overridepublic void onDestroy() {super.onDestroy();if (musicPlayer != null) {if (musicPlayer.isPlaying()) timer.cancel();musicPlayer.stop();musicPlayer.release();}this.unregisterReceiver(updateReceiver);}private BroadcastReceiver updateReceiver = new BroadcastReceiver() {@Overridepublic void onReceive(Context context, Intent intent) {String action = intent.getAction();  if (action.equals("action.changesong")) {prepareMusic(intent);}}};}

其中NetFragment和DownloadFragment只需继承Fragment即可看到程序运行效果
Android本地及网络音乐播放器源码下载


http://www.ppmy.cn/news/407457.html

相关文章

在线音乐播放项目——BY音乐

前言&#xff1a; 这是我的第一个 SSM 项目 —— BY 音乐&#xff0c;所涉及到的技术&#xff1a;Spring、SpringBoot、SpringMVC、MyBatis、BCrypt 加密、自定义拦截器、HTML、CSS、JavaScrip、jquery、ajax …… 如项目有问题 or 改进方案随时下方留言&#xff0c;感谢支持 &…

【蓝桥杯算法题】获取桌面图标名称和坐标

【蓝桥杯算法题】获取桌面图标名称和坐标 实现解释 实现 可以使用Python的第三方库pyautogui来获取桌面图标的名称和坐标。下面是一个示例代码&#xff1a; import pyautogui# 获取屏幕分辨率 screenWidth, screenHeight pyautogui.size()# 获取所有桌面图标的位置和名称 de…

FPGA基础知识-行为及建模

目录 学习目标 学习内容 1.结构化过程语句 2.过程赋值语句 3.时序控制 4.条件语句 5.多路分支语句 6.循环语句 7.顺序块和并行块 8.生成块 学习时间 学习产出 学习目标&#xff1a; 解释结构化过程always和initial在行为级建模中的重要性, 定义阻塞( blockin…

关于诺基亚60系列和symbian的基本问题

1. 什么是60系列平台&#xff1f;60系列平台是一个智能电话软件工具包&#xff0c;设备制造商可以通过授权在自己的智能电话硬件中使用这个平台。设备制造商可以使用标准的60系列软件&#xff0c;但一般情况下他们会提出需求来定制60系列软件。60系列完全使用图形化用户界面&am…

我一直用nokia的手机

nokia的活动 http://www.nokia6500.com.cn/show.php?id11127766

人工智能的历史、现在与未来

人工智能的历史、现在与未来 人工智能的历史和背景人工智能的主要内容人工智能产业发展参考文献 人工智能的历史和背景 18世纪末&#xff0c;第一次工业革命&#xff0c;蒸汽机、发动机的诞生推动了机械自动化&#xff1b; 19世纪末&#xff0c;第二次工业革命&#xff0c;内燃…

未来智能手机完全不需要动手 现在的手机弱爆了

作者&#xff1a;大宝 编辑&#xff1a;竹一 图片&#xff1a;网络 官网&#xff1a;iterduo.com 智能手机其实蹦跶不了几年了。 你现在可能依然会在大街上拿出手机&#xff0c;聊天也好、看新闻也罢&#xff0c;有些人就是为了给迎面而来的人看看自己的iPhone X&#xff0c;但…

NOKIA自己掌控的新的智能手机系统ASHA

Asha系统是由诺基亚公司2012年收购Smarterphone公司后投资研发智能操作系统&#xff0c;它有着智能机中更加出色的滑动触摸操作体验&#xff0c;以及Fastlane界面&#xff0c;还拥有类似以前MeeGo系统的N9上的滑动操作&#xff0c;诺基亚公司于2013年5月9日在印度发布了第一款A…