您的位置:首页 > 移动开发 > Android开发

Android 音乐播放器的开发教程(四)Activity和Fragment的通信以及Fragment的切换 ----- 小达

2014-12-26 23:50 661 查看

Activity和Fragment的通信以及Fragment的切换

在上一篇的博客中讲到了,播放器的主界面布局,是由一个activity和一个fragment构成的,activity启动的时候,在其onCreate()方法里就会创建一个fragment的实例对象,并显示在activity中的,这样的一个好处就是处于activity上的控制台(控制上一首/下一首等的按钮)可以不随着fragment的切换而变化,会一直固定在这个播放器的界面上,避免了在好多个activity里都重复写这个控制台.

这一篇博客主要讲的是activity和fragment之间的通信,还有如何用FragmentManager和FragmentTransaction实现Fragment之间的切换.



在开始之前,先新建一个类名为AppConstant,和它的名字一样,这个类专门用来存放需要用到的常量:

public interface AppConstant {
    public class PlayerMsg{
        public static final int PLAY_MSG = 1;                      //开始播放
        public static final int PAUSE = 2;                         //暂停播放
        public static final int PREVIOUS_MUSIC = 3;                //上一首
        public static final int NEXT_MUSIC = 4;                    //下一首
        public static final int LOOP_MODE = 5;                     //循环播放
        public static final int RANDOM_MODE = 6;                   //随机播放
        public static final int CHANGE_TO_MY_MUSIC_FRAGMENT=7;     //更换fragment消息
        public static final int LIST_CLICK = 8;                    //列表点击
        public static final int BACK_TO_MAIN_FRAGMENT=9;           //回退到主fragment
        public static final int DISMISS_CLICK = 10;                //回退到主fragment
        public static final int FRAGMENT_RANDOM_PLAY = 11;         //小卷毛点歌
        public static final int ADD_TO_F***ORITE = 12;              //加入我的最爱
        public static final int DELETE_FROM_F***ORITE = 13;         //删除我的最爱
    }

    public class NotificationMsg{
        public static final String NOTIFICATION_PREVIOUS_MUSIC = "PREVIOUS";
        public static final String NOTIFICATION_NEXT_MUSIC = "NEXT";
        public static final String NOTIFICATION_PAUSE_MUSIC = "PLAY";
        public static final String NOTIFICATION_EXIT = "EXIT";
    }
}




在上一篇开发的基础之上,再新建一个Fragment命名为MyMusicFragment,得到了一个fragment_my_music.xml和一个MyMusicFragment.java文件,布局就不多说了,一眼就能看穿的简单布局.

布局的效果大概如下图所示:




其中的fragment_my_music.xml文件布局如下代码:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/music_list_layout"
    android:layout_gravity="center_horizontal"
    android:orientation="vertical"
    android:layout_height="fill_parent"
    android:layout_width="fill_parent"
    android:background="@drawable/bg_photo_01">

    <RelativeLayout
        android:id="@+id/top_layout"
        android:background="#00000000"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">

        <ImageView
            android:id="@+id/top_layout_right_ImageView"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:background="@drawable/img_actionitem_back"/>

        <AutoCompleteTextView
            android:id="@+id/auto_text_view"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:gravity="center"
            android:textSize="7pt"
            android:textColor="@color/tomato"
            android:hint="请输入歌曲名"
            android:completionThreshold="1"
            android:layout_toRightOf="@id/top_layout_right_ImageView"
            android:layout_toEndOf="@id/top_layout_right_ImageView"
            android:layout_toLeftOf="@+id/find_music_button"
            android:layout_toStartOf="@+id/find_music_button"
            android:layout_alignBottom="@+id/find_music_button" />

        <ImageButton
            android:id="@+id/find_music_button"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:background="@drawable/img_search"
            android:layout_centerVertical="true"
            android:layout_alignParentRight="true"
            android:layout_alignParentEnd="true" />

    </RelativeLayout>

    <RelativeLayout
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_below="@id/top_layout">

        <ListView
            android:id="@+id/music_list"

            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:divider="#ffff99c9"
            android:dividerHeight="2dp"
            android:drawSelectorOnTop="false"
            android:listSelector="@color/cornsilk">
        </ListView>
    </RelativeLayout>

</RelativeLayout>


布局文件中的<AutoCompleteTextView>是后面用于快速查询歌曲的一个自动补全TextView,暂时可以不用管,而<ListView>就是我们用于显示歌曲列表的地方,在下一篇博客中会讲到.

在MyMusicFragment中有一个回退到MainFragment的按钮,注册的方法也是类似的,直接给出源代码:

@Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {

        View rootView = inflater.inflate(R.layout.fragment_my_music, container, false);

        rootView.findViewById(R.id.top_layout_right_ImageView).                                                  //切换至我的音乐Fragment
                setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                mListener.onMyMusicFragmentInteraction(AppConstant.PlayerMsg.BACK_TO_MAIN_FRAGMENT);
            }
        });

        return rootView;
    }


我们需要实现的Fragment切换是,在MainActivity中将已经显示出来的一个MainFragment实例切换成一个新创建的MyMusicFragment,先要实现的是用户的点击响应时间,由于是在MainFragment上的点击事件,也就是 我的音乐 按钮的点击事件,应该在MainFragment上注册相应的监听器,但是Fragment里面又没有像Activity里那样直接findViewById的方法,于是小达就上网查资料,发现Fragment里面会有一个这样的内置函数,

@Override
    public View (LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // Inflate the layout for this fragment

        
        return inflater.inflate(R.layout.fragment_my_music, container, false);
    }


当第一次绘制Fragment的UI时系统调用这个方法,必须返回一个View,如果Fragment不提供UI也可以返回null。

对Fragment上的按钮监听器就在这个里面注册,例如如下代码所示:

@Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {

        View rootView = inflater.inflate(R.layout.fragment_main, container, false);

        rootView.findViewById(R.id.myMusicButton).                                                  //切换至我的音乐Fragment
                setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                mListener.onMainFragmentInteraction(AppConstant.PlayerMsg.CHANGE_TO_MY_MUSIC_FRAGMENT);
            }
        });

        return rootView;
    }


这里的按钮监听器已经加在按钮上之后,切换到activity中实现Fragment接口的位置,,做出切换fragment的动作...

在这里需要注意的是,activity部分要加一个实现接口的代码.

public class MainActivity extends ActionBarActivity

implements MainFragment.OnFragmentInteractionListener,

MyMusicFragment.OnFragmentInteractionListener{

..........

.....

}

/*
    这个方法是activity和fragment通信的一种方法
    在MainFragment中调用这个方法,可以在activity中做出相应的反应
     */
    public void onMainFragmentInteraction(int msg){

        /*
        对其中的参数msg做出判断,如果为CHANGE_TO_MY_MUSIC_FRAGMENT
        则执行跳转
         */
        if(msg == AppConstant.PlayerMsg.CHANGE_TO_MY_MUSIC_FRAGMENT){

            /*
            在这里并没有直接切换Fragment
            而是调用了activity实现MyMusicFragment的那个接口
            对后面的开发能带来一点便利之处
             */
            onMyMusicFragmentInteraction(AppConstant.PlayerMsg.CHANGE_TO_MY_MUSIC_FRAGMENT);
        }
    }

   public void onMyMusicFragmentInteraction(int msg){

        myMusicFragment = new MyMusicFragment();       //创建了MyMusicFragment的实例
        FragmentManager fragmentManager = getFragmentManager();   //得到FragmentManager
        FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction(); //得到fragmentTransaction
        

        if(msg == AppConstant.PlayerMsg.CHANGE_TO_MY_MUSIC_FRAGMENT){

            fragmentTransaction.replace(R.id.fragment_layout, myMusicFragment);
            fragmentTransaction.addToBackStack(null);        //这句话是将被替换的MainFragment加入到一个专门存放fragment的栈中,在回退的时候显示上一个Fragment
            fragmentTransaction.commit();
        }

        if(msg == AppConstant.PlayerMsg.BACK_TO_MAIN_FRAGMENT){

            fragmentTransaction.replace(R.id.fragment_layout, mainFragment);
            fragmentTransaction.addToBackStack(null);
            fragmentTransaction.commit();
        }
    }


到这里为止,就可以实现两个fragment之间的自由切换了,有什么问题的话直接给我留言或者Q我,2319821734.我会尽力回答的,有什么好的建议或者意见也可以向小达提出,我会改正的..233333,下一篇博客将介绍怎么从音乐库中将本地音乐抓出来,放在我们今天写出来的MyMusicFragment中..今天就写这么多啦,各位,886....


                                            
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐