[ 문제 상황 ]
EditText 를 통해 사용자 입력을 받아 Intent 로 데이터를 넘겨 받아오는 과정에서 getStringExtra()를 사용하면 데이터가 null 이 되는 것을 알게되었다.
이유는 무엇일까?
[ 해결 과정 ]
디버깅을 통해 일단 (1) 데이터가 잘 전달되는지 (2) 잘 받아와지는지 확인하였다.
1) 데이터가 잘 전달되는지 확인하기
moveTopicList 는 TopicListFragment 로 데이터를 전달해주는 Intent 객체이다.
mExtras 를 확인해보면 Bundle 안에 topic=주제입력 으로 잘 들어가있는 것을 확인할 수 있다.
2) 데이터가 잘 받아와지는지 확인하기
데이터를 받는 화면인 TopicListFragment 에서 디버깅해보면 일단 해당 Intent 의 mExtras 에 데이터가 있는 것을 확인할 수 있다.
근데 저장된 topic 을 보면 넘어와야 할 "주제입력"이 아닌 null 이 된 것을 볼 수 있다.
왜지? 이전에는 잘 사용했는데 말이야! 그래서 이전의 코드와 현재 코드를 비교해보았다.
3) 수정 전 getStringExtra() 를 사용할 때의 코드 살펴보기
// TopicDialogActivity.kt
val topic = Topic(inputText.text.toString(), selectedColor, DateFormat.currentDateFormat())
if (StringFormat.checkLengthOfTopic(topic.topic.length)) {
val moveTopicList = Intent(this, TopicListFragment::class.java)
moveTopicList.putExtra("topic", topic.topic)
moveTopicList.putExtra("color", topic.color)
moveTopicList.putExtra("date", topic.registDate)
setResult(TopicListFragment.INTENT_RESULT_TOPIC, moveTopicList)
finish()
}
Topic 객체를 생성한 후 -> 해당 객체의 변수에 접근하여 putExtra 를 통해 Intent 에 데이터를 넣었다.
4) 수정 후 지금 코드 살펴보기
// TopicListFragment.kt
val inputTopic = inputText.text
if (StringFormat.checkLengthOfTopic(inputTopic.length)) {
val moveTopicList = Intent(this, TopicListFragment::class.java)
moveTopicList.putExtra("topic", inputTopic)
setResult(TopicListFragment.INTENT_RESULT_TOPIC, moveTopicList)
}
Topic 객체를 미리 만들 필요가 없다고 생각되어서 EditText 를 통해 입력받은 데이터만 전달하는 것으로 수정했다.
달라진 부분은 putExtra() 메서드에 argument 를 넣을 때
(1) 객체의 변수(String 타입)를 넣었는지
(2) EditText 의 getText() 를 통해 바로 데이터를 넣었는지
이 부분이 달라져서 문제가 발생했던 것이다.
5) putExtra() 메서드 살펴보기
가장 먼저 수정 전 코드에서 Topic의 topic 변수는 String 타입이기 때문에 Intent 에 putExtra 를 하게되면
// Intent.java
public @NonNull Intent putExtra(String name, @Nullable String value) {
if (mExtras == null) {
mExtras = new Bundle();
}
mExtras.putString(name, value);
return this;
}
위와 같이 value 의 타입이 String 인 putExtra 를 통해 Bundle 에 putString() 으로 데이터를 저장하게 된다.
그러므로 String 의 값이 저장되어 있었기 때문에 getStringExtra() 로 데이터에 접근하여 받아올 수 있었다.
하지만 수정 후의 코드에서는 가장 먼저 EditText 의 데이터를 .getText() 를 통해 받아왔는데
// EditText.java
public Editable getText() {
CharSequence text = super.getText();
// This can only happen during construction.
if (text == null) {
return null;
}
if (text instanceof Editable) {
return (Editable) super.getText();
}
super.setText(text, BufferType.EDITABLE);
return (Editable) super.getText();
}
CharSequence 타입으로 데이터가 저장되어 지는 것을 알 수 있다.
Intenet 에 putExtra() 메서드를 통해 데이터를 넣어보려해도 나는 value 의 타입이 String 이 아닌 CharSequence 타입을 파라미터로 받는 putExtra() 가 호출되었던 것이다.
// Intent.java
public @NonNull Intent putExtra(String name, @Nullable CharSequence value) {
if (mExtras == null) {
mExtras = new Bundle();
}
mExtras.putCharSequence(name, value);
return this;
}
CharSequence 타입의 데이터를 Intent 에서 받아오려면
// Intent.java
public @Nullable CharSequence getCharSequenceExtra(String name) {
return mExtras == null ? null : mExtras.getCharSequence(name);
}
getCharSequenceExtra() 를 사용해야 한다.
확인 차 getCharSequenceExtra() 를 통해 다시 테스트를 해보자면
이번 입력 데이터는 "주제 입력 테스트"
topic 부분에 null 이 아닌 "주제 입력 테스트" 가 잘 들어온 것을 확인할 수 있다!
[ 결론 ]
데이터의 타입이 일치하지 않아서(CharSequence != String) Intent 의 getStringExtra() 를 통해서는 데이터를 받아올 수 없었던 것이다.
getStringExtra() 가 아닌 getCharSequenceExtra() 를 사용하면 데이터를 받아볼 수 있다!
'Android > note' 카테고리의 다른 글
[Android] Parameter specified as non-null is null (0) | 2023.09.28 |
---|---|
[Android] Room Database 버전 올리기 그런데 오류를 곁들인 .. (Migration didn't properly handle) (0) | 2023.09.15 |
[Android] MVP 디자인 패턴에서 View 와 Presenter 는 왜 꼭 1:1로 대응되어야 할까? (0) | 2023.09.10 |
[Android] Room Database 마이그레이션 도오전 (0) | 2023.08.30 |
[Android] SupportFragmentManager 파도타기 (0) | 2023.06.18 |