feat: 메인 홈 - 인기 크리에이터

- 팔로우/언팔로우 기능 추가
This commit is contained in:
2025-07-21 18:44:59 +09:00
parent 58bc42cc0f
commit bdac7b7899
5 changed files with 81 additions and 19 deletions

View File

@@ -340,7 +340,7 @@ class AppDI(private val context: Context, isDebugMode: Boolean) {
viewModel { AlarmContentAllViewModel(get()) }
viewModel { SearchViewModel(get()) }
viewModel { PointStatusViewModel(get()) }
viewModel { HomeViewModel(get()) }
viewModel { HomeViewModel(get(), get()) }
}
private val repositoryModule = module {

View File

@@ -23,5 +23,5 @@ data class GetExplorerSectionCreatorResponse(
@SerializedName("nickname") val nickname: String,
@SerializedName("tags") val tags: String,
@SerializedName("profileImageUrl") val profileImageUrl: String,
@SerializedName("followerCount") val followerCount: Int
@SerializedName("follow") var follow: Boolean
)

View File

@@ -14,7 +14,8 @@ import kr.co.vividnext.sodalive.databinding.ItemHomeCreatorBinding
import kr.co.vividnext.sodalive.explorer.GetExplorerSectionCreatorResponse
class CreatorRankingAdapter(
private val onClickItem: (Long) -> Unit
private val onClickItem: (Long) -> Unit,
private val onClickFollow: (Long, Boolean) -> Unit
) : RecyclerView.Adapter<CreatorRankingAdapter.ViewHolder>() {
private val items = mutableListOf<GetExplorerSectionCreatorResponse>()
@@ -24,8 +25,6 @@ class CreatorRankingAdapter(
private val binding: ItemHomeCreatorBinding
) : RecyclerView.ViewHolder(binding.root) {
fun bind(item: GetExplorerSectionCreatorResponse, index: Int) {
binding.root.setOnClickListener { onClickItem(item.id) }
Glide
.with(context)
.load(item.profileImageUrl)
@@ -58,6 +57,20 @@ class CreatorRankingAdapter(
binding.ivCrown.visibility = View.GONE
}
}
if (item.follow) {
binding.tvFollow.text = "팔로잉"
} else {
binding.tvFollow.text = "팔로우"
}
binding.tvFollow.setOnClickListener {
item.follow = !item.follow
notifyItemChanged(index)
onClickFollow(item.id, item.follow)
}
binding.root.setOnClickListener { onClickItem(item.id) }
}
}

View File

@@ -277,20 +277,33 @@ class HomeFragment : BaseFragment<FragmentHomeBinding>(FragmentHomeBinding::infl
)
binding.tvFamousCreatorTitle.text = spSectionTitle
creatorRankingAdapter = CreatorRankingAdapter {
if (SharedPreferenceManager.token.isNotBlank()) {
startActivity(
Intent(
requireActivity(),
UserProfileActivity::class.java
).apply {
putExtra(Constants.EXTRA_USER_ID, it)
creatorRankingAdapter = CreatorRankingAdapter(
onClickItem = {
if (SharedPreferenceManager.token.isNotBlank()) {
startActivity(
Intent(
requireActivity(),
UserProfileActivity::class.java
).apply {
putExtra(Constants.EXTRA_USER_ID, it)
}
)
} else {
(requireActivity() as MainActivity).showLoginActivity()
}
},
onClickFollow = { creatorId, follow ->
if (SharedPreferenceManager.token.isNotBlank()) {
if (follow) {
viewModel.follow(creatorId, follow = true, notify = true)
} else {
viewModel.follow(creatorId, follow = false, notify = false)
}
)
} else {
(requireActivity() as MainActivity).showLoginActivity()
} else {
(requireActivity() as MainActivity).showLoginActivity()
}
}
}
)
val recyclerView = binding.rvFamousCreator
recyclerView.layoutManager = LinearLayoutManager(

View File

@@ -9,13 +9,16 @@ import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
import kr.co.vividnext.sodalive.audition.GetAuditionListItem
import kr.co.vividnext.sodalive.base.BaseViewModel
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
import kr.co.vividnext.sodalive.explorer.GetExplorerSectionCreatorResponse
import kr.co.vividnext.sodalive.live.GetRoomListResponse
import kr.co.vividnext.sodalive.user.UserRepository
class HomeViewModel(private val repository: HomeRepository) : BaseViewModel() {
class HomeViewModel(
private val repository: HomeRepository,
private val userRepository: UserRepository
) : BaseViewModel() {
private var _isLoading = MutableLiveData(false)
val isLoading: LiveData<Boolean>
@@ -172,4 +175,37 @@ class HomeViewModel(private val repository: HomeRepository) : BaseViewModel() {
)
)
}
fun follow(creatorId: Long, follow: Boolean = true, notify: Boolean = true) {
_isLoading.value = true
compositeDisposable.add(
userRepository.creatorFollow(
creatorId = creatorId,
follow,
notify,
token = "Bearer ${SharedPreferenceManager.token}"
)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(
{
_isLoading.value = false
if (!it.success || it.data == null) {
if (it.message != null) {
_toastLiveData.postValue(it.message)
} else {
_toastLiveData.postValue(
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
)
}
}
},
{
_isLoading.value = false
it.message?.let { message -> Logger.e(message) }
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
}
)
)
}
}