Android 實現簡單音樂播放器(一)


      今天掐指一算,學習Android長達近兩個月了,今天開始,對過去一段時間的學習收獲以及遇到的疑難雜症做一些總結。

      簡單音樂播放器是我自己完成的第一個功能較為完整的APP,可以說是我的Android學習之路上的一個小小里程碑,給我增加了很多信心(~~真容易獲得滿足~~)。從下面開始,我將詳細介紹MusicPlayer的設計過程。

      首先,先看一下這個項目的工程目錄和運行效果:

          

      從上面的圖片看到,整個工程的布局文件有兩個:activity_main.xml和musiclist.xml,其中,musiclist.xml中放置了兩個TextView,分別對應歌曲名稱和演唱者,結合activity_main.xml中的ListView,完成一張音樂文件列表。播放頁面的其他組件的布局則由activity_main.xml完成。具體如下:

     activity_main.xml:

  1 <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
  2     xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
  3     android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin"
  4     android:paddingRight="@dimen/activity_horizontal_margin"
  5     android:paddingTop="@dimen/activity_vertical_margin"
  6     android:paddingBottom="@dimen/activity_vertical_margin" tools:context=".MainActivity">
  7     <LinearLayout
  8         android:orientation="vertical"
  9         android:layout_width="fill_parent"
 10         android:layout_height="fill_parent"
 11         android:layout_alignParentBottom="true"
 12         android:layout_alignParentStart="true">
 13         <LinearLayout
 14             android:orientation="vertical"
 15             android:layout_width="fill_parent"
 16             android:layout_height="match_parent"
 17             android:layout_alignParentTop="true"
 18             android:layout_alignParentStart="true"
 19             android:layout_weight="2">
 20 
 21             <TextView
 22                 android:layout_width="wrap_content"
 23                 android:layout_height="wrap_content"
 24                 android:text="本地音樂文件"
 25                 android:id="@+id/textView"
 26                 android:textSize="25dp" />
 27 
 28             <ListView
 29                 android:layout_width="match_parent"
 30                 android:layout_height="match_parent"
 31                 android:id="@android:id/list"
 32                 android:scrollbars="vertical"
 33                 android:divider="@android:color/holo_blue_light"
 34                 android:dividerHeight="2dp"
 35                 android:drawSelectorOnTop="false"
 36                 android:choiceMode="singleChoice"/>
 37         </LinearLayout>
 38 
 39         <LinearLayout
 40             android:orientation="vertical"
 41             android:layout_width="fill_parent"
 42             android:layout_height="match_parent"
 43             android:layout_weight="3">
 44 
 45             <tina.musicplayer.AlwaysMarqueeTextView
 46                 android:layout_width="100dp"
 47                 android:layout_height="wrap_content"
 48                 android:id="@+id/nameDisplay"
 49                 android:layout_gravity="center_horizontal"
 50                 android:textSize="28dp"
 51                 android:ellipsize="marquee"
 52                 android:marqueeRepeatLimit="marquee_forever"
 53                 android:focusable="true"
 54                 android:singleLine="true"
 55                 android:layout_margin="5dp"/>
 56 
 57             <RelativeLayout
 58                 android:orientation="horizontal"
 59                 android:layout_width="match_parent"
 60                 android:layout_height="wrap_content"
 61                 android:layout_gravity="center_horizontal">
 62                 <TextView
 63                     android:layout_width="wrap_content"
 64                     android:layout_height="wrap_content"
 65                     android:text="00:00"
 66                     android:id="@+id/currTime"
 67                     android:layout_alignParentStart="true"/>
 68 
 69                 <TextView
 70                     android:layout_width="wrap_content"
 71                     android:layout_height="wrap_content"
 72                     android:text="00:00"
 73                     android:id="@+id/totalTime"
 74                     android:layout_alignParentEnd="true"/>
 75             </RelativeLayout>
 76 
 77             <SeekBar
 78                 android:layout_width="fill_parent"
 79                 android:layout_height="wrap_content"
 80                 android:id="@+id/seekBar"
 81                 android:layout_gravity="center_horizontal"
 82                 android:layout_margin="10dp"/>
 83 
 84             <RelativeLayout
 85                 android:layout_width="match_parent"
 86                 android:layout_height="wrap_content"
 87                 android:layout_gravity="center_horizontal"
 88                 android:layout_margin="20dp">
 89 
 90                 <ImageButton
 91                     android:layout_width="wrap_content"
 92                     android:layout_height="wrap_content"
 93                     android:id="@+id/previous"
 94                     android:layout_gravity="center_horizontal"
 95                     android:layout_marginStart="40dp"
 96                     android:src="@drawable/player_previous"
 97                     android:onClick="onPreviousClick"
 98                     android:background="@android:color/transparent"
 99                     android:layout_alignParentTop="true"
100                     android:layout_alignParentStart="true" />
101 
102                 <ImageButton
103                     android:layout_width="wrap_content"
104                     android:layout_height="wrap_content"
105                     android:id="@+id/stop"
106                     android:src="@drawable/player_stop"
107                     android:layout_gravity="center_horizontal"
108                     android:onClick="onStopClick"
109                     android:background="@android:color/transparent"
110                     android:layout_alignParentTop="true"
111                     android:layout_centerHorizontal="true"
112                     android:layout_toRightOf="@+id/previous"
113                     android:layout_marginStart="30dp"/>
114 
115                 <ImageButton
116                     android:layout_width="wrap_content"
117                     android:layout_height="wrap_content"
118                     android:id="@+id/play"
119                     android:layout_gravity="center_horizontal"
120                     android:src="@drawable/player_play"
121                     android:onClick="onPlayClick"
122                     android:background="@android:color/transparent"
123                     android:layout_alignParentTop="true"
124                     android:layout_toRightOf="@+id/stop"
125                     android:layout_marginStart="30dp"/>
126 
127                 <ImageButton
128                     android:layout_width="wrap_content"
129                     android:layout_height="wrap_content"
130                     android:layout_gravity="center_horizontal"
131                     android:id="@+id/next"
132                     android:src="@drawable/player_next"
133                     android:onClick="onNextClick"
134                     android:background="@android:color/transparent"
135                     android:layout_alignParentTop="true"
136                     android:layout_toRightOf="@+id/play"
137                     android:layout_marginStart="30dp" />
138             </RelativeLayout>
139         </LinearLayout>
140     </LinearLayout>
141 </RelativeLayout>
View Code

     musiclist.xml:

 1 <?xml version="1.0" encoding="utf-8"?>
 2 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
 3     android:layout_width="match_parent" android:layout_height="match_parent"
 4     android:orientation="horizontal"
 5     android:background="@drawable/selector">
 6 
 7     <TextView
 8         android:layout_width="200dp"
 9         android:layout_height="wrap_content"
10         android:text="New Text"
11         android:id="@+id/songName"
12         android:textSize="25dp"
13         android:textColor="@android:color/holo_purple"
14         android:layout_weight="2"/>
15 
16     <TextView
17         android:layout_width="200dp"
18         android:layout_height="wrap_content"
19         android:text="New Text"
20         android:id="@+id/artistName"
21         android:textSize="25dp"
22         android:gravity="right"
23         android:textColor="@android:color/holo_purple"
24         />
25 </LinearLayout>
View Code

     預覽效果:                               

          

     在播放頁面實現的過程中,主要有以下幾個重要的點:

1、自動水平滾動的TextView

     為了增加音樂播放器的趣味性,我放置了一個可以水平滾動的TextView,用來顯示當前選中的歌曲名稱,這也就是常常說的走馬燈的文字效果。那么如何實現呢?

     首先,新建一個TextView的子類(AlwaysMarqueeTextView),重寫isFocusd()方法,使得該類對象始終獲得焦點。

 1 package tina.musicplayer;
 2 
 3 import android.content.Context;
 4 import android.util.AttributeSet;
 5 import android.widget.TextView;
 6 
 7 /**
 8  * Created by CW3479 on 2015/4/2.
 9  */
10 public class AlwaysMarqueeTextView extends TextView {
11     public AlwaysMarqueeTextView(Context context) {
12         super(context);
13     }
14 
15     public AlwaysMarqueeTextView(Context context, AttributeSet attrs) {
16         super(context, attrs);
17     }
18 
19     public AlwaysMarqueeTextView(Context context, AttributeSet attrs, int defStyleAttr) {
20         super(context, attrs, defStyleAttr);
21     }
22 
23     @Override
24     public boolean isFocused() {
25         return true;
26     }
27 }
View Code

     然后,在布局文件中,放置AlwaysMarqueeTextView,設置屬性:

  android:ellipsize="marquee"     
  android:marqueeRepeatLimit="marquee_forever"
  android:focusable="true"
  android:singleLine="true"

    以上,可以實現程序運行時,選中歌曲,歌曲名就能自動從右往左重復滾動。需要注意的是,只有當AlwaysMarqueeTextView中的文字超過其能夠顯示的長度時,文字才能開始滾動。所以android:layout_width="100dp"屬性需要設置為合適的值。

    關於跑馬燈效果,還可以參考一下網絡上的這篇文章。http://www.cnblogs.com/Gaojiecai/archive/2013/06/18/3142783.html

2、音樂文件列表

     為了完成音樂文件列表的呈現,我用到了ListActivity,在布局文件activity_main.xml中,放置的ListView,設置屬性:

    android:id="@android:id/list"    這里的id一定要設置成"@android:id/list",才能使其綁定到ListActivity
    android:scrollbars="vertical"     使list長度超過ListView的顯示高度時,ListView能夠垂直滾動
    android:divider="@android:color/holo_blue_light"  list中每一行之間的分割線
   android:dividerHeight="2dp"
    android:choiceMode="singleChoice" 設置選擇模式為單選
    android:drawSelectorOnTop="false" 使選中某一項時,選中背景不覆蓋當前文字使用

    現在,我們已經有了ListView和musiclist.xml中的兩個TextView,具體如何使用到程序中呢?

    (1)定義全局變量

1     private ListView musicListView;
2     private SimpleAdapter listAdapter;
3     private List<HashMap<String,String>> list=new ArrayList<HashMap<String,String>>();

     (2)MainActivity繼承ListActivity,設置ListAdapter。

1 musicListView=(ListView)findViewById(android.R.id.list);
2 listAdapter=new SimpleAdapter(MainActivity.this,list,R.layout.musiclist,new String[]{"name","artist"}, new int[]{R.id.songName,R.id.artistName});
3 MainActivity.this.setListAdapter(listAdapter);

     至此,完成一個音樂播放列表的基本框架。下面,再增加一點小功能。

   在點擊列表時,我希望能區別出選中的項,即:選中一首歌曲時,該項的背景變成另一種顏色。如何實現這種功能?

      (1)在res/drawable文件夾中新建一個selector.xml文件,在里面定義TextView的不同狀態下的背景。

      (2)在musiclist.xml中,設置LinearLayout的屬性android:background="@drawable/selector"

     selector.xml:

 1 <?xml version="1.0" encoding="utf-8"?>
 2 <selector xmlns:android="http://schemas.android.com/apk/res/android">
 3     <!--被選中時的布局-->
 4     <item
 5         android:state_activated="true">
 6         <shape>
 7             <gradient
 8                 android:angle="270"
 9                 android:endColor="#99BD4C"
10                 android:startColor="#C1C125"
11                 />
12             <corners
13                 android:radius="8dp"
14                 />
15         </shape>
16         </item>
17     <!--默認的布局-->
18     <item>
19         <shape>
20             <gradient
21                 android:angle="270"
22                 android:endColor="#A8C3B0"
23                 android:startColor="#C0CFCE"
24                 />
25             <corners
26                 android:radius="8dp"
27                 />
28         </shape>
29     </item>
30 
31 </selector>
View Code

     需要注意的是,區分列表項是否選中的屬性是:"android:state_activated",當這個屬性的值為true時,表明選項被選中。

  以上,基本完成了音樂播放器的頁面設計。在下一篇文章Android 實現簡單音樂播放器(二)中,我將介紹音樂播放器的功能實現。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM