1. 基於android音樂播放器源代碼(正常播放、有列表)
package my.android.players;
import java.io.File;
import java.io.FilenameFilter;
import java.util.ArrayList;
import java.util.List;
import android.app.Activity;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.media.MediaPlayer;
import android.os.Bundle;
import android.view.KeyEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.ImageButton;
import android.widget.TextView;
public class mainActivity extends Activity {
private List<String> myMusicList=new ArrayList<String>();
//當前播放歌曲的索引
private int currentListItem=0;
//音樂的路徑
private static final String MUSIC_PATH="/sdcard/mp3";
//播放對象
private MediaPlayer myMediaPlayer;
private TextView m_TextView;
//播放按鈕
private ImageButton m_start;
private ImageButton m_stop;
private ImageButton m_next;
private ImageButton m_last;
/*設定bIsPaused一開始為false */
private boolean bIsRun = false;
private boolean isplay;
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.main2);
myMediaPlayer=new MediaPlayer();
musicList();
m_TextView=(TextView)findViewById(R.id.mtextview);
m_start=(ImageButton)findViewById(R.id.imgbtn_start);
m_stop=(ImageButton)findViewById(R.id.imgbtn_stop);
m_next=(ImageButton)findViewById(R.id.imgbtn_next);
m_last=(ImageButton)findViewById(R.id.imgbtn_last);
listener();
Intent intent = this.getIntent();
Bundle bundle = intent.getExtras();
currentListItem = bundle.getInt("currentListItem");
isplay=bundle.getBoolean("isplay");
if(isplay==true)
{
bIsRun=false;
playMusic(MUSIC_PATH+"/"+myMusicList.get(currentListItem));
}
}
//監聽事件
void listener(){
//開始
m_start.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
try
{
if(myMediaPlayer.isPlaying()==true)
{
myMediaPlayer.pause();
m_start.setImageResource(R.drawable.pause);
}
else
{
playMusic(MUSIC_PATH+"/"+myMusicList.get(currentListItem));
}
}
catch (IllegalStateException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
//下一首
m_next.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
nextMusic();
}
});
//上一首
m_last.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
lastMusic();
}
});
//停止
m_stop.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
stopMusic();
}
});
myMediaPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
@Override
public void onCompletion(MediaPlayer mp) {
// TODO Auto-generated method stub
nextMusic();
}
});
}
//播放音樂
void playMusic(String path){
try {
if(bIsRun==false)
{
myMediaPlayer.reset();
myMediaPlayer.setDataSource(path);
myMediaPlayer.prepare();
myMediaPlayer.start();
/*
* 取出歌曲名的.mp3後綴
* */
String str=(myMusicList.get(currentListItem)).toString();
System.out.println(str);
String str1[]=str.split("\\.");
System.out.println(str1[0]);
m_TextView.setText(str1[0]);
}
else
{
myMediaPlayer.start();
}
m_start.setImageResource(R.drawable.start);
bIsRun=true;
} catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
}
//下一首
void nextMusic(){
if(++currentListItem>=myMusicList.size()){
currentListItem=0;
}
bIsRun=false;
playMusic(MUSIC_PATH+"/"+myMusicList.get(currentListItem));
}
//上一首
void lastMusic(){
if(--currentListItem<0)
currentListItem=myMusicList.size()-1;
bIsRun=false;
playMusic(MUSIC_PATH+"/"+myMusicList.get(currentListItem));
}
//停止
void stopMusic() {
if (myMediaPlayer.isPlaying()) {
m_start.setImageResource(R.drawable.pause);
myMediaPlayer.stop();// 停止
bIsRun=false;
}
else
playMusic(MUSIC_PATH+"/"+myMusicList.get(currentListItem));
}
//當用戶返回時結束音樂並釋放音樂對象
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
// TODO Auto-generated method stub
if(keyCode==KeyEvent.KEYCODE_BACK){
new AlertDialog.Builder(mainActivity.this).setTitle("message")
.setIcon(android.R.drawable.dialog_frame)
.setMessage("你確定要離開嗎?")
.setPositiveButton("確定",new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
// TODO Auto-generated method stub
myMediaPlayer.stop();
myMediaPlayer.release();
finish();
}
}).setNegativeButton("取消",new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
// TODO Auto-generated method stub
}
}).show();
}
return super.onKeyDown(keyCode, event);
}
/**
* 文件過濾器
*
* @author
*
*/
class MusicFilter implements FilenameFilter {
@Override
public boolean accept(File dir, String filename) {
return (filename.endsWith(".mp3"));
}
}
//綁定音樂
void musicList(){
try{
File home=new File(MUSIC_PATH);
if(!home.exists())
home.mkdirs();
if(home.listFiles(new MusicFilter()).length>=0){
for(File file:home.listFiles(new MusicFilter())){
myMusicList.add(file.getName().toString());
}
}
}
catch(Exception ex)
{
ex.printStackTrace();
}
}
}
package my.android.players;
import java.io.File;
import java.io.FilenameFilter;
import java.util.ArrayList;
import java.util.List;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ListView;
public class Activity01 extends Activity {
//播放列表
private List<String> myMusicList=new ArrayList<String>();
//當前播放歌曲的索引
private int currentListItem;
//音樂的路徑
private static final String MUSIC_PATH="/sdcard/mp3";
//播放列表
private ListView m_ListView;
private boolean isplay=true;
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
m_ListView=(ListView)findViewById(R.id.lv_music);
musicList();
//當選擇列表項時播放音樂
m_ListView.setOnItemClickListener(new ListView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> arg0, View arg1, int arg2,
long arg3) {
currentListItem = arg2;
Intent intent = new Intent();
Bundle mBundle=new Bundle();
mBundle.putInt("currentListItem", currentListItem);
mBundle.putBoolean("isplay", isplay);
intent.putExtras(mBundle);
intent.setClass(Activity01.this,mainActivity.class);
startActivity(intent);
finish();
}
});
}
/**
* 文件過濾器
*
* @author
*
*/
class MusicFilter implements FilenameFilter {
@Override
public boolean accept(File dir, String filename) {
return (filename.endsWith(".mp3"));
}
}
//綁定音樂
void musicList(){
try{
File home=new File(MUSIC_PATH);
if(!home.exists())
home.mkdirs();
if(home.listFiles(new MusicFilter()).length>=0){
for(File file:home.listFiles(new MusicFilter())){
myMusicList.add(file.getName().toString());
}
ArrayAdapter<String> musicList=new ArrayAdapter<String>
(Activity01.this,android.R.layout.simple_list_item_1, myMusicList);
m_ListView.setAdapter(musicList);
}
}
catch(Exception ex)
{
ex.printStackTrace();
}
}
}
2. Android要求做一個一個簡易音樂播放器。用Service實現
android開發培訓一個簡單的Android音樂播放器
在這里主要是用兩個簡單的按鈕實現音樂的播放和停止功能,工程的目錄結構為:
同時添加一個文件夾,裡面放後綴為mp3的文件就可以了。 在main配置文件主要是添加兩個Button:
添加一個activity類和一個service類AndroidManifest.xml配置文件為:
創建一個MusicServiceActivity類啟動service類:中網互贏 手機客戶端
3. android怎樣做一個音樂播放器
你好,可以參考一下
本文將引導大家做一個音樂播放器,在做這個Android開發實例的過程中,能夠幫助大家進一步熟悉和掌握學過的ListView和其他一些組件。為了有更好的學習效果,其中很多功能我們手動實現,例如音樂播放的快進快退等。
http://www.jizhuomi.com/android/example/104.html
4. android音樂播放器開發問題
刪除也就從你的列表中拿到指定歌曲的position 然後從數據源中移除 新建播放列表的話你可以重新new一個List 將你要放到新建播放列表中的歌曲的地址add進去不就行了么?
5. 如何開發一款音樂播放器APP
你可以參考這個開源的音樂播放器ryanhoo/StylishMusicPlayer,不過可能有點難。慢慢看。初學者的話,先從模仿UI做起吧,然後再慢慢實現一點點的功能。比如做播放介面的時候,先做UI,然後做每個控制元件的點選事件,然後做播放音樂,等等。
你可以參考這個開源的音樂播放器ryanhoo/StylishMusicPlayer,不過可能有點難。慢慢看。初學者的話,先從模仿UI做起吧,然後再慢慢實現一點點的功能。
酷狗的歌詞逐字匹配 是因為酷狗歌詞的製作過程 你用酷狗製作過歌詞嗎? 如果你想做成一樣的 我建議你去製作一份歌詞才能明白。。。只用LRC寫 即使加點或者空格什麼的 也一定會影響美觀 如果你根據酷狗的歌詞製作步驟能寫出相關演演算法 那程式里的演演算法就好寫了。。。
學習app開發技術就可以
OooPlay 是一款極簡音樂播放器,本文是產品原型設計培訓師、OooPlay 設計者尹廣磊的分享,文中詳細闡述了OooPlay在產品原型設計和開發過程中的思維演化方式以及產畝橘友品心路歷程,在此分享給感迅槐興趣的讀者。
先談談主體設計
在開始談論如何設計出這款應用之前,先來看看OooPlay這款應用的演示視訊讓大家有個直觀的了解。看過視訊之後,因為布局或互動方式也許大家會覺得有一點酷的感覺,但本質上我們未不是在追求酷的感覺,而是始終在圍繞功能做一款隨性而緊湊的產品設計。
那下面就來還原一下,是如何一步步遞進到現在的設計結果的:
首先,iPhone自帶的音樂播放器不方便在列表上試聽歌曲,一點選就會進入到另一個播放介面。這樣想試聽幾首歌曲的話需要頻繁點選「返回」。後來注意到有這樣一款應用Panamp是在列表上直接播放的就很方便,只可惜這款應用不常用到的功能比較多,所以算不上精簡和巧妙的設計導致特色不是很突出。我想從最初的角度出發如果讓它能夠是列表的形式並能聽歌的話,只需要一個列表和播放暫停按鈕就夠了。就像下面的草圖這樣:
然而僅僅這樣是不夠的,因為隨著列表的瀏覽和滾動,如何能夠快速回到正在播放的歌曲上就變得重要,所以需要在列表的頂端或底端能有一個按鈕,可以快速定位到正在播放的歌曲上。想到必須要有這么個東西,那麼加什麼元素才能顯示不突兀多餘,又能伍薯跟整體的簡潔風格比較和諧呢?於是想到歌曲的CD畫面對於反 映正在播放的歌曲是誰很重要,而且CD畫面還能消除一些軟體介面的單調。
另外,播放中時還應該有一些動態效果以體現出正在播放中的狀態來。基於這些功能和元素的結合,想到了用CD圓盤來顯示「CD畫面」,用圓盤的轉動來 體現出「正在播放中」,用點選圓盤的邊緣來回到「正在播放的歌曲」,這樣才算達到了一種「緊湊」的設計。後面就是把播放、暫停、上一首、下一首這樣最常用的功能,融入到CD圓盤的旁邊。如下圖這樣
然而,細想之下只有這些還是不夠,因為搜尋歌曲雖然不常用,但是當需要用到時不能讓使用者從幾百首歌里找不出那首歌曲來。所以需要有搜尋功能,後面意識到還不止,還有隨機、單首迴圈等,那麼把這些功能加在什麼位置?加在頂部嗎?底部已經佔用比較多的高度了,加在頂部一下子就會擠壓到中間內容的空間,同 時讓簡潔的感覺盪然無存。我就創造性的在紙上嘗試著畫了一個側欄,把搜尋、隨機、單首迴圈放在上面。
因為覺得歌曲列表的寬度壓縮一點沒關系。沒想到這樣放的效果不錯,同時這種非對稱的設計讓CD圓盤待在那個位置特別恰當。我不想把CD圓盤放在中間那樣毫無新意的表達方式。於是有了下圖:
這樣基本的布局有了,然後繼續去細化一些功能。我個人經常聽到一首歌突然很有感覺,就想到手機里還有這個人的另外一首歌也很不錯,就想去聽一下。所以,需要有個功能可以通過一首歌找到這個人的全部歌曲。於是在歌曲名稱的後面增加一個「小人」圖示,可以搜尋這個演唱者的其它歌曲,使用搜索的方式也是為 了不額外增加介面,同時把「搜尋」這么一個不常用的功能也變得常用了。
另外,很多播放器都有了定時結束播放的功能,以便於睡覺前聽著音樂入睡。我也增加了此功能,從常用的角度只保留了30分鍾和60分鍾兩個時間檔(沙漏是倒計時結束播放)。再有就是為軟體的「關於」保留一個入口,還有因為我有藍芽立體聲耳機所以增加了AirPlay功能的支援(無AirPlay裝置時 不出現此圖示)。於是就有了下圖:
其實,在只有列表的時候我就想到讓音樂可以左右滑動以置頂置底了。這個是受Clear應用視訊的影響,Clear的設計方式真的帶給了設計師一些新的思考方向。本質上那種重要的資訊偏靠上不重要的資訊偏靠下的內容,都可以採用這種方式處理。
我個人覺得,音樂就可以恰當的使用這種方式,那些因為心情等暫時不想聽的歌曲直接右滑就可以置底,意思是「死的遠遠的」,那些比較關注想多了解的歌 曲就可以左滑把它置頂,這樣最方便找到。這樣隨性的處理,就可以讓上面的歌曲偏好聽,下面的歌曲偏不好聽。這是其它音樂播放器所做不到的,況且它使用起來是如此的簡便,這也是這個播放器最大的亮點。
同時,由於把想關注的歌曲左滑置頂了,所以也不需要再保留自帶播放器「播放列表」的功能了,因為接近頂端的位置就算是播放列表了。而且我總覺得過去「播放列表」的方式,把歌曲在多個列表間移來移去過於機械化,一點也不隨性和簡便。歌曲左右滑動見下圖:
我並沒有保留可以拖動歌曲排序的功能,因為單手那樣操作並不容易,即便要雙手來這樣操作那大概也是有強迫症思維的人才會去刻意組織每一首歌的排序。「刻意」就違背我「隨性」的原則,況且按住並拖動歌曲也會大大增加誤操作的機率。
至此該應用主要功能的設計過程應該介紹完了,簡單總結為三點:
在列表直接播放,可以快速試聽歌曲。
左右滑動可以將歌曲好聽與否快速分開。
點選演唱者圖示可以快速檢視該演唱者歌曲。
因為手機有側鍵可以控制音量,所以沒有在軟體介面上保留音量控制。聽音樂時沒想到還需要進度條,所以沒有進度條控制,不過跟自帶播放器一樣你可以按住「下一首」來快進歌曲(同時支援線控方式)。 因為OooPlay播放器只有一個主介面且全圖示設計,不需要額外的翻譯即可全球發行。基於全球使用者這樣一個市場,無法提供比較靠譜的聯網顯示歌詞服務。加上使用者iTunes自帶的音樂多數不帶歌詞且無法逐句定位顯示,所以綜上原因我們也舍棄了顯示歌詞的功能,就讓隨性的音樂響起,不必在意他唱的每一句都 是什麼。
再談談細節
為了把產品做到接近於完美,OooPlay極簡音樂播放器還有很多細節做了精心的處理,下面列舉幾點(部分內容在之前文章中介紹過,已經了解的可直接跳過):
正在播放的歌曲如果右滑,那表示不想聽,所以此歌曲會停止播放並置底,然後開始播放「下一首」歌曲;如果是正在播放的歌曲左滑,表示好聽 或想關注,所以不能夠停止播放。該歌曲需要置頂,但是該歌曲需要留在原來的位置上,因為當該首歌播放完以後需要播放下面一首歌,而不能去播放頂上的第二首歌,因為那些可能是從上聽下來剛剛聽過的歌曲。
左右滑動是全域性性的操作,在任何搜尋結果中左滑過的歌曲,回到所有歌曲列表時依然能夠在最上面找到,不必擔心只有回到那個搜尋結果才能在上面找到。
不是所有歌曲後面都顯示演唱者圖示,只有某演唱者在庫中的歌曲數量在1首以上時才會顯示,因為如果該演唱者只有一首歌曲的話,你再去搜索也沒有意義了,避免你搜索完發現還是只有一首歌曲而失望。
隨機播放時的演演算法做了特殊處理,曲庫如果有10首歌以上,最下面1首歌隨機時不會被播放到;如果有20首歌以上,最下面2首歌不會被播放到。以此類推最多會有30首最下面的歌隨機時不會被播放到。避免你隨機播放時還是會聽到你最近不想聽的歌曲。
列表的方式會有誤操作的可能,如果你錯點了一首歌曲,可以在5秒鍾以內按「上一首」,就可以回到剛才聽的歌曲,並且從斷開的位置繼續播放。5秒鍾以後,說明你大概不是誤操作,再按「上一首」就會正常跳到「上一首」歌曲上。
當一首歌快唱完的25秒以內,也就是歌曲 *** 基本唱完的時候,如果你按「上一首」按鈕,會重新播放當天歌曲。因為當快唱完的時候你按「上一首」大概是這首歌曲聽著很爽,想再來一遍。iPhone自帶的播放器是開始播放3秒鍾以後,按「上一首」重新播放當前歌曲。
如果你新同步了5首歌進到手機里,新同步的歌曲會排在原來所有歌曲的最上面。你新同步進來的歌曲大概就是馬上想聽下它們吧,所以把它們放在最上面。你原來那些歌曲的排序也都保留了,不會因為同步而讓你所有歌曲重新排序。
正如你看到的,從啟動畫面開始我們就做了連貫的動畫銜接,讓每一層含義都清晰可辯。
我們不想單單為了讓你看一下無用的「關於」資訊就多佔用一個介面,所以在那裡我們的「夜間模式」還能給你最後一層驚喜。
開發過程大致經歷了以下幾個階段:
2013-01-21 受到DailyCost激發,決定要從音樂播放器角度做個產品。
2013-01-22 上午紙上完成草圖,晚上製作出了最初的主原型介面。
2013-01-24 經朋友介紹找到我應用的開發者 rexshi,28日找到介面設計 soioi。
2013-03-03 過完春節並完成所有原型細節,回到北京。
2013-03-16 溝通完各項工作,開始進入開發階段。
2013-05-15 主體開發功能完成,放出了一個開發者版本的演示視訊。
2013-05-24 釋出了一個公測的預覽版本。
2013-06-14 提交AppStore稽核。
2013-06-21 OooPlay稽核通過上線,當天達到付費音樂榜第7名,次日達到第3名。
沒有那麼復雜啊。
我在」應用之星「網站上,做了些音樂APP。
只要上傳你的音訊檔案,很快就能生成。
小白使用者的救星~~
酷狗音樂+蝦米音樂;
網易雲音樂+蝦米音樂;
QQ音樂+蝦米音樂
酷我音樂+蝦米音樂
這樣兩兩搭配歌曲較全,如果只選一個酷狗音樂或網易雲音樂
你好 相對你的描述 覺得是酷狗 希望幫到你
酷狗音樂
6. android音樂播放器怎麼實現用戶交互
首先實現一個Service類,我們命名之為MainService,那麼我們應該如何啟動這個Service呢?啟動Service一個Service有兩種方法:一種是startService (Intent);另外一種是:bindService (Intent);
第一種啟動方式,適用於Service獨立完成任務,例如說一個下載,如果不需要暫停或者取消的話,可以這樣來做。但是,我們這是音樂播放應用,把MediaPlayer放在Service中執行播放,這樣的方式很難有暫停等交互。(其實也可以這樣做,例如每次交互操作都用startService來做,通過Intent把暫停等命令出入進去,進度條也可以通過廣播來發送出去,但是這樣做,感覺很醜陋,肯定不是常規的高效做法);
第二種啟動方式,可以在onServiceConnected中,獲得一個Service對象(可能不是一個Service對象,至少是一個可以接觸Service內部操作的句柄)。這樣,便可以輕松操作播放和接收進度通知。但是這種方式有弊端,一旦與之綁定的context退出,則綁定接觸,Service也會被回收(但是不會執行onDestory方法);
那麼是不是就只是簡單用第二種啟動方式?
當然不是這樣,在谷歌官方文檔中,有交代,這兩種方式並不沖突,而且十分適用於音樂播放類的應用。
原文如下:
A bound service
The service is created when another component (a client) calls bindService(). The client then communicates with the service through an IBinder interface. The client can close the connection by calling unbindService(). Multiple clients can bind to the same service and when all of them unbind, the system destroys the service. (The service does not need to stop itself.)
These two paths are not entirely separate. That is, you can bind to a service that was already started withstartService(). For example, a background music service could be started by calling startService() with anIntent that identifies the music to play. Later, possibly when the user wants to exercise some control over the player or get information about the current song, an activity can bind to the service by calling bindService(). In cases like this, stopService() or stopSelf() does not actually stop the service until all clients unbind.
簡單理解是:可以有多個client去綁定同一個Service,並且只有所有綁定的client都解除綁定以後,Service就會被destory掉,不需要執行stopSelf方法,同樣不會回調到onDestory方法;一個Client可以綁定一個已經start的Service,這樣綁定的話,要停止這個service,則必須先解除一切綁定的client,然後再調用stopService或者stopSelf方法。
得到官方的說法後,就可以放心大膽的寫代碼了。
為了方便,我們定義一個自己的Application類——BeApplication,來執行相關操作。
在這個Application類的onCreate方法中,我們先啟動一個Service,然後綁定這個Service。注意,讓自己的BeApplication能夠運行,要在manifest文件中的<application/>標簽下,定義android:name=」包名加我們application類的類名」。
現在寫我們用音樂播放的Service類——MainService,同樣記得在manfest文件中聲明這個Service。
注意之前在BeApplication中的onServiceConnected方法,我們在那個方法中,取得了由MainService中的onBind方法返回的IBinder對象,並通過這個對象,我們在BeApplication中拿到這個用於播放音樂的Service,這樣以來,與Service交互容易的多。
也許你會問,這樣已經拿到service對象了,那有何必要去start這個service呢?
注意MainService中的onStartCommend方法,此方法返回了一個int常量,對於這個常量,官方有這樣的解釋:
START_STICKY
If the system kills the service after onStartCommand() returns, recreate the service and call onStartCommand(), but do not redeliver the last intent. Instead, the system calls onStartCommand() with a null intent, unless there were pending intents to start the service, in which case, those intents are delivered. This is suitable for media players (or similar services) that are not executing commands, but running indefinitely and waiting for a job.