[안드로이드] 프래그먼트(fragment) 예제

2018. 1. 17. 20:52 안드로이드/프래그먼트(Fragment)

[안드로이드] 프래그먼트(fragment) 예제



실습1 - 레이아웃에 의한 프래그먼트 추가(이벤트 전달)
 

  • 앱의 메인화면 출력 -> activity_fragmentdemo.xml, FragmentDemo.java
  • 프래그먼트 리스트영역 -> ListFrag.java
    (ListFragment 클래스로 작성하기 때문에 별도의 XML 레이아웃이 필요 없음)
  • 프래그먼트 자세히보기 영역 -> DetailFrag.java, detail.xml
  • 클릭이벤트 처리를 위한 리스너 -> OnListItemSelectedListener.java

1) activity_fragmentdemo.xml - 메인화면 레이아웃
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
 
    <!--프래그먼트는 시스템에서 사용할 수 있는 고유식별자가 필요함-->
    <fragment
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:layout_weight="1"
        android:id="@id/android:list"
        class="com.example.chae.finaltest.ListFrag" />
 
    <fragment
        android:layout_width="0dp"
        android:layout_height="match_parent"
        android:layout_weight="4.5"
        android:id="@+id/detail"
        class="com.example.chae.finaltest.DetailFrag" />
 
</LinearLayout>


2) detail.xml - 오른쪽 프래그먼트

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#ff33aa99">
 
    <TextView
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:id="@+id/tv"
        android:layout_gravity="center_horizontal|center_vertical"
        android:layout_marginTop="20dp"
        android:text="자세히 보기"
        android:textColor="#ff0000"
        android:textSize="20dp"
        android:textStyle="bold"/>
 
</LinearLayout>


3) DetailFrag.java - 프래그먼트를 위한 xml 레이아웃을 전개inflation 하기 위한
                              fragment 클래스를 상속한 자바 코드


public class DetailFrag extends Fragment {
 
    @Nullable
    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        return inflater.inflate(R.layout.detail, container, false);
    }
 
    public void setText(String item){
        TextView tv = (TextView) getView().findViewById(R.id.tv);
        tv.setText(item); //detail.xml에 있는 텍스트뷰에 텍스트를 설정
    }


4) OnListItemSelectedListener.java
: 프래그먼트에서 사용자와 상호작용하기 때문에 프래그먼트에서 이벤트가 발생
: 프래그먼트에서 발생한 이벤트를 호스트 액티비티와 공유
-> 인터페이스를 정의하고 액티비티에서 인터페이스를 구현
public interface OnListItemSelectedListener {
    public void onListItemSelected(int position);
}



5) ListFrag.java - 왼쪽 리스트 프래그먼트


public class ListFrag extends ListFragment {
    OnListItemSelectedListener listener;
 
    //프래그먼트를 액티비티에 부착할 때 시스템이 호출하는 메소드
    @Override
    public void onAttach(Activity activity) {
        super.onAttach(activity);
        try{
            //호스트 액티비티의 인터페이스 구현 여부를 확인
            listener = (OnListItemSelectedListener) activity;
        }
        catch (ClassCastException e){
            throw new ClassCastException(activity.toString()
                    + "must implement OnListItemSelectedListener interface");
        }
    }
 
    //프래그먼트가 생성될 때 호출
    @Override
    public void onActivityCreated(Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
 
        //리스트 어댑터와 숫자 배열을 사용하여 왼쪽의 프래그먼트 화면 생성
        setListAdapter(new ArrayAdapter<String>(getActivity(),
                android.R.layout.simple_list_item_1,
                new String[] {"1""2""3""4""5"}));
    }
 
    //리스트 화면에서 하나의 항목을 선택하면 호출되는 콜백 메소드
    //프래그먼트에서 발생한 이벤트를 액티비티에게 전달
    @Override
    public void onListItemClick(ListView l, View v, int position, long id) {
        listener.onListItemSelected(position);
    }
}


6) FragmentDemo.java
package com.example.chae.finaltest;
 
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
 
public class FragmentDemo extends AppCompatActivity implements OnListItemSelectedListener {
 
    //자세히보기 프래그먼트에 나타날 내용을 문자열 배열로 정의
    String[] numbers = new String[] {"One""Two""Three""Four""Five"};
 
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_fragmentdemo);
    }
 
    @Override
    public void onListItemSelected(int position) {
 
        //프래그먼트 관리자를 가져와 R.id.detail라는 리소스id를 이용해 
        // 오른쪽 프래그먼트의 레퍼런스를 detail 변수에 할당
        DetailFrag df = (DetailFrag) getFragmentManager().findFragmentById(R.id.detail);
 
        //DetailFrag 인스턴스가 null이 아니고 <fragment> 엘리먼트를 통한 
        // 액티비티 뷰 계층 구조 레이아웃의 일부인지 확인
        if(df != null && df.isInLayout()){
            df.setText(numbers[position]);
        }
    }
}


* FragmentManager 객체 
: 프래그먼트를 액티비티에 추가하거나 바꾸거나 삭제할 때 사용할 수 있음

 


실습2  - 실습1에 자세히보기 페이지에 텍스트와 이미지 출력 추가 

 


1) detail.xml - 이미지뷰 추가


<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#ff33aa99">
 
    <TextView
        android:layout_width="wrap_content"
        android:layout_height="0dp"
        android:layout_weight="1"
        android:id="@+id/tv"
        android:layout_gravity="center"
        android:layout_marginTop="20dp"
        android:text="자세히 보기"
        android:textColor="#ff0000"
        android:textSize="20dp"
        android:textStyle="bold"/>
    
    <ImageView
        android:layout_width="wrap_content"
        android:layout_height="0dp"
        android:layout_weight="9"
        android:id="@+id/iv"/>
 
</LinearLayout>


2) DetailFrag.java - setImage 메소드 추가

public class DetailFrag extends Fragment {
 
    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        return inflater.inflate(R.layout.detail, container, false);
    }
 
    public void setText(String item){
        TextView tv = (TextView) getView().findViewById(R.id.tv);
        tv.setText(item); //detail.xml에 있는 텍스트뷰에 텍스트를 설정
    }
 
    public void setImage(int rscID){
        ImageView iv = (ImageView) getView().findViewById(R.id.iv);
        iv.setImageResource(rscID);
    }
}


3) FragmentDemo.java - 이미지들의 리소스id 추가

public class FragmentDemo extends AppCompatActivity implements OnListItemSelectedListener {
 
    //자세히보기 프래그먼트에 나타날 내용을 문자열 배열로 정의
    String[] numbers = new String[] {"오예""흑흑""크앙"};
    int[] imgRsc = {R.drawable.duck_fun, R.drawable.duck_sad, R.drawable.green_ang};
 
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_fragmentdemo);
    }
 
    @Override
    public void onListItemSelected(int position) {
 
        //프래그먼트 관리자를 가져와 R.id.detail라는 리소스id를 이용해
        // 오른쪽 프래그먼트의 레퍼런스를 detail 변수에 할당
        DetailFrag df = (DetailFrag) getFragmentManager().findFragmentById(R.id.detail);
 
        //DetailFrag 인스턴스가 null이 아니고 <fragment> 엘리먼트를 통한
        // 액티비티 뷰 계층 구조 레이아웃의 일부인지 확인
        if(df != null && df.isInLayout()){
            df.setText(numbers[position]);
            df.setImage(imgRsc[position]);
        }
    }
}


출처 : http://blog.naver.com/kcwwck77/220560002178