-
Notifications
You must be signed in to change notification settings - Fork 3
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
6주차 산출물입니다 #38
6주차 산출물입니다 #38
Conversation
- calendarView 상단바 수정 - diary_edit 이모지 크기 수정 - 검색창 서치바 크기 및 아이콘 수정
style: fix margin
- 친구 찾기에 구현 - 테스트용 더미데이터 추가
- fab 버튼 구현 - 친구 요청 목록 구현 - 이슈 : 앱에서 "<" 버튼을 누를때는 잘 동작하는데, 핸드폰에서 뒤로가기하면 fab이 나타났다가 사라지는 현상 발생
- fcm을 사용해 자동기록 될 때마다 알림이 오면 이모지를 눌러서 이모지가 기록될 수 있는 기능의 초기 구현 - 이슈: 백그라운드에서 기본으로 설정된 알림이 옴 - 이슈: 잠금화면에서 알림 확장할 때, 상단바가 내려옴
fab 추가, 잠금화면 알림, members api 처리
카카오 로그인 백엔드 Post
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
6주차도 고생많으셨습니다.
코드는 먼저 머지해두겠습니다. 코멘트는 별도로 확인 부탁드립니다.
FAB의 기본동작이 PopupWindow or Dialog로 동작했던것으로 기억합니다. 그래서, 상호작용이 있었거나 여백을 누르거나 했을때는 shrink되는 동작으로 되는게 default 였던거 같고, 이걸 커스텀 하기 보다는, expand값을 fragment에서 가지고 있으니, onResume이나 onRestart 혹은 다른 화면으로 갔다왔을때 해당 값을 참고해서 새롭게 expand 메소드를 호출할 수 있게 하는건 어떨까 합니다.
아하, 잠금화면 일때 상호작용 가능하게 하기 보다는 (잠금을 풀었을때만 동작하는게 기본이었던거 같습니다) 이슈에 적힌대로 구현을 하려면 알림보다는 위젯으로 구현을 해야할것 같습니다. 유튜브 / 유튜브 뮤직을 참고했을때의 모습처럼 상호작용 가능한 위젯이 되는것이죠.
remote view를 사용하더라도 알림은 정보성 조회를 하기위한 기능이라 상호작용을 직접하도록 하기 보다는 클릭했을때 앱이 실행된다거나 했었고, 앱을 키지 않아도 앱내 기능을 사용하게 하려면, 알림은 그 범위를 넘어선것이 아닌가 하는 느낌이 들긴하네요
이슈 #36
@settle54 36번 이슈페이지에 코멘트를 추가했ㅅ브니다. 혹시 해결되지 않는다면 말씀한번더 부탁드립니다 ㅠ
companion object { | ||
lateinit var prefs: PreferenceUtil | ||
} | ||
override fun onCreate() { | ||
super.onCreate() | ||
KakaoSdk.init(this, "${BuildConfig.KAKAO_NATIVE_KEY}") | ||
prefs = PreferenceUtil(applicationContext) | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
application 클래스에서 PreferenceUtil을 초기화하고, 이걸 매번 가져다 사용할 수 있겠지만, 아직 프로젝트 초반이니 Hilt를 적용해서 의존성 주입을 받을 수 있도록 구성하는걸 추천드립니다.
} catch (e: Exception) { | ||
callback(emptyList()) | ||
callback(emptyList(), emptyList()) | ||
} | ||
} else { | ||
callback(emptyList()) | ||
callback(emptyList(), emptyList()) | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
실패했을때 emptyList를 반환해서 리스트가 비어있을때의 처리를 해도 괜찮겠지만,
callback -> onSuccess / onFailure 2개를 만들어서, 각각 사용하는것도 괜찮을것 같습니다.
private fun getPlaceNamesFromCoordinates(
latitude: Double,
longitude: Double,
onSuccess: (List<String>, List<String>) -> Unit,
onFailure: (e: Throwable) -> Unit
)
private fun handleEmotion(context: Context, emotion: Emotions) { | ||
val emoji = emotion.getEmotionUnicode() | ||
val label = when (emotion) { | ||
Emotions.HAPPY -> "행복" | ||
Emotions.SAD -> "슬픔" | ||
Emotions.INSENSITIVE -> "무표정" | ||
Emotions.ANGRY -> "화남" | ||
Emotions.CONFOUNDED -> "싫음" | ||
} | ||
|
||
// 선택된 감정 처리 -> 백엔드 전송 필요 | ||
Toast.makeText(context, "선택된 감정: $emoji $label", Toast.LENGTH_SHORT).show() | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
이 부분에서 백엔드와 통신이 필요한것이군요.
fun performBackgroundTask() {
// API 호출 로직 (Retrofit, OkHttp 등 사용)
GlobalScope.launch(Dispatchers.IO) {
// 백엔드 API 호출
val response = apiService.callBackendApi()
if (response.isSuccessful) {
// API 호출 성공 처리
}
}
}
이렇게 GlobalScope로 실행되도록 처리하면 가능하지 않을까 싶고,
백엔드 API 실행만을 위한 Service클래스를 하나 더 만들어서, 이 Service를 실행하게 하는것도 방법이 될것 같습니다. (ForegroundService로 실행되어야 하는건 동일할것이구요)
만약, 이 구현이 힘들거나 기술적으로 불가능하다면, LocalDataBase에 기록들을 쌓아두었다가, 앱이 실행되었을때 한번에 백엔드로 전송하는것도 방법이 될것 같습니다. (bulk upload 방식 )
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
cc. @todlf
val remoteViews = RemoteViews(packageName, R.layout.custom_notification) | ||
remoteViews.setTextViewText(R.id.happyEmojiTextView, Emotions.HAPPY.getEmotionUnicode()) | ||
remoteViews.setTextViewText(R.id.sadEmojiTextView, Emotions.SAD.getEmotionUnicode()) | ||
remoteViews.setTextViewText(R.id.insensitiveEmojiTextView, Emotions.INSENSITIVE.getEmotionUnicode()) | ||
remoteViews.setTextViewText(R.id.angryEmojiTextView, Emotions.ANGRY.getEmotionUnicode()) | ||
remoteViews.setTextViewText(R.id.confoundedEmojiTextView, Emotions.CONFOUNDED.getEmotionUnicode()) | ||
|
||
val emotions = listOf( | ||
R.id.happyEmojiTextView to Emotions.HAPPY, | ||
R.id.sadEmojiTextView to Emotions.SAD, | ||
R.id.insensitiveEmojiTextView to Emotions.INSENSITIVE, | ||
R.id.angryEmojiTextView to Emotions.ANGRY, | ||
R.id.confoundedEmojiTextView to Emotions.CONFOUNDED | ||
) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@todlf remoteView의 텍스트뷰를 클릭했을때 백엔드로 데이터를 전송하는 것을 여기에 구현할 수 있을것 같네요.
val notificationIntent = Intent(this, �BackendLogicService::class.java)
val pendingIntent = PendingIntent.getService(this, 0, notificationIntent, PendingIntent.FLAG_UPDATE_CURRENT)
remoteViews.setOnClickPendingIntent(R.id.insensitiveEmojiTextView, pendingIntent)
이렇게 백엔드 전송만을 위한 Service를 하나더 실행시키는 것도 방법이 될것 같습니다.
private fun showDeleteConfirmationDialog(friends: Friends) { | ||
AlertDialog.Builder(itemView.context) | ||
.setTitle("친구 삭제") | ||
.setMessage("${friends.name}님을 친구에서 삭제하시겠습니까?") | ||
.setNegativeButton("아니오") { dialog, _ -> dialog.dismiss() } | ||
.setPositiveButton("네") { _, _ -> onDeleteFriend(friends) } | ||
.show() | ||
CustomDialog( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
보통 다이얼로그를 띄우는것은 RecyclerView ViewHolder에서 처리하기 보다는 Activity에서 구현을 하는것 같습니다.
ViewHolder에서는 itemView를 롱클릭 했을때 호출되는 람다 (혹은 Listener인터페이스) 만 호출시켜주는 형태인것이죠.
class FriendsListAdapter(
//private val activity: FragmentActivity,
private val onFriendLongClick: (friends: Friends) -> Unit, // 이것을 ViewHolder에 전달후 사용.
private val onDeleteFriend: (Friends) -> Unit
)
binding.friendListIcon.setOnClickListener { | ||
requireActivity().supportFragmentManager.beginTransaction().apply { | ||
replace(R.id.fragment_container, FriendsListFragment()) | ||
addToBackStack(null) | ||
commit() | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
여기도 CalendarViewFragment
와 동일한 내용입니다!
viewModel = ViewModelProvider(this, TimelineViewModelFactory(diaryRepository)).get( | ||
TimelineViewModel::class.java |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
viewModel 인스턴스를 생성할때 안드로이드에서 제공해주는 확장함수가 있어서 이걸 사용하는걸 더 추천드립니다.
private val viewModel by viewModels<TimelineViewModel>()
private fun makeToast(string: String) { | ||
Toast.makeText( | ||
context, | ||
string, | ||
Toast.LENGTH_SHORT | ||
).show() | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Context의 확장함수로 하나 만들어둬도 유용하게 쓰일것 같네요
fun Context.showToast(message: String) {
Toast.makeText(
context,
message,
Toast.LENGTH_SHORT
).show()
}
private fun setFilterSheet() { | ||
|
||
filterBottomSheet = SearchFilterDialogFragment() | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
SearchFragment가 생성될때 (정확히는 onViewCreated 될때) 무조건 SearchFilterDialogFragment가 만들어지는것이니, 멤버변수 및 지연초기화를 사용해서 이렇게 선언해두는건 어떨까요?
private val filterBottomSheet by lazy {
SearchFilterDialogFragment()
}
지금 경우에서 setFilterSheet
가 여러분 호출되지는 않는것 같네요
<?xml version="1.0" encoding="utf-8"?> | ||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" | ||
android:id="@+id/friendContainer" | ||
android:orientation="vertical" | ||
android:layout_width="wrap_content" | ||
android:layout_height="wrap_content" | ||
android:gravity="center" | ||
android:layout_marginEnd="9dp"> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@arieum 아하, 질문주신 부분이 여기인것 같네요.
LinearLayout의 gravity를 center_vertical / center_horizontal 으로 하거나 이렇게 해도 해결되지 않는다면, ConstraintLayout으로 위치를 좀더 세세하게 잡을 수 있도록 하는게 어떨까 합니다.
항상 감사하고 잘 부탁드립니다! 😊