diff --git a/.idea/inspectionProfiles/Project_Default.xml b/.idea/inspectionProfiles/Project_Default.xml new file mode 100644 index 0000000..7373961 --- /dev/null +++ b/.idea/inspectionProfiles/Project_Default.xml @@ -0,0 +1,8 @@ + + + + \ No newline at end of file diff --git a/app/src/main/java/com/example/musicplayer/adapter/AlbumSongAdapter.java b/app/src/main/java/com/example/musicplayer/adapter/AlbumSongAdapter.java index 6b2628d..392686d 100644 --- a/app/src/main/java/com/example/musicplayer/adapter/AlbumSongAdapter.java +++ b/app/src/main/java/com/example/musicplayer/adapter/AlbumSongAdapter.java @@ -12,7 +12,7 @@ import com.example.musicplayer.R; import com.example.musicplayer.callback.OnItemClickListener; import com.example.musicplayer.app.App; import com.example.musicplayer.entiy.AlbumSong; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import java.util.List; @@ -66,7 +66,7 @@ public class AlbumSongAdapter extends RecyclerView.Adapter { holder.songNameTv.setText(mp3Info.getName()); holder.artistTv.setText(mp3Info.getSinger()); //根据播放的歌曲是否为当前列表的歌曲显示 - if(mp3Info.getSongId().equals(FileHelper.getSong().getSongId())){ + String songId = Objects.requireNonNull(FileUtil.getSong()).getSongId(); + if(songId!=null&&(mp3Info.getSongId().equals(songId))){ holder.songNameTv.setTextColor(App.getContext(). getResources().getColor(R.color.musicStyle_low)); holder.artistTv.setTextColor(App.getContext(). diff --git a/app/src/main/java/com/example/musicplayer/app/Api.java b/app/src/main/java/com/example/musicplayer/app/Api.java index b37f861..a36a6e2 100644 --- a/app/src/main/java/com/example/musicplayer/app/Api.java +++ b/app/src/main/java/com/example/musicplayer/app/Api.java @@ -5,21 +5,19 @@ package com.example.musicplayer.app; */ public class Api { - public static String SINGER_URL="http://music.163.com/api/search/get/"; - - //MessAPI - public static String QQ_URL="https://v1.itooi.cn/tencent/"; - - public static String PLAY_URL="https://v1.itooi.cn/tencent/url?id="; - public static String PIC_URL=QQ_URL+"pic?id="; - public static String LRC_URL=QQ_URL+"lrc?id="; - + //根据歌手获取歌手图片的baseUrl + public static final String SINGER_PIC_BASE_URL ="http://music.163.com/"; + public static final String SINGER_PIC="api/search/get/web?csrf_token=&type=100"; + //获取歌手图片需要添加user-agent的表头 + public static final String HEADER_USER_AGENT="User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.132 Safari/537.36"; + + /** + * 存取到手机内存的文件名 + */ public static String STORAGE_IMG_FILE= App.getContext().getExternalFilesDir("") + "/yuanmusic/img/"; public static String STORAGE_LRC_FILE= App.getContext().getExternalFilesDir("") + "/yuanmusic/lrc/"; public static String STORAGE_SONG_FILE= App.getContext().getExternalFilesDir("") + "/yuanmusic/song/"; - public static final String BASE_API_URL_LASTFM = "http://ws.audioscrobbler.com/2.0/"; - //Fiddler抓包qq音乐网站后的地址 public static final String FIDDLER_BASE_QQ_URL ="https://c.y.qq.com/"; public static final String FIDDLER_BASE_SONG_URL="https://u.y.qq.com/"; //获取播放地址的baseUrl @@ -38,7 +36,6 @@ public class Api { //歌词 public static final String SONG_LRC ="soso/fcgi-bin/client_search_cp?p=1&n=30&format=json&t=7";//搜索歌词 public static final String ONLINE_SONG_LRC="https://c.y.qq.com/lyric/fcgi-bin/fcg_query_lyric_new.fcg?format=json&nobase64=1";//根据qq音乐的mid获取歌词 - - + public static final String HEADER_REFERER="Referer:https://y.qq.com/portal/player.html";//得到歌词需要添加Referer的表头 } diff --git a/app/src/main/java/com/example/musicplayer/app/Constant.java b/app/src/main/java/com/example/musicplayer/app/Constant.java index 0f0daf3..5caaf8c 100644 --- a/app/src/main/java/com/example/musicplayer/app/Constant.java +++ b/app/src/main/java/com/example/musicplayer/app/Constant.java @@ -47,4 +47,11 @@ public class Constant { public static final int SONG_LOCAL=1; + //后缀 + public static final String LRC=".lrc"; + + //音乐id + public static final String SONG_ID_UNFIND ="unFind"; + + } diff --git a/app/src/main/java/com/example/musicplayer/contract/IPlayContract.java b/app/src/main/java/com/example/musicplayer/contract/IPlayContract.java index 87780c1..569346e 100644 --- a/app/src/main/java/com/example/musicplayer/contract/IPlayContract.java +++ b/app/src/main/java/com/example/musicplayer/contract/IPlayContract.java @@ -13,19 +13,20 @@ public interface IPlayContract { String getSingerName(); //得到歌手的姓名 void getSingerAndLrc();//按钮点击事件,获取封面和歌词 void setSingerImg(String ImgUrl); //将图片设置成背景 - void setImgFail(String errorMessage); void showLove(boolean love); //判断是否显示我喜欢的图标 void showLoveAnim(); //喜欢的动画 void saveToLoveSuccess();//保存到我喜欢数据库成功 void sendUpdateCollection(); //发送广播更新收藏列表 - void showLrcMessage(String lrc); //显示歌词获取信息 void showLrc(String lrc);//显示歌词 - void getLrcError();//获取不到歌词 + void getLrcError(String content);//获取不到歌词 + void setLocalSongId(String songId); //设置本地音乐的songId + void getSongIdSuccess(String songId);//成功获取到该音乐的id + void saveLrc(String lrc);//保存歌词 } interface Presenter extends IPresenter { void getSingerImg(String singer,String song,long duration); - void getLrc(String songName, String songId,long duration); //搜索歌词 - void getSongOnlineLrc(String songId);//获取网络歌曲 + void getLrc(String songId,int type);//获取歌词 + void getSongId(String song,long duration);//获取歌曲在qq音乐中的id void queryLove(String songId);//查询我喜欢的数据库中有没这首歌 void saveToLove(Song song); //添加到我喜欢的表 diff --git a/app/src/main/java/com/example/musicplayer/entiy/LocalSong.java b/app/src/main/java/com/example/musicplayer/entiy/LocalSong.java index f83121d..b8bb631 100644 --- a/app/src/main/java/com/example/musicplayer/entiy/LocalSong.java +++ b/app/src/main/java/com/example/musicplayer/entiy/LocalSong.java @@ -9,7 +9,7 @@ import org.litepal.crud.LitePalSupport; public class LocalSong extends LitePalSupport{ private int id; - private String songId; + private String songId ; private String name; private String singer; private String url; diff --git a/app/src/main/java/com/example/musicplayer/model/db/DbHelperImpl.java b/app/src/main/java/com/example/musicplayer/model/db/DbHelperImpl.java index da560e8..75344ad 100644 --- a/app/src/main/java/com/example/musicplayer/model/db/DbHelperImpl.java +++ b/app/src/main/java/com/example/musicplayer/model/db/DbHelperImpl.java @@ -54,8 +54,6 @@ public class DbHelperImpl implements DbHelper { for (int i = 0; i < cursor.getCount(); i++) { cursor.moveToNext(); LocalSong mp3Info = new LocalSong(); - long id = cursor.getLong(cursor - .getColumnIndex(MediaStore.Audio.Media._ID)); //音乐id String title = cursor.getString((cursor .getColumnIndex(MediaStore.Audio.Media.TITLE)));//音乐标题 String artist = cursor.getString(cursor @@ -80,7 +78,7 @@ public class DbHelperImpl implements DbHelper { mp3Info.setSinger(artist); mp3Info.setDuration(duration / 1000); mp3Info.setUrl(url); - mp3Info.setSongId(String.valueOf(id)); + mp3Info.setSongId(i+""); mp3InfoList.add(mp3Info); } } @@ -97,8 +95,8 @@ public class DbHelperImpl implements DbHelper { song.setName(localSong.getName()); song.setSinger(localSong.getSinger()); song.setUrl(localSong.getUrl()); - song.setDuration(localSong.getDuration()); song.setSongId(localSong.getSongId()); + song.setDuration(localSong.getDuration()); if(!song.save()) return false; } return true; diff --git a/app/src/main/java/com/example/musicplayer/model/https/RetrofitFactory.java b/app/src/main/java/com/example/musicplayer/model/https/RetrofitFactory.java index c21b4f0..a7978eb 100644 --- a/app/src/main/java/com/example/musicplayer/model/https/RetrofitFactory.java +++ b/app/src/main/java/com/example/musicplayer/model/https/RetrofitFactory.java @@ -23,6 +23,7 @@ public class RetrofitFactory { private static OkHttpClient sOkHttpClient; private static Retrofit sRetrofit; private static Retrofit songUrlRetrofit; + private static Retrofit sSingerPicRetrofit; // 创建网络请求Observable @@ -52,15 +53,15 @@ public class RetrofitFactory { // 获取歌手照片 private synchronized static Retrofit getRetrofitOfSinger() { - if (sRetrofit == null) { - sRetrofit = new Retrofit.Builder() - .baseUrl(Api.SINGER_URL) // 对应服务端的host + if (sSingerPicRetrofit == null) { + sSingerPicRetrofit = new Retrofit.Builder() + .baseUrl(Api.SINGER_PIC_BASE_URL) // 对应服务端的host .client(getOkHttpClient()) .addConverterFactory(GsonConverterFactory.create()) // 这里还结合了Gson .addCallAdapterFactory(RxJava2CallAdapterFactory.create()) // 把Retrofit请求转化成RxJava的Observable .build(); } - return sRetrofit; + return sSingerPicRetrofit; } //得到播放地址 diff --git a/app/src/main/java/com/example/musicplayer/model/https/api/RetrofitService.java b/app/src/main/java/com/example/musicplayer/model/https/api/RetrofitService.java index 1f469a0..ef21eb4 100644 --- a/app/src/main/java/com/example/musicplayer/model/https/api/RetrofitService.java +++ b/app/src/main/java/com/example/musicplayer/model/https/api/RetrofitService.java @@ -60,7 +60,7 @@ public interface RetrofitService { * 根据songmid获取歌词:https://c.y.qq.com/lyric/fcgi-bin/fcg_query_lyric_new.fcg?songmid=000wocYU11tSzS&format=json&nobase64=1 * headers中的Referer是qq用来防盗链的 */ - @Headers("Referer:https://y.qq.com/portal/player.html") + @Headers(Api.HEADER_REFERER) @GET(Api.ONLINE_SONG_LRC) Observable getOnlineSongLrc(@Query("songmid") String songId); @@ -71,7 +71,12 @@ public interface RetrofitService { @GET(Api.SONG_LRC) Observable getLrc(@Query("w") String seek); - @POST("web?csrf_token=&type=100") + /** + * 得到歌手照片,主要用于本地音乐:http://music.163.com/api/search/get/web?s=刘瑞琦&type=100 + * @param singer 歌手名字 + */ + @Headers(Api.HEADER_USER_AGENT) + @POST(Api.SINGER_PIC) @FormUrlEncoded Observable getSingerImg(@Field("s")String singer); diff --git a/app/src/main/java/com/example/musicplayer/presenter/PlayPresenter.java b/app/src/main/java/com/example/musicplayer/presenter/PlayPresenter.java index 2432ec0..3f6dc48 100644 --- a/app/src/main/java/com/example/musicplayer/presenter/PlayPresenter.java +++ b/app/src/main/java/com/example/musicplayer/presenter/PlayPresenter.java @@ -1,19 +1,17 @@ package com.example.musicplayer.presenter; -import android.util.Log; - import com.example.musicplayer.app.Constant; import com.example.musicplayer.base.observer.BaseObserver; import com.example.musicplayer.base.presenter.BasePresenter; import com.example.musicplayer.contract.IPlayContract; -import com.example.musicplayer.entiy.OnlineSong; import com.example.musicplayer.entiy.OnlineSongLrc; +import com.example.musicplayer.entiy.SearchSong; import com.example.musicplayer.entiy.SingerImg; import com.example.musicplayer.entiy.Song; -import com.example.musicplayer.entiy.SongLrc; import com.example.musicplayer.model.https.RetrofitFactory; +import java.util.ArrayList; import java.util.List; import io.reactivex.ObservableSource; @@ -34,65 +32,67 @@ public class PlayPresenter extends BasePresenter implements RetrofitFactory.createRequestOfSinger().getSingerImg(singer) .subscribeOn(Schedulers.io()).observeOn(AndroidSchedulers.mainThread()) .doOnNext(singerImg -> mView.setSingerImg(singerImg.getResult().getArtists().get(0).getImg1v1Url())) + .doOnError(SingerImg -> mView.showToast("获取不到歌手图片")) .observeOn(Schedulers.io()) - .flatMap((Function>) singerImg -> RetrofitFactory.createRequest().getLrc(song)) + .flatMap((Function>) singerImg -> RetrofitFactory.createRequest().search(song,1)) .observeOn(AndroidSchedulers.mainThread()) - .subscribeWith(new BaseObserver(mView) { + .subscribeWith(new BaseObserver(mView) { @Override - public void onNext(SongLrc value) { + public void onNext(SearchSong value) { super.onNext(value); - if (value.getCode() == 200) { - getSongLrcSuccess(value.getData().getLyric().getList(),null,duration); + if (value.getCode() == 0) { + matchLrc(value.getData().getSong().getList(),duration); } else { - mView.showLrcMessage(null); + mView.getLrcError(null); } } @Override public void onError(Throwable e) { super.onError(e); - mView.showLrcMessage(null); - } - }) - ); - } - - @Override - public void getLrc(String songName, String songId,long duration) { - addRxSubscribe( - mModel.getLrc(songName) - .subscribeOn(Schedulers.io()) - .observeOn(AndroidSchedulers.mainThread()) - .subscribeWith(new BaseObserver(mView){ - @Override - public void onNext(SongLrc value) { - super.onNext(value); - if (value.getCode() == 0) { - getSongLrcSuccess(value.getData().getLyric().getList(),songId,duration); - } else { - mView.showLrcMessage(null); - } + mView.getLrcError(null); } }) ); } @Override - public void getSongOnlineLrc(String songId) { + public void getLrc(String songId,int type) { mModel.getOnlineSongLrc(songId) .subscribeOn(Schedulers.io()).observeOn(AndroidSchedulers.mainThread()) .subscribeWith(new BaseObserver(mView,false,false){ @Override public void onNext(OnlineSongLrc onlineSongLrc){ if(onlineSongLrc.getCode() == 0){ - mView.showLrc(onlineSongLrc.getLyric()); + String lrc = onlineSongLrc.getLyric(); + //如果是本地音乐,就将歌词保存起来 + if(type == Constant.SONG_LOCAL) mView.saveLrc(lrc); + mView.showLrc(lrc); }else { - mView.getLrcError(); + mView.getLrcError(null); } } }); } + @Override + public void getSongId(String song, long duration) { + addRxSubscribe( + mModel.search(song, 1) + .subscribeOn(Schedulers.io()).observeOn(AndroidSchedulers.mainThread()) + .subscribeWith(new BaseObserver(mView, true, true) { + @Override + public void onNext(SearchSong searchSong) { + super.onNext(searchSong); + if (searchSong.getCode() == 0) { + matchSong(searchSong.getData().getSong().getList(),duration); + } else { + mView.getLrcError(null); + } + } + })); + } + @Override public void queryLove(String songId) { @@ -113,25 +113,32 @@ public class PlayPresenter extends BasePresenter implements } } - - private void getSongLrcSuccess(List listBeans, String songId,long duration) { - boolean isLrc =false; - for(SongLrc.DataBean.LyricBean.ListBean listBean : listBeans){ - if(null != songId){ - if(listBean.getSongmid().equals(songId)){ - isLrc = true; - mView.showLrcMessage(listBean.getContent()); - break; - } - }else { - if(listBean.getInterval() == duration){ - isLrc = true; - mView.showLrcMessage(listBean.getContent()); - break; - } + //匹配歌词 + private void matchLrc(List listBeans,long duration){ + boolean isFind = false; + for(SearchSong.DataBean.SongBean.ListBean listBean:listBeans){ + if(duration == listBean.getInterval()){ + isFind = true; + mView.setLocalSongId(listBean.getSongmid()); } + } + //如果找不到歌曲id就传输找不到歌曲的消息 + if(!isFind) { + mView.getLrcError(Constant.SONG_ID_UNFIND); + } + } + private void matchSong(List listBeans,long duration){ + boolean isFind = false; + for(SearchSong.DataBean.SongBean.ListBean listBean:listBeans){ + if(duration == listBean.getInterval()){ + isFind = true; + mView.getSongIdSuccess(listBean.getSongmid()); + } + } + //如果找不到歌曲id就传输找不到歌曲的消息 + if(!isFind) { + mView.getLrcError(Constant.SONG_ID_UNFIND); } - if(!isLrc) mView.showLrcMessage(null); } } diff --git a/app/src/main/java/com/example/musicplayer/service/PlayerService.java b/app/src/main/java/com/example/musicplayer/service/PlayerService.java index 70bf3fd..2ee2293 100644 --- a/app/src/main/java/com/example/musicplayer/service/PlayerService.java +++ b/app/src/main/java/com/example/musicplayer/service/PlayerService.java @@ -10,12 +10,10 @@ import android.util.Log; import com.example.musicplayer.app.Api; import com.example.musicplayer.app.Constant; -import com.example.musicplayer.base.observer.BaseObserver; import com.example.musicplayer.entiy.HistorySong; import com.example.musicplayer.entiy.LocalSong; import com.example.musicplayer.entiy.Love; import com.example.musicplayer.entiy.OnlineSong; -import com.example.musicplayer.entiy.SingerImg; import com.example.musicplayer.entiy.Song; import com.example.musicplayer.entiy.SongUrl; import com.example.musicplayer.event.OnlineSongChangeEvent; @@ -26,7 +24,7 @@ import com.example.musicplayer.event.SongHistoryEvent; import com.example.musicplayer.event.SongLocalEvent; import com.example.musicplayer.event.SongStatusEvent; import com.example.musicplayer.model.https.RetrofitFactory; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import org.greenrobot.eventbus.EventBus; import org.litepal.LitePal; @@ -60,7 +58,7 @@ public class PlayerService extends Service { @Override public void onCreate() { - mListType = FileHelper.getSong().getListType(); + mListType = FileUtil.getSong().getListType(); if (mListType == Constant.LIST_TYPE_ONLINE) { mSongList = LitePal.findAll(OnlineSong.class); } else if (mListType == Constant.LIST_TYPE_LOCAL) { @@ -70,9 +68,9 @@ public class PlayerService extends Service { } else if (mListType == Constant.LIST_TYPE_HISTORY) { mHistoryList = orderHistoryList(LitePal.findAll(HistorySong.class)); //保证最近播放列表一开始总是第一个 - Song song = FileHelper.getSong(); + Song song = FileUtil.getSong(); song.setCurrent(0); - FileHelper.saveSong(song); + FileUtil.saveSong(song); } } @@ -82,7 +80,7 @@ public class PlayerService extends Service { @Override public void onCompletion(MediaPlayer mp) { EventBus.getDefault().post(new SongStatusEvent(Constant.SONG_PAUSE));//暂停广播 - mCurrent = FileHelper.getSong().getCurrent(); + mCurrent = FileUtil.getSong().getCurrent(); mCurrent++; //将歌曲的信息保存起来 if (mListType == Constant.LIST_TYPE_LOCAL) { @@ -132,9 +130,9 @@ public class PlayerService extends Service { public void getHistoryList() { mHistoryList = orderHistoryList(LitePal.findAll(HistorySong.class)); //保证最近播放列表一开始总是第一个 - Song song = FileHelper.getSong(); + Song song = FileUtil.getSong(); song.setCurrent(0); - FileHelper.saveSong(song); + FileUtil.saveSong(song); } /** @@ -158,7 +156,7 @@ public class PlayerService extends Service { } else if (mListType == Constant.LIST_TYPE_HISTORY) { EventBus.getDefault().post(new SongHistoryEvent()); //发送随机歌曲改变事件 } - mCurrent = FileHelper.getSong().getCurrent(); + mCurrent = FileUtil.getSong().getCurrent(); mediaPlayer.reset();//把各项参数恢复到初始状态 if (mListType == Constant.LIST_TYPE_LOCAL) { mediaPlayer.setDataSource(mLocalSongList.get(mCurrent).getUrl()); @@ -179,7 +177,7 @@ public class PlayerService extends Service { public void playOnline() { try { mediaPlayer.reset(); - mediaPlayer.setDataSource(FileHelper.getSong().getUrl()); + mediaPlayer.setDataSource(FileUtil.getSong().getUrl()); mediaPlayer.prepare(); isPlaying = true; saveToHistoryTable(); @@ -219,7 +217,7 @@ public class PlayerService extends Service { public void next() { EventBus.getDefault().post(new SongStatusEvent(Constant.SONG_RESUME)); - mCurrent = FileHelper.getSong().getCurrent(); + mCurrent = FileUtil.getSong().getCurrent(); mCurrent++; Log.d(TAG, "next: "+mCurrent); if (mListType == Constant.LIST_TYPE_LOCAL) { @@ -251,7 +249,7 @@ public class PlayerService extends Service { public void last() { EventBus.getDefault().post(new SongStatusEvent(Constant.SONG_RESUME));//暂停广播 - mCurrent = FileHelper.getSong().getCurrent(); + mCurrent = FileUtil.getSong().getCurrent(); mCurrent--; if (mCurrent == -1) { if (mListType == Constant.LIST_TYPE_LOCAL) { @@ -340,7 +338,7 @@ public class PlayerService extends Service { song.setSongId(localSong.getSongId()); song.setOnline(false); song.setListType(Constant.LIST_TYPE_LOCAL); - FileHelper.saveSong(song); + FileUtil.saveSong(song); } //保存网络专辑列表的信息 @@ -356,7 +354,7 @@ public class PlayerService extends Service { song.setImgUrl(mSongList.get(current).getPic()); song.setOnline(true); song.setListType(Constant.LIST_TYPE_ONLINE); - FileHelper.saveSong(song); + FileUtil.saveSong(song); } //保存我的收藏的列表的信息 @@ -373,7 +371,7 @@ public class PlayerService extends Service { song.setListType(Constant.LIST_TYPE_LOVE); song.setOnline(love.isOnline()); song.setDuration(love.getDuration()); - FileHelper.saveSong(song); + FileUtil.saveSong(song); } //保存我的收藏的列表的信息 @@ -389,13 +387,13 @@ public class PlayerService extends Service { song.setListType(Constant.LIST_TYPE_HISTORY); song.setOnline(historySong.isOnline()); song.setDuration(historySong.getDuration()); - FileHelper.saveSong(song); + FileUtil.saveSong(song); } //将歌曲保存到最近播放的数据库中 private void saveToHistoryTable() { - final Song song = FileHelper.getSong(); + final Song song = FileUtil.getSong(); LitePal.where("songId=?", song.getSongId()).findAsync(HistorySong.class) .listen(new FindMultiCallback() { @Override @@ -461,10 +459,10 @@ public class PlayerService extends Service { if(songUrl.getCode() == 0){ String sip = songUrl.getReq_0().getData().getSip().get(0); String purl = songUrl.getReq_0().getData().getMidurlinfo().get(0).getPurl(); - Song song = FileHelper.getSong(); + Song song = FileUtil.getSong(); assert song != null; song.setUrl(sip+purl); - FileHelper.saveSong(song); + FileUtil.saveSong(song); try { mediaPlayer.setDataSource(sip+purl); startPlay(); diff --git a/app/src/main/java/com/example/musicplayer/util/FileHelper.java b/app/src/main/java/com/example/musicplayer/util/FileUtil.java similarity index 66% rename from app/src/main/java/com/example/musicplayer/util/FileHelper.java rename to app/src/main/java/com/example/musicplayer/util/FileUtil.java index 29dbb2c..a73534e 100644 --- a/app/src/main/java/com/example/musicplayer/util/FileHelper.java +++ b/app/src/main/java/com/example/musicplayer/util/FileUtil.java @@ -7,13 +7,19 @@ import android.util.Log; import com.example.musicplayer.app.Api; import com.example.musicplayer.app.App; +import com.example.musicplayer.app.Constant; import com.example.musicplayer.entiy.Song; +import java.io.BufferedReader; +import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; +import java.io.FileReader; +import java.io.FileWriter; import java.io.IOException; +import java.io.InputStream; import java.io.ObjectInputStream; import java.io.ObjectOutputStream; @@ -23,8 +29,8 @@ import java.io.ObjectOutputStream; */ -public class FileHelper { - private static String TAG = "FileHelper"; +public class FileUtil { + private static String TAG = "FileUtil"; /** * 将person对象保存到文件中 @@ -100,4 +106,44 @@ public class FileHelper { } } } + + //保存歌词到本地 + public static void saveLrcToNative(String lrc,String songName){ + //开启线程保存歌词 + new Thread(() -> { + File file = new File(Api.STORAGE_LRC_FILE); + if (!file.exists()) { + file.mkdirs(); + } + File lrcFile = new File(file, songName + Constant.LRC); + try { + FileWriter fileWriter = new FileWriter(lrcFile); + fileWriter.write(lrc); + fileWriter.close(); + } catch (IOException e) { + e.printStackTrace(); + } + }).start(); + } + + public static String getLrcFromNative(String songName) { + try { + FileReader fileReader = new FileReader(Api.STORAGE_LRC_FILE+songName+Constant.LRC); + BufferedReader bufferedReader = new BufferedReader(fileReader); + StringBuilder lrc = new StringBuilder(); + while (true){ + String s = bufferedReader.readLine(); + if(s == null) break; + lrc.append(s).append("\n"); + } + fileReader.close(); + Log.d(TAG, "getLrcFromNative: "+lrc.toString()); + return lrc.toString(); + } catch (IOException e) { + e.printStackTrace(); + } + return null; + } + + } \ No newline at end of file diff --git a/app/src/main/java/com/example/musicplayer/view/MainActivity.java b/app/src/main/java/com/example/musicplayer/view/MainActivity.java index bc0e43a..b0953a6 100644 --- a/app/src/main/java/com/example/musicplayer/view/MainActivity.java +++ b/app/src/main/java/com/example/musicplayer/view/MainActivity.java @@ -31,7 +31,7 @@ import com.example.musicplayer.event.OnlineSongErrorEvent; import com.example.musicplayer.event.SongStatusEvent; import com.example.musicplayer.service.PlayerService; import com.example.musicplayer.util.CommonUtil; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import com.example.musicplayer.view.main.MainFragment; import com.example.musicplayer.view.search.SearchContentFragment; @@ -90,9 +90,9 @@ public class MainActivity extends BaseActivity { unbindService(connection); EventBus.getDefault().unregister(this); if (mSeekBarThread != null || mSeekBarThread.isAlive()) mSeekBarThread.interrupt(); - Song song = FileHelper.getSong(); + Song song = FileUtil.getSong(); song.setCurrentTime(mPlayStatusBinder.getCurrentTime()); - FileHelper.saveSong(song); + FileUtil.saveSong(song); } @@ -118,7 +118,7 @@ public class MainActivity extends BaseActivity { mCircleAnimator.setRepeatMode(ValueAnimator.RESTART); - mSong = FileHelper.getSong(); + mSong = FileUtil.getSong(); if (mSong.getSongName() != null) { Log.d(TAG, "initView: " + mSong.toString()); mLinear.setVisibility(View.VISIBLE); @@ -167,7 +167,7 @@ public class MainActivity extends BaseActivity { mPlayerBtn.setSelected(false); mCircleAnimator.pause(); } else if(status == Constant.SONG_CHANGE){ - mSong = FileHelper.getSong(); + mSong = FileUtil.getSong(); mSongNameTv.setText(mSong.getSongName()); mSingerTv.setText(mSong.getSinger()); mSeekBar.setMax((int) mSong.getDuration()); @@ -236,11 +236,11 @@ public class MainActivity extends BaseActivity { mMediaPlayer.seekTo(time); } } else { - if (FileHelper.getSong().isOnline()) { + if (FileUtil.getSong().isOnline()) { Log.d(TAG, "onClick: "+mSong.getCurrentTime()); mPlayStatusBinder.playOnline(); } else { - mPlayStatusBinder.play(FileHelper.getSong().getListType()); + mPlayStatusBinder.play(FileUtil.getSong().getListType()); } mMediaPlayer = mPlayStatusBinder.getMediaPlayer(); mMediaPlayer.seekTo((int) mSong.getCurrentTime()); @@ -267,17 +267,17 @@ public class MainActivity extends BaseActivity { //播放情况 if (mPlayStatusBinder.isPlaying()) { - Song song = FileHelper.getSong(); + Song song = FileUtil.getSong(); song.setCurrentTime(mPlayStatusBinder.getCurrentTime()); - FileHelper.saveSong(song); + FileUtil.saveSong(song); toPlayActivityIntent.putExtra(Constant.PLAYER_STATUS, Constant.SONG_PLAY); } else { //暂停情况 - Song song = FileHelper.getSong(); + Song song = FileUtil.getSong(); song.setCurrentTime(mSeekBar.getProgress()); - FileHelper.saveSong(song); + FileUtil.saveSong(song); } - if (FileHelper.getSong().getImgUrl() != null) { + if (FileUtil.getSong().getImgUrl() != null) { toPlayActivityIntent.putExtra(SearchContentFragment.IS_ONLINE, true); } startActivity(toPlayActivityIntent, diff --git a/app/src/main/java/com/example/musicplayer/view/PlayActivity.java b/app/src/main/java/com/example/musicplayer/view/PlayActivity.java index 74ab802..135940c 100644 --- a/app/src/main/java/com/example/musicplayer/view/PlayActivity.java +++ b/app/src/main/java/com/example/musicplayer/view/PlayActivity.java @@ -48,7 +48,7 @@ import com.example.musicplayer.service.PlayerService; import com.example.musicplayer.util.CommonUtil; import com.example.musicplayer.util.DisplayUtil; import com.example.musicplayer.util.FastBlurUtil; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import com.example.musicplayer.util.MediaUtil; import com.example.musicplayer.widget.BackgroundAnimationRelativeLayout; import com.example.musicplayer.widget.DiscView; @@ -61,15 +61,19 @@ import org.greenrobot.eventbus.ThreadMode; import java.io.BufferedOutputStream; import java.io.BufferedReader; import java.io.BufferedWriter; +import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; +import java.io.FileReader; +import java.io.FileWriter; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.OutputStreamWriter; +import java.io.UnsupportedEncodingException; import java.net.HttpURLConnection; import java.net.URL; import java.util.List; @@ -149,10 +153,10 @@ public class PlayActivity extends BaseMvpActivity implements IPla public void onServiceConnected(ComponentName name, IBinder service) { mPlayStatusBinder = (PlayerService.PlayStatusBinder) service; - isOnline = FileHelper.getSong().isOnline(); + isOnline = FileUtil.getSong().isOnline(); if (isOnline) { mGetImgAndLrcBtn.setVisibility(View.GONE); - setSingerImg(FileHelper.getSong().getImgUrl()); + setSingerImg(FileUtil.getSong().getImgUrl()); if (mPlayStatus == Constant.SONG_PLAY) { mDisc.play(); mPlayBtn.setSelected(true); @@ -209,7 +213,7 @@ public class PlayActivity extends BaseMvpActivity implements IPla bindService(playIntent, connection, Context.BIND_AUTO_CREATE); //界面填充 - mSong = FileHelper.getSong(); + mSong = FileUtil.getSong(); mListType = mSong.getListType(); mSingerTv.setText(mSong.getSinger()); mSongTv.setText(mSong.getSongName()); @@ -289,6 +293,7 @@ public class PlayActivity extends BaseMvpActivity implements IPla mBackIv.setOnClickListener(v -> { finish(); }); + //获取本地音乐的图片和歌词 mGetImgAndLrcBtn.setOnClickListener(v -> getSingerAndLrc()); //进度条的监听事件 @@ -374,10 +379,10 @@ public class PlayActivity extends BaseMvpActivity implements IPla showLoveAnim(); if (isLove) { mLoveBtn.setSelected(false); - mPresenter.deleteFromLove(FileHelper.getSong().getSongId()); + mPresenter.deleteFromLove(FileUtil.getSong().getSongId()); } else { mLoveBtn.setSelected(true); - mPresenter.saveToLove(FileHelper.getSong()); + mPresenter.saveToLove(FileUtil.getSong()); } isLove = !isLove; }); @@ -385,12 +390,23 @@ public class PlayActivity extends BaseMvpActivity implements IPla //唱碟点击效果 mDisc.setOnClickListener(v -> { if (!isOnline) { - if (getLrcFromLocal().equals("")) { - mPresenter.getLrc(getSongName(), null, mSong.getDuration()); + String lrc = FileUtil.getLrcFromNative(mSong.getSongName()); + if (null == lrc) { + String songId = mSong.getSongId(); + Log.d(TAG, "onClick: songId="+songId); + if(songId.length()<14&&Constant.SONG_ID_UNFIND.equals(songId)){//匹配不到歌词 + getLrcError(null); + }else if(songId.length()<14){//歌曲的id还未匹配 + Log.d(TAG, "onClick: "+mSong.getDuration()); + mPresenter.getSongId(mSong.getSongName(),mSong.getDuration()); + }else {//歌词还未匹配 + mPresenter.getLrc(mSong.getSongId(),Constant.SONG_LOCAL); + } + }else { + showLrc(lrc); } - showLrc(getLrcFromLocal()); } else { - mPresenter.getSongOnlineLrc(mSong.getSongId()); + mPresenter.getLrc(mSong.getSongId(),Constant.SONG_ONLINE); } } ); @@ -409,7 +425,7 @@ public class PlayActivity extends BaseMvpActivity implements IPla @Override public String getSingerName() { - Song song = FileHelper.getSong(); + Song song = FileUtil.getSong(); if (song.getSinger().contains("/")) { String[] s = song.getSinger().split("/"); return s[0].trim(); @@ -420,7 +436,7 @@ public class PlayActivity extends BaseMvpActivity implements IPla } private String getSongName() { - Song song = FileHelper.getSong(); + Song song = FileUtil.getSong(); assert song != null; return song.getSongName().trim(); } @@ -440,11 +456,11 @@ public class PlayActivity extends BaseMvpActivity implements IPla //如果是本地音乐 if (!isOnline) { //保存图片到本地 - FileHelper.saveImgToNative(PlayActivity.this, mImgBmp, getSingerName()); + FileUtil.saveImgToNative(PlayActivity.this, mImgBmp, getSingerName()); //将封面地址放到数据库中 LocalSong localSong = new LocalSong(); - localSong.setPic(Api.STORAGE_IMG_FILE + FileHelper.getSong().getSinger() + ".jpg"); - localSong.updateAll("songId=?", FileHelper.getSong().getSongId()); + localSong.setPic(Api.STORAGE_IMG_FILE + FileUtil.getSong().getSinger() + ".jpg"); + localSong.updateAll("songId=?", FileUtil.getSong().getSongId()); } try2UpdateMusicPicBackground(mImgBmp); @@ -460,10 +476,6 @@ public class PlayActivity extends BaseMvpActivity implements IPla } - @Override - public void setImgFail(String errorMessage) { - CommonUtil.showToast(this, errorMessage); - } @Override public void showLove(final boolean love) { @@ -496,21 +508,6 @@ public class PlayActivity extends BaseMvpActivity implements IPla EventBus.getDefault().post(new SongCollectionEvent(false)); } - @Override - public void showLrcMessage(String lrc) { - if (lrc == null) { - CommonUtil.showToast(PlayActivity.this, getString(R.string.get_lrc_fail)); - mLrc = null; - } else { - if (isOnline) { - showLrc(lrc); - } else { - mLrc = lrc; - saveLrcToLocal(); - } - } - } - //设置唱碟中歌手头像 private void setDiscImg(Bitmap bitmap) { @@ -528,7 +525,7 @@ public class PlayActivity extends BaseMvpActivity implements IPla if (event.getSongStatus() == Constant.SONG_CHANGE) { mDisc.setVisibility(View.VISIBLE); mLrcView.setVisibility(View.GONE); - mSong = FileHelper.getSong(); + mSong = FileUtil.getSong(); mSongTv.setText(mSong.getSongName()); mSingerTv.setText(mSong.getSinger()); mDurationTimeTv.setText(MediaUtil.formatTime(mSong.getDuration())); @@ -595,80 +592,6 @@ public class PlayActivity extends BaseMvpActivity implements IPla } - private void saveLrcToLocal() { - new Thread(() -> { - HttpURLConnection urlConnection = null; - BufferedReader reader = null; - BufferedWriter writer = null; - try { - URL url = new URL(mLrc); - urlConnection = (HttpURLConnection) url.openConnection(); - urlConnection.setRequestMethod("GET"); - InputStream inputStream = urlConnection.getInputStream(); - reader = new BufferedReader(new InputStreamReader(inputStream)); - StringBuilder lrcBuilder = new StringBuilder(); - String lrc; - - /** - * 保存到本地 - */ - if (!isOnline) { - File file = new File(Api.STORAGE_LRC_FILE); - if (!file.exists()) { - file.mkdirs(); - } - File lrcFile = new File(file, getSongName() + ".lrc"); - FileOutputStream outputStream = new FileOutputStream(lrcFile); - OutputStreamWriter outputStreamWriter = new OutputStreamWriter(outputStream, "gbk"); - writer = new BufferedWriter(outputStreamWriter); - } - while ((lrc = reader.readLine()) != null) { - if (isOnline) { - lrcBuilder.append(lrc); - lrcBuilder.append("\n"); - } else { - //写入 - writer.write(lrc); - writer.newLine(); - } - - } - if (isOnline) showLrc(lrcBuilder.toString()); - } catch (Exception e) { - e.printStackTrace(); - } finally { - if (urlConnection != null) urlConnection.disconnect(); - try { - if (reader != null) reader.close(); - if (writer != null) writer.close(); - } catch (IOException e) { - e.printStackTrace(); - } - } - }).start(); - } - - /** - * 从本地读取歌词文件 - */ - private String getLrcFromLocal() { - try { - InputStream inputStream = new FileInputStream(new File(Api.STORAGE_LRC_FILE + getSongName() + ".lrc")); - ByteArrayOutputStream os = new ByteArrayOutputStream(); - byte[] buffer = new byte[1024]; - int len = -1; - while ((len = inputStream.read(buffer)) != -1) { - os.write(buffer, 0, len); - } - return os.toString("gbk"); //文件编码是gbk - - } catch (FileNotFoundException e) { - e.printStackTrace(); - } catch (IOException e) { - e.printStackTrace(); - } - return ""; - } /** * 展示歌词 @@ -687,8 +610,28 @@ public class PlayActivity extends BaseMvpActivity implements IPla } @Override - public void getLrcError() { + public void getLrcError(String content) { showToast(getString(R.string.get_lrc_fail)); + mSong.setSongId(content); + FileUtil.saveSong(mSong); + } + + @Override + public void setLocalSongId(String songId) { + mSong.setSongId(songId); + FileUtil.saveSong(mSong); //保存 + } + + @Override + public void getSongIdSuccess(String songId) { + Log.d(TAG, "getSongIdSuccess: "+songId); + setLocalSongId(songId);//保存音乐信息 + mPresenter.getLrc(songId,Constant.SONG_LOCAL);//获取歌词 + } + + @Override + public void saveLrc(String lrc) { + FileUtil.saveLrcToNative(lrc,mSong.getSongName()); } private void downLoad(String url, String song) { diff --git a/app/src/main/java/com/example/musicplayer/view/main/CollectionFragment.java b/app/src/main/java/com/example/musicplayer/view/main/CollectionFragment.java index 8753060..3748ffb 100644 --- a/app/src/main/java/com/example/musicplayer/view/main/CollectionFragment.java +++ b/app/src/main/java/com/example/musicplayer/view/main/CollectionFragment.java @@ -23,7 +23,7 @@ import com.example.musicplayer.entiy.Love; import com.example.musicplayer.entiy.Song; import com.example.musicplayer.event.SongCollectionEvent; import com.example.musicplayer.service.PlayerService; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import org.greenrobot.eventbus.EventBus; import org.greenrobot.eventbus.Subscribe; @@ -92,8 +92,8 @@ public class CollectionFragment extends Fragment { mLoveList.addAll(orderList(LitePal.findAll(Love.class))); mAdapter.notifyDataSetChanged(); if(songCollectionEvent.isLove()){//定位歌曲 - if (FileHelper.getSong() != null) { - mManager.scrollToPositionWithOffset(FileHelper.getSong().getCurrent() + 4, mRecycler.getHeight()); + if (FileUtil.getSong() != null) { + mManager.scrollToPositionWithOffset(FileUtil.getSong().getCurrent() + 4, mRecycler.getHeight()); } } } @@ -119,7 +119,7 @@ public class CollectionFragment extends Fragment { song.setCurrent(position); song.setDuration(love.getDuration()); song.setListType(Constant.LIST_TYPE_LOVE); - FileHelper.saveSong(song); + FileUtil.saveSong(song); mPlayStatusBinder.play(Constant.LIST_TYPE_LOVE); } diff --git a/app/src/main/java/com/example/musicplayer/view/main/HistoryFragment.java b/app/src/main/java/com/example/musicplayer/view/main/HistoryFragment.java index 00bd8e4..73be7b6 100644 --- a/app/src/main/java/com/example/musicplayer/view/main/HistoryFragment.java +++ b/app/src/main/java/com/example/musicplayer/view/main/HistoryFragment.java @@ -24,7 +24,7 @@ import com.example.musicplayer.entiy.HistorySong; import com.example.musicplayer.entiy.Song; import com.example.musicplayer.event.SongHistoryEvent; import com.example.musicplayer.service.PlayerService; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import org.greenrobot.eventbus.EventBus; import org.greenrobot.eventbus.Subscribe; @@ -120,7 +120,7 @@ public class HistoryFragment extends Fragment { song.setCurrent(position); song.setDuration(history.getDuration()); song.setListType(Constant.LIST_TYPE_HISTORY); - FileHelper.saveSong(song); + FileUtil.saveSong(song); mPlayStatusBinder.play(Constant.LIST_TYPE_HISTORY); }); diff --git a/app/src/main/java/com/example/musicplayer/view/main/LocalFragment.java b/app/src/main/java/com/example/musicplayer/view/main/LocalFragment.java index 1881c3a..a77b925 100644 --- a/app/src/main/java/com/example/musicplayer/view/main/LocalFragment.java +++ b/app/src/main/java/com/example/musicplayer/view/main/LocalFragment.java @@ -23,7 +23,7 @@ import com.example.musicplayer.entiy.Song; import com.example.musicplayer.event.SongLocalEvent; import com.example.musicplayer.presenter.LocalPresenter; import com.example.musicplayer.service.PlayerService; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import org.greenrobot.eventbus.EventBus; import org.greenrobot.eventbus.Subscribe; @@ -96,8 +96,8 @@ public class LocalFragment extends BaseMvpFragment implements IL @Subscribe(threadMode = ThreadMode.MAIN) public void onMessageEvent(SongLocalEvent event){ songAdapter.notifyDataSetChanged(); - if (FileHelper.getSong() != null) { - layoutManager.scrollToPositionWithOffset(FileHelper.getSong().getCurrent() + 4, mRecycler.getHeight()); + if (FileUtil.getSong() != null) { + layoutManager.scrollToPositionWithOffset(FileUtil.getSong().getCurrent() + 4, mRecycler.getHeight()); } } @@ -141,7 +141,7 @@ public class LocalFragment extends BaseMvpFragment implements IL song.setOnline(false); song.setSongId(mp3Info.getSongId()); song.setListType(Constant.LIST_TYPE_LOCAL); - FileHelper.saveSong(song); + FileUtil.saveSong(song); mPlayStatusBinder.play(Constant.LIST_TYPE_LOCAL); }); @@ -178,8 +178,8 @@ public class LocalFragment extends BaseMvpFragment implements IL //令recyclerView定位到当前播放的位置 songAdapter = new SongAdapter(mActivity, mLocalSongsList); mRecycler.setAdapter(songAdapter); - if (FileHelper.getSong() != null) { - layoutManager.scrollToPositionWithOffset(FileHelper.getSong().getCurrent() - 4, mRecycler.getHeight()); + if (FileUtil.getSong() != null) { + layoutManager.scrollToPositionWithOffset(FileUtil.getSong().getCurrent() - 4, mRecycler.getHeight()); } songAdapter.setOnItemClickListener(position -> { //将点击的序列化到本地 @@ -193,7 +193,7 @@ public class LocalFragment extends BaseMvpFragment implements IL song.setOnline(false); song.setSongId(mp3Info.getSongId()); song.setListType(Constant.LIST_TYPE_LOCAL); - FileHelper.saveSong(song); + FileUtil.saveSong(song); mPlayStatusBinder.play(Constant.LIST_TYPE_LOCAL); }); diff --git a/app/src/main/java/com/example/musicplayer/view/search/AlbumSongFragment.java b/app/src/main/java/com/example/musicplayer/view/search/AlbumSongFragment.java index 1aaf240..3d4dbef 100644 --- a/app/src/main/java/com/example/musicplayer/view/search/AlbumSongFragment.java +++ b/app/src/main/java/com/example/musicplayer/view/search/AlbumSongFragment.java @@ -10,7 +10,6 @@ import android.support.v4.app.Fragment; import android.support.v4.widget.NestedScrollView; import android.support.v7.widget.LinearLayoutManager; import android.support.v7.widget.RecyclerView; -import android.util.Log; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; @@ -20,7 +19,6 @@ import android.widget.TextView; import com.example.musicplayer.R; import com.example.musicplayer.adapter.AlbumSongAdapter; import com.example.musicplayer.app.Api; -import com.example.musicplayer.app.App; import com.example.musicplayer.app.Constant; import com.example.musicplayer.base.fragment.BaseMvpFragment; import com.example.musicplayer.contract.IAlbumSongContract; @@ -30,7 +28,7 @@ import com.example.musicplayer.event.SongAlbumEvent; import com.example.musicplayer.presenter.AlbumSongPresenter; import com.example.musicplayer.service.PlayerService; import com.example.musicplayer.util.CommonUtil; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import com.github.florent37.materialviewpager.MaterialViewPagerHelper; import com.github.florent37.materialviewpager.header.MaterialViewPagerHeaderDecorator; import com.wang.avi.AVLoadingIndicatorView; @@ -198,7 +196,7 @@ public class AlbumSongFragment extends BaseMvpFragment imple song.setListType(Constant.LIST_TYPE_ONLINE); song.setImgUrl(Api.ALBUM_PIC+dataBean.getAlbummid()+ Api.JPG); song.setUrl(null); - FileHelper.saveSong(song); + FileUtil.saveSong(song); mPlayStatusBinder.play(Constant.LIST_TYPE_ONLINE); diff --git a/app/src/main/java/com/example/musicplayer/view/search/SearchContentFragment.java b/app/src/main/java/com/example/musicplayer/view/search/SearchContentFragment.java index 6138ffe..e4910ca 100644 --- a/app/src/main/java/com/example/musicplayer/view/search/SearchContentFragment.java +++ b/app/src/main/java/com/example/musicplayer/view/search/SearchContentFragment.java @@ -27,7 +27,7 @@ import com.example.musicplayer.event.OnlineSongErrorEvent; import com.example.musicplayer.presenter.SearchContentPresenter; import com.example.musicplayer.service.PlayerService; import com.example.musicplayer.util.CommonUtil; -import com.example.musicplayer.util.FileHelper; +import com.example.musicplayer.util.FileUtil; import com.github.jdsjlzx.recyclerview.LRecyclerView; import com.github.jdsjlzx.recyclerview.LRecyclerViewAdapter; @@ -168,7 +168,7 @@ public class SearchContentFragment extends BaseLoadingFragment确定 收藏成功 + 获取封面和歌词成功 抱歉,获取不到该歌曲的歌词信息 //专辑