Home » Android -5. Intent 및 데이터 전달

Android -5. Intent 및 데이터 전달

어플리케이션 구성요소를 호출하거나 메시지를 보낼 때 사용하고, 정보의 형태에 따라 명시적 인텐트(Explicit Intent)와 암시적 인텐트(Implicit Intent)로 나뉜다.

5.1. 명시적 인텐트(Explicit Intent)

  • 호출 대상 컴포넌트의 이름이 명시되어 있는 인텐트, 즉 어떤 것을 호출해야 할지 명시되어 있는 인텐트

<step3/IntentSample1>

[php]
// xml에 정의 된 id를 통해 TextView, Button 객체 생성
TextView intentText1 = (TextView) findViewById(R.id.intentSampleTextView1);
Button intentBtn = (Button) findViewById(R.id.intentSampleButton1);
// 넘어온 데이터 받기
String getData = StrUtil.isNullCheck(getIntent().getStringExtra("data")); (1)
// TextView에 넘어온 데이터를 설정
intentText1.setText(intentText1.getText() + "\n" + getData);
// 버튼의 이벤트 리스너
intentBtn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// 인텐트 객체 생성 및 이동 할 액티비티 설정
Intent intent = new Intent(IntentSample1.this, IntentSample2.class); (2)
// 전달할 데이터 설정
String data = "before activity => IntentSample1";
intent.putExtra("data", data); (3)
startActivity(intent); (4)
}
});
[/php]

번호 설명
(1) 이전 Activity에서 넘겨온 데이터를 받는다.
(2) Intent 객체 생성
첫번째 인자로 context 객체, 두번째 인자로 이동할 Activity를 설정
(3) putExtra(key, value) 형태로 데이터를 담아준다.
(4) Activity 실행. 예제에서는 IntentSample2로 이동한다.



그림 24. 명시적 Intent

<step3/IntentSample4>

[php]
// 버튼의 이벤트 리스너
intentBtn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// 인텐트 객체 생성 및 이동 할 액티비티 설정
Intent intent = new Intent(IntentSample4.this, IntentSample5.class);
// 전달할 데이터 설정
String data = "before activity => IntentSample4";
intent.putExtra("data", data);

startActivityForResult(intent, REQ_CODE); (1)
}
});
}

// 이전 액티비티에서 빠져나온후 결과를 받는 메소드
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data); (2)

Logger.i("requestCode : " + requestCode);
Logger.i("resultCode : " + resultCode);

// 이전 액티비티로 부터 얻은 request, result code로 판단 (3)
if (requestCode == REQ_CODE) {
if (resultCode == RES_CODE) {
intentText4.setText(intentText4.getText() + "\n" + data.getStringExtra("data"));
}
}

}
[/php]

번호 설명
(1) startActivityforResult로 Activity를 실행할 경우 실행 된 Activity가 끝난 후 Activity가 다시 띄어질 때 onActivityResult 메소드가 실행 되어진다. 일자로 Request code를 정의해준다.
(2) startActivityforResult로 실행 된 Activity가 끝나고 돌아올 때 실행된다.
(3) Request code와 Result Code로 비교한 후 맞다면 필요한 처리를 한다.(예제에서는 TextView의 text를 설정)

<step3/IntentSample5>

[php]
// 버튼의 이벤트 리스너
finishBtn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent();
intent.putExtra("data", "finish");

// setResult를 해주면 이 액티비티를 부른 액티비티의 onActivityResult 메소드가 실행 된다.
setResult(RES_CODE, intent); (1)
finish();(2)
}
});
[/php]

번호 설명
(1) startActivityForResult 메소드로 온 경우 다시 이전 Activity로 갈 때 데이터를 전해 주고 싶을 경우 setResult(request code, intent)를 설정해준다.
(2) 현재 Activity를 종료한다.

5.2. 암시적 인텐트(Inplicit Intent)

  • 호출할 컴포넌트를 정확히 아는 것이 아니라 인텐트 객체 내에 호출 대상 컴포넌트를 찾을 수 있는 정보들만 들어있는데 인텐트 객체 내의 이러한 정보들은 호출 대상 컴포넌트가 “어떤 작업을 처리할 수 있는지”, “어떤 유형의 데이터를 처리할 수 있는지” 그리고 “처리할 데이터가 있는 주소”를 주로 담고 있다.

<step3/IntentSample6>

[php]
intent = new Intent(Intent.ACTION_DIAL, Uri.parse("tel:010-0000-0000")); (1)
startActivity(intent);
[/php]

번호 설명
(1) action은 "행동"을 뜻한다. 호출 대상 컴포넌트가 처리해줬으면 하는 작업이 action에 정의된다. 예제에서는 ACTION_DIAL을 호출하면 전화 Activity가 띄어지게 되고 자동으로 010-0000-0000이 입력되어 나타나게 된다.


그림 25. 암시적 Intent

참고. URI(Uniform Resource Identifier)
– URI는 어떤 자원을 나타내는 유일한 주소. URL(Uniform Resource Location) 또한 URI의 하위개념으로 인터넷의 특정 페이지를 나타내는 주소가 URL인것과 마찬가지로, 안드로이드 시스템 내의 자원의 주소를 표현하는 하나의 방식이다.

5.3. Intent의 Flag

  • 일반적으로 Intent를 사용하여 Activity를 띄우면 스택에 계속 쌓이게 된다. 즉, Activity A -> Activity B -> Activity C -> Activity A 를 띄었다면 스택에는 A->B->C->A의 상태로 쌓여있고 A를 끝내면 C가, C를 끝내면 B가 나타나게 된다. 하지만 상황에 따라서는 C->A를 부를 때 이전에 있던 A를 다시 불러내서 사용하고 싶을 수도 있고 C->A로 갈 때 이전에 있던 Activity B, C를 없애야 할 때도 있다. 이를 처리할 수 있는 것이 Intent의 FLAG이다.

<step3/IntentSampleAddFlag>

[php]
Intent intent = new Intent(IntentSampleAddFlag.this, MainActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP|Intent.FLAG_ACTIVITY_SINGLE_TOP); (1)
startActivity(intent);
[/php]

번호 설명
(1) FLAG_ACTIVITY_CLEAR_TOP과 FLAG_ACTIVITY_SINGLE_TOP을 설정하여 이전의 액티비티를 없애도록 설정

자주 쓰이는 FLAG의 종류

  • FLAG_ACTIVITY_NEW_TASK:
    동일 affinity의 task가 있으면 그곳에 실행되고 아니면 새로운 task를 실행

  • FLAG_ACTIVITY_SINGLE_TOP:
    액티비티를 호출 할 경우 호출 된 엑티비티가 현재 태스크의 최상단에 존재하고 있었다면 새로운 인스턴스를 생성하지 않는다. 예를 들어 ABC가 액티비티 스택에 존재하는 상태에서 C를 호출하였다면 여전히 ABC가 존재하게 된다. 실행시 재사용 액티비티의 실행은 onPause(), onNewIntent(), onResume() 순으로 호출된다
    ☞ [B]를 single top설정: [A][B] 상태에서 [B] 호출시 => [A][재사용된B]
    ☞ [B]를 single top설정: [B][A] 상태에서 [B] 호출시 => [B][A][B]

  • FLAG_ACTIVITY_NO_HISTORY:
    해당 액티비티는 재활성화시(back키를 눌러 다시 활성화될때) pop 된다
    ☞ [B]를 no history설정: [A][B][A] 상태에서 back키 사용시 [A]가 pop 되고 [B] 역시
    no history에 의해 pop => [A]

  • FLAG_ACTIVITY_REORDER_TO_FRONT:
    activity 호출시 이미 같은 activity가 task내에 있으면 같은 activity는 pop 시키고 해당 activity가 push 된다
    ☞ [A]를 reorder to front설정: [A][B] 상태에서 [A] 호출시 같은 activity인 [A]가 pop되고 => [B][A]

  • FLAG_ACTIVITY_CLEAR_TOP:
    해당 task에 있는 모든 activity를 pop 시키고 해당 activity가 root activity로 task에 push된다
    ☞ [A]를 clear top설정: [A][B] 상태에서 [A] 호출시 모두 pop되고 => [A]
    단, 해당 플래그는 액티비티를 모두 onDestroy() 시킨 후 새롭게 onCreate() 시키기 때문에 [A]를
    유지하려면 FLAG_ACTIVITY_SINGLE_TOP 플래그와 함께 사용하면 된다