fix: 사용하지 않는 이전 콘텐츠 메인 연관 파일 제거
This commit is contained in:
@@ -161,7 +161,6 @@
|
|||||||
<activity android:name=".mypage.profile.ProfileUpdateActivity" />
|
<activity android:name=".mypage.profile.ProfileUpdateActivity" />
|
||||||
<activity android:name=".mypage.profile.nickname.NicknameUpdateActivity" />
|
<activity android:name=".mypage.profile.nickname.NicknameUpdateActivity" />
|
||||||
<activity android:name=".mypage.profile.password.ModifyPasswordActivity" />
|
<activity android:name=".mypage.profile.password.ModifyPasswordActivity" />
|
||||||
<activity android:name=".audio_content.curation.AudioContentCurationActivity" />
|
|
||||||
<activity android:name=".audio_content.all.AudioContentNewAllActivity" />
|
<activity android:name=".audio_content.all.AudioContentNewAllActivity" />
|
||||||
<activity android:name=".audio_content.all.AudioContentRankingAllActivity" />
|
<activity android:name=".audio_content.all.AudioContentRankingAllActivity" />
|
||||||
<activity android:name=".audio_content.all.by_theme.AudioContentAllByThemeActivity" />
|
<activity android:name=".audio_content.all.by_theme.AudioContentAllByThemeActivity" />
|
||||||
@@ -177,14 +176,6 @@
|
|||||||
<activity android:name=".audition.detail.AuditionDetailActivity" />
|
<activity android:name=".audition.detail.AuditionDetailActivity" />
|
||||||
<activity android:name=".audition.role.AuditionRoleDetailActivity" />
|
<activity android:name=".audition.role.AuditionRoleDetailActivity" />
|
||||||
|
|
||||||
<activity android:name=".audio_content.main.v2.AudioContentMainActivity" />
|
|
||||||
<activity android:name=".audio_content.main.v2.alarm.all.AlarmContentAllActivity" />
|
|
||||||
<activity android:name=".audio_content.main.v2.asmr.AsmrNewContentAllActivity" />
|
|
||||||
<activity android:name=".audio_content.main.v2.replay.ReplayNewContentAllActivity" />
|
|
||||||
<activity android:name=".audio_content.main.v2.free.introduce_creator.IntroduceCreatorActivity" />
|
|
||||||
<activity android:name=".audio_content.main.v2.series.origianl_audio_drama.OriginalAudioDramaContentAllActivity" />
|
|
||||||
<activity android:name=".audio_content.main.v2.series.completed.CompletedSeriesActivity" />
|
|
||||||
|
|
||||||
<activity android:name=".search.SearchActivity" />
|
<activity android:name=".search.SearchActivity" />
|
||||||
<activity android:name=".audition.AuditionActivity" />
|
<activity android:name=".audition.AuditionActivity" />
|
||||||
|
|
||||||
|
|||||||
@@ -7,7 +7,6 @@ import kr.co.vividnext.sodalive.audio_content.all.by_theme.GetContentByThemeResp
|
|||||||
import kr.co.vividnext.sodalive.audio_content.comment.GetAudioContentCommentListResponse
|
import kr.co.vividnext.sodalive.audio_content.comment.GetAudioContentCommentListResponse
|
||||||
import kr.co.vividnext.sodalive.audio_content.comment.ModifyCommentRequest
|
import kr.co.vividnext.sodalive.audio_content.comment.ModifyCommentRequest
|
||||||
import kr.co.vividnext.sodalive.audio_content.comment.RegisterAudioContentCommentRequest
|
import kr.co.vividnext.sodalive.audio_content.comment.RegisterAudioContentCommentRequest
|
||||||
import kr.co.vividnext.sodalive.audio_content.curation.GetCurationContentResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.GetAudioContentDetailResponse
|
import kr.co.vividnext.sodalive.audio_content.detail.GetAudioContentDetailResponse
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.PutAudioContentLikeRequest
|
import kr.co.vividnext.sodalive.audio_content.detail.PutAudioContentLikeRequest
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.PutAudioContentLikeResponse
|
import kr.co.vividnext.sodalive.audio_content.detail.PutAudioContentLikeResponse
|
||||||
@@ -16,18 +15,9 @@ import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentCurationResponse
|
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentCurationResponse
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRanking
|
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRanking
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.alarm.GetContentMainTabAlarmResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.asmr.GetContentMainTabAsmrResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.content.GetContentMainTabContentResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.free.GetContentMainTabLiveFreeResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.home.GetContentMainTabHomeResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.replay.GetContentMainTabLiveReplayResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.GetContentMainTabSeriesResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.order.GetAudioContentOrderListResponse
|
import kr.co.vividnext.sodalive.audio_content.order.GetAudioContentOrderListResponse
|
||||||
import kr.co.vividnext.sodalive.audio_content.order.OrderRequest
|
import kr.co.vividnext.sodalive.audio_content.order.OrderRequest
|
||||||
import kr.co.vividnext.sodalive.audio_content.player.GenerateUrlResponse
|
import kr.co.vividnext.sodalive.audio_content.player.GenerateUrlResponse
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.upload.theme.GetAudioContentThemeResponse
|
import kr.co.vividnext.sodalive.audio_content.upload.theme.GetAudioContentThemeResponse
|
||||||
import kr.co.vividnext.sodalive.common.ApiResponse
|
import kr.co.vividnext.sodalive.common.ApiResponse
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.GetAudioContentListResponse
|
import kr.co.vividnext.sodalive.explorer.profile.GetAudioContentListResponse
|
||||||
@@ -190,17 +180,6 @@ interface AudioContentApi {
|
|||||||
@Header("Authorization") authHeader: String
|
@Header("Authorization") authHeader: String
|
||||||
): Single<ApiResponse<Any>>
|
): Single<ApiResponse<Any>>
|
||||||
|
|
||||||
@GET("/audio-content/curation/{id}")
|
|
||||||
fun getAudioContentListByCurationId(
|
|
||||||
@Path("id") id: Long,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Query("page") page: Int,
|
|
||||||
@Query("size") size: Int,
|
|
||||||
@Query("sort-type") sort: AudioContentViewModel.Sort,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetCurationContentResponse>>
|
|
||||||
|
|
||||||
@GET("/audio-content/main/theme")
|
@GET("/audio-content/main/theme")
|
||||||
fun getNewContentThemeList(
|
fun getNewContentThemeList(
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
||||||
@@ -257,187 +236,4 @@ interface AudioContentApi {
|
|||||||
@Path("id") contentId: Long,
|
@Path("id") contentId: Long,
|
||||||
@Header("Authorization") authHeader: String
|
@Header("Authorization") authHeader: String
|
||||||
): Single<ApiResponse<GenerateUrlResponse>>
|
): Single<ApiResponse<GenerateUrlResponse>>
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/home")
|
|
||||||
fun getContentMainHome(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetContentMainTabHomeResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/home/popular-content-by-creator")
|
|
||||||
fun getPopularContentByCreator(
|
|
||||||
@Query("creatorId") creatorId: Long,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentRankingItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/home/content/ranking")
|
|
||||||
fun getContentMainHomeContentRanking(
|
|
||||||
@Query("sort-type") sortType: String,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentRankingItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/series")
|
|
||||||
fun getContentMainSeries(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetContentMainTabSeriesResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/series/original")
|
|
||||||
fun getOriginalAudioDramaList(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Query("page") page: Int,
|
|
||||||
@Query("size") size: Int,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetSeriesListResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/series/recommend-by-genre")
|
|
||||||
fun getRecommendSeriesListByGenre(
|
|
||||||
@Query("genreId") genreId: Long,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetSeriesListResponse.SeriesListItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/series/recommend-series-by-creator")
|
|
||||||
fun getRecommendSeriesByCreator(
|
|
||||||
@Query("creatorId") creatorId: Long,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetSeriesListResponse.SeriesListItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/series/completed-rank")
|
|
||||||
fun getCompletedSeries(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Query("page") page: Int,
|
|
||||||
@Query("size") size: Int,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetSeriesListResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/content")
|
|
||||||
fun getContentMainContent(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetContentMainTabContentResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/content/new-content-by-theme")
|
|
||||||
fun getContentMainNewContentOfTheme(
|
|
||||||
@Query("theme") theme: String,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentMainItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/content/ranking")
|
|
||||||
fun getDailyContentRanking(
|
|
||||||
@Query("sort-type") sortType: String,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentRankingItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/content/popular-content-by-creator")
|
|
||||||
fun getContentMainContentPopularContentByCreator(
|
|
||||||
@Query("creatorId") creatorId: Long,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentRankingItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/alarm")
|
|
||||||
fun getContentMainAlarm(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetContentMainTabAlarmResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/alarm/all")
|
|
||||||
fun getContentMainAlarmAll(
|
|
||||||
@Query("theme") theme: String,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Query("page") page: Int,
|
|
||||||
@Query("size") size: Int,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetNewContentAllResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/asmr")
|
|
||||||
fun getContentMainAsmr(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetContentMainTabAsmrResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/asmr/popular-content-by-creator")
|
|
||||||
fun getPopularAsmrContentByCreator(
|
|
||||||
@Query("creatorId") creatorId: Long,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentRankingItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/replay")
|
|
||||||
fun getContentMainReplay(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetContentMainTabLiveReplayResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/replay/popular-content-by-creator")
|
|
||||||
fun getPopularReplayContentByCreator(
|
|
||||||
@Query("creatorId") creatorId: Long,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentRankingItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/free")
|
|
||||||
fun getContentMainFree(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<GetContentMainTabLiveFreeResponse>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/free/introduce-creator")
|
|
||||||
fun getIntroduceCreatorList(
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Query("page") page: Int,
|
|
||||||
@Query("size") size: Int,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentMainItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/free/new-content-by-theme")
|
|
||||||
fun getNewFreeContentOfTheme(
|
|
||||||
@Query("theme") theme: String,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Query("page") page: Int,
|
|
||||||
@Query("size") size: Int,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentMainItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/free/popular-content-by-creator")
|
|
||||||
fun getPopularFreeContentByCreator(
|
|
||||||
@Query("creatorId") creatorId: Long,
|
|
||||||
@Query("isAdultContentVisible") isAdultContentVisible: Boolean,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentRankingItem>>>
|
|
||||||
|
|
||||||
@GET("/v2/audio-content/main/content/recommend-content-by-tag")
|
|
||||||
fun getRecommendedContentByTag(
|
|
||||||
@Query("tag") tag: String,
|
|
||||||
@Query("contentType") contentType: ContentType,
|
|
||||||
@Header("Authorization") authHeader: String
|
|
||||||
): Single<ApiResponse<List<GetAudioContentMainItem>>>
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,7 +6,6 @@ import kr.co.vividnext.sodalive.audio_content.donation.AudioContentDonationReque
|
|||||||
import kr.co.vividnext.sodalive.audio_content.order.OrderRequest
|
import kr.co.vividnext.sodalive.audio_content.order.OrderRequest
|
||||||
import kr.co.vividnext.sodalive.audio_content.order.OrderType
|
import kr.co.vividnext.sodalive.audio_content.order.OrderType
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
||||||
import kr.co.vividnext.sodalive.explorer.ExplorerApi
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
import kr.co.vividnext.sodalive.settings.ContentType
|
||||||
import okhttp3.MultipartBody
|
import okhttp3.MultipartBody
|
||||||
import okhttp3.RequestBody
|
import okhttp3.RequestBody
|
||||||
@@ -14,25 +13,8 @@ import java.util.TimeZone
|
|||||||
|
|
||||||
class AudioContentRepository(
|
class AudioContentRepository(
|
||||||
private val api: AudioContentApi,
|
private val api: AudioContentApi,
|
||||||
private val categoryApi: CategoryApi,
|
private val categoryApi: CategoryApi
|
||||||
private val explorerApi: ExplorerApi
|
|
||||||
) {
|
) {
|
||||||
fun getAudioContentListByCurationId(
|
|
||||||
curationId: Long,
|
|
||||||
page: Int,
|
|
||||||
size: Int,
|
|
||||||
sort: AudioContentViewModel.Sort = AudioContentViewModel.Sort.NEWEST,
|
|
||||||
token: String
|
|
||||||
) = api.getAudioContentListByCurationId(
|
|
||||||
id = curationId,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
page = page - 1,
|
|
||||||
size = size,
|
|
||||||
sort = sort,
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getAudioContentList(
|
fun getAudioContentList(
|
||||||
id: Long,
|
id: Long,
|
||||||
categoryId: Long,
|
categoryId: Long,
|
||||||
@@ -127,13 +109,6 @@ class AudioContentRepository(
|
|||||||
token: String
|
token: String
|
||||||
) = api.likeContent(request, authHeader = token)
|
) = api.likeContent(request, authHeader = token)
|
||||||
|
|
||||||
fun getNewContentOfTheme(theme: String, token: String) = api.getNewContentOfTheme(
|
|
||||||
theme = theme,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getNewContentAllOfTheme(
|
fun getNewContentAllOfTheme(
|
||||||
isFree: Boolean,
|
isFree: Boolean,
|
||||||
theme: String,
|
theme: String,
|
||||||
@@ -184,16 +159,6 @@ class AudioContentRepository(
|
|||||||
authHeader = token
|
authHeader = token
|
||||||
)
|
)
|
||||||
|
|
||||||
fun getCurationList(page: Int, size: Int, token: String) = api.getCurationList(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
page = page - 1,
|
|
||||||
size = size,
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getMainBannerList(token: String) = api.getMainBannerList(authHeader = token)
|
|
||||||
fun getMainOrderList(token: String) = api.getMainOrderList(authHeader = token)
|
|
||||||
fun pinContent(
|
fun pinContent(
|
||||||
audioContentId: Long,
|
audioContentId: Long,
|
||||||
token: String
|
token: String
|
||||||
@@ -224,6 +189,4 @@ class AudioContentRepository(
|
|||||||
sort = sort,
|
sort = sort,
|
||||||
authHeader = token
|
authHeader = token
|
||||||
)
|
)
|
||||||
|
|
||||||
fun getCreatorRank(token: String) = explorerApi.getCreatorRank(authHeader = token)
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,178 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.curation
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Intent
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.widget.TextView
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseActivity
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ActivityAudioContentCurationBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AudioContentCurationActivity : BaseActivity<ActivityAudioContentCurationBinding>(
|
|
||||||
ActivityAudioContentCurationBinding::inflate
|
|
||||||
) {
|
|
||||||
|
|
||||||
private val viewModel: AudioContentCurationViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var adapter: AudioContentNewAllAdapter
|
|
||||||
|
|
||||||
private var curationId: Long = 0
|
|
||||||
private lateinit var title: String
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
title = intent.getStringExtra(Constants.EXTRA_AUDIO_CONTENT_CURATION_TITLE) ?: ""
|
|
||||||
curationId = intent.getLongExtra(Constants.EXTRA_AUDIO_CONTENT_CURATION_ID, 0)
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
|
|
||||||
if (title.isBlank() || curationId <= 0) {
|
|
||||||
Toast.makeText(applicationContext, "잘못된 요청입니다.", Toast.LENGTH_LONG).show()
|
|
||||||
finish()
|
|
||||||
}
|
|
||||||
|
|
||||||
bindData()
|
|
||||||
viewModel.getContentList(curationId = curationId)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(this, layoutInflater)
|
|
||||||
binding.toolbar.tvBack.text = title
|
|
||||||
binding.toolbar.tvBack.setOnClickListener { finish() }
|
|
||||||
|
|
||||||
val spanCount = 3
|
|
||||||
val spacing = 40
|
|
||||||
adapter = AudioContentNewAllAdapter(
|
|
||||||
itemWidth = (screenWidth - (spacing * (spanCount + 1))) / 3,
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = GridLayoutManager(this, spanCount)
|
|
||||||
binding.rvCuration.addItemDecoration(GridSpacingItemDecoration(spanCount, spacing, true))
|
|
||||||
|
|
||||||
binding.rvCuration.addOnScrollListener(object : RecyclerView.OnScrollListener() {
|
|
||||||
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
|
|
||||||
super.onScrolled(recyclerView, dx, dy)
|
|
||||||
|
|
||||||
val lastVisibleItemPosition = (recyclerView.layoutManager as LinearLayoutManager?)!!
|
|
||||||
.findLastCompletelyVisibleItemPosition()
|
|
||||||
val itemTotalCount = recyclerView.adapter!!.itemCount - 1
|
|
||||||
|
|
||||||
// 스크롤이 끝에 도달했는지 확인
|
|
||||||
if (!recyclerView.canScrollVertically(1) &&
|
|
||||||
lastVisibleItemPosition == itemTotalCount
|
|
||||||
) {
|
|
||||||
viewModel.getContentList(curationId)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = adapter
|
|
||||||
|
|
||||||
binding.tvSortNewest.setOnClickListener {
|
|
||||||
viewModel.changeSort(AudioContentViewModel.Sort.NEWEST)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvSortPriceLow.setOnClickListener {
|
|
||||||
viewModel.changeSort(AudioContentViewModel.Sort.PRICE_LOW)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvSortPriceHigh.setOnClickListener {
|
|
||||||
viewModel.changeSort(AudioContentViewModel.Sort.PRICE_HIGH)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(this) {
|
|
||||||
it?.let { Toast.makeText(applicationContext, it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(this) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth, "")
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.contentListLiveData.observe(this) {
|
|
||||||
if (viewModel.page - 1 == 1) {
|
|
||||||
adapter.clear()
|
|
||||||
binding.rvCuration.scrollToPosition(0)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvTotalCount.text = "${it.totalCount}"
|
|
||||||
adapter.addItems(it.items)
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.sort.observe(this) {
|
|
||||||
deselectSort()
|
|
||||||
selectSort(
|
|
||||||
when (it) {
|
|
||||||
AudioContentViewModel.Sort.PRICE_HIGH -> {
|
|
||||||
binding.tvSortPriceHigh
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentViewModel.Sort.PRICE_LOW -> {
|
|
||||||
binding.tvSortPriceLow
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
binding.tvSortNewest
|
|
||||||
}
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
viewModel.getContentList(curationId = curationId)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun deselectSort() {
|
|
||||||
val color = ContextCompat.getColor(
|
|
||||||
applicationContext,
|
|
||||||
R.color.color_88e2e2e2
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.tvSortNewest.setTextColor(color)
|
|
||||||
binding.tvSortPriceLow.setTextColor(color)
|
|
||||||
binding.tvSortPriceHigh.setTextColor(color)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun selectSort(view: TextView) {
|
|
||||||
view.setTextColor(
|
|
||||||
ContextCompat.getColor(
|
|
||||||
applicationContext,
|
|
||||||
R.color.color_e2e2e2
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,86 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.curation
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentViewModel
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AudioContentCurationViewModel(
|
|
||||||
private val repository: AudioContentRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _contentListLiveData = MutableLiveData<GetCurationContentResponse>()
|
|
||||||
val contentListLiveData: LiveData<GetCurationContentResponse>
|
|
||||||
get() = _contentListLiveData
|
|
||||||
|
|
||||||
private val _sort = MutableLiveData(AudioContentViewModel.Sort.NEWEST)
|
|
||||||
val sort: LiveData<AudioContentViewModel.Sort>
|
|
||||||
get() = _sort
|
|
||||||
|
|
||||||
private var isLast = false
|
|
||||||
var page = 1
|
|
||||||
private val size = 10
|
|
||||||
|
|
||||||
fun getContentList(curationId: Long) {
|
|
||||||
if (!_isLoading.value!! && !isLast) {
|
|
||||||
_isLoading.value = true
|
|
||||||
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getAudioContentListByCurationId(
|
|
||||||
curationId = curationId,
|
|
||||||
page = page,
|
|
||||||
size = size,
|
|
||||||
sort = _sort.value!!,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
if (it.data.items.isNotEmpty()) {
|
|
||||||
page += 1
|
|
||||||
_contentListLiveData.postValue(it.data!!)
|
|
||||||
} else {
|
|
||||||
isLast = true
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun changeSort(sort: AudioContentViewModel.Sort) {
|
|
||||||
page = 1
|
|
||||||
isLast = false
|
|
||||||
_sort.postValue(sort)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,11 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.curation
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetCurationContentResponse(
|
|
||||||
@SerializedName("totalCount") val totalCount: Int,
|
|
||||||
@SerializedName("items") val items: List<GetAudioContentMainItem>
|
|
||||||
)
|
|
||||||
@@ -1,41 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainBinding
|
|
||||||
|
|
||||||
class AudioContentMainContentAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit,
|
|
||||||
private val onClickCreator: (Long) -> Unit,
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainItemViewHolder>() {
|
|
||||||
|
|
||||||
private val items = mutableListOf<GetAudioContentMainItem>()
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(
|
|
||||||
parent: ViewGroup,
|
|
||||||
viewType: Int
|
|
||||||
) = AudioContentMainItemViewHolder(
|
|
||||||
ItemAudioContentMainBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
),
|
|
||||||
onClickItem = onClickItem,
|
|
||||||
onClickCreator = onClickCreator
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: AudioContentMainItemViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetAudioContentMainItem>) {
|
|
||||||
this.items.clear()
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,737 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Intent
|
|
||||||
import android.graphics.Color
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.text.SpannableString
|
|
||||||
import android.text.Spanned
|
|
||||||
import android.text.style.ForegroundColorSpan
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.LinearLayout
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.zhpan.bannerview.BaseBannerAdapter
|
|
||||||
import com.zhpan.indicator.enums.IndicatorSlideMode
|
|
||||||
import com.zhpan.indicator.enums.IndicatorStyle
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentRankingAllActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.by_theme.AudioContentAllByThemeActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.box.AudioContentBoxActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.curation.AudioContentCurationActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.curation.AudioContentMainCurationAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.curation.AudioContentMainCurationViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.new_content.AudioContentMainNewContentThemeAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.new_content.AudioContentMainNewContentViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ranking.AudioContentMainCreatorRankingViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ranking.AudioContentMainRankingAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ranking.AudioContentMainRankingViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.recommend_series.AudioContentMainRecommendSeriesViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.upload.AudioContentUploadActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseFragment
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.databinding.FragmentAudioContentMainBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.ExplorerSectionAdapter
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.series.UserProfileSeriesListAdapter
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.main.MainActivity
|
|
||||||
import kr.co.vividnext.sodalive.mypage.alarm.AlarmListActivity
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.settings.notification.MemberRole
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AudioContentMainFragment : BaseFragment<FragmentAudioContentMainBinding>(
|
|
||||||
FragmentAudioContentMainBinding::inflate
|
|
||||||
) {
|
|
||||||
private val creatorRankViewModel: AudioContentMainCreatorRankingViewModel by inject()
|
|
||||||
private lateinit var creatorRankAdaptor: ExplorerSectionAdapter
|
|
||||||
|
|
||||||
private val recommendSeriesViewModel: AudioContentMainRecommendSeriesViewModel by inject()
|
|
||||||
private lateinit var seriesAdapter: UserProfileSeriesListAdapter
|
|
||||||
|
|
||||||
private val bannerViewModel: AudioContentMainBannerViewModel by inject()
|
|
||||||
private lateinit var bannerAdapter: AudioContentMainBannerAdapter
|
|
||||||
|
|
||||||
private val newContentViewModel: AudioContentMainNewContentViewModel by inject()
|
|
||||||
private lateinit var newContentThemeAdapter: AudioContentMainNewContentThemeAdapter
|
|
||||||
private lateinit var newContentAdapter: AudioContentMainContentAdapter
|
|
||||||
|
|
||||||
private val contentRankingViewModel: AudioContentMainRankingViewModel by inject()
|
|
||||||
private lateinit var contentRankingSortAdapter: AudioContentMainNewContentThemeAdapter
|
|
||||||
private lateinit var contentRankingAdapter: AudioContentMainRankingAdapter
|
|
||||||
|
|
||||||
private val curationViewModel: AudioContentMainCurationViewModel by inject()
|
|
||||||
private lateinit var curationAdapter: AudioContentMainCurationAdapter
|
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
|
||||||
super.onViewCreated(view, savedInstanceState)
|
|
||||||
setupView()
|
|
||||||
|
|
||||||
curationViewModel.getCurationList()
|
|
||||||
bannerViewModel.getMainBannerList()
|
|
||||||
newContentViewModel.getThemeList()
|
|
||||||
creatorRankViewModel.getCreatorRank()
|
|
||||||
newContentViewModel.getNewContentOfTheme("전체")
|
|
||||||
contentRankingViewModel.getContentRanking()
|
|
||||||
contentRankingViewModel.getContentRankingSortType()
|
|
||||||
recommendSeriesViewModel.getRecommendSeriesList()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupView() {
|
|
||||||
if (SharedPreferenceManager.role == MemberRole.CREATOR.name) {
|
|
||||||
binding.llUploadContent.visibility = View.VISIBLE
|
|
||||||
binding.llUploadContent.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireActivity(),
|
|
||||||
AudioContentUploadActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
binding.llUploadContent.visibility = View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
setupCreatorRank()
|
|
||||||
setupRecommendSeries()
|
|
||||||
setupBanner()
|
|
||||||
setupNewContentTheme()
|
|
||||||
setupNewContent()
|
|
||||||
setupContentRankingSortType()
|
|
||||||
setupContentRanking()
|
|
||||||
setupCuration()
|
|
||||||
|
|
||||||
binding.llShortPlay.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentAllByThemeActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_THEME_ID, 11L)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.llMorningCall.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentAllByThemeActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_THEME_ID, 12L)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.ivContentKeep.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireContext(),
|
|
||||||
AudioContentBoxActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.ivAlarm.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireActivity(),
|
|
||||||
AlarmListActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.flSearchChannel.setOnClickListener {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCreatorRank() {
|
|
||||||
creatorRankAdaptor = ExplorerSectionAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
isVisibleRanking = true
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCreatorRank.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCreatorRank.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
creatorRankAdaptor.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCreatorRank.adapter = creatorRankAdaptor
|
|
||||||
|
|
||||||
creatorRankViewModel.creatorRankLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.tvDesc.text = it.desc
|
|
||||||
binding.tvCreatorRankTitle.text = if (
|
|
||||||
!it.coloredTitle.isNullOrBlank() &&
|
|
||||||
!it.color.isNullOrBlank()
|
|
||||||
) {
|
|
||||||
val spStr = SpannableString(it.title)
|
|
||||||
|
|
||||||
try {
|
|
||||||
spStr.setSpan(
|
|
||||||
ForegroundColorSpan(
|
|
||||||
Color.parseColor("#${it.color}")
|
|
||||||
),
|
|
||||||
it.title.indexOf(it.coloredTitle),
|
|
||||||
it.title.indexOf(it.coloredTitle) + it.coloredTitle.length,
|
|
||||||
Spanned.SPAN_EXCLUSIVE_EXCLUSIVE
|
|
||||||
)
|
|
||||||
|
|
||||||
spStr
|
|
||||||
} catch (e: IllegalArgumentException) {
|
|
||||||
it.title
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
it.title
|
|
||||||
}
|
|
||||||
|
|
||||||
creatorRankAdaptor.addItems(it.creators)
|
|
||||||
if (creatorRankAdaptor.itemCount <= 0 && it.creators.isEmpty()) {
|
|
||||||
binding.llCreatorRank.visibility = View.GONE
|
|
||||||
binding.rvCreatorRank.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llCreatorRank.visibility = View.VISIBLE
|
|
||||||
binding.rvCreatorRank.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
creatorRankViewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRecommendSeries() {
|
|
||||||
seriesAdapter = UserProfileSeriesListAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
isVisibleCreator = true
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRecommendSeries
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
seriesAdapter.itemCount - 1 -> {
|
|
||||||
outRect.right = 0
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = seriesAdapter
|
|
||||||
|
|
||||||
recommendSeriesViewModel.seriesListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
seriesAdapter.addItems(it)
|
|
||||||
binding.llRecommendSeries.visibility = if (
|
|
||||||
seriesAdapter.itemCount <= 0 && it.isEmpty()
|
|
||||||
) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
recommendSeriesViewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.llRecommendSeriesRefresh.setOnClickListener {
|
|
||||||
seriesAdapter.clear()
|
|
||||||
recommendSeriesViewModel.getRecommendSeriesList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupBanner() {
|
|
||||||
val layoutParams = binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams as LinearLayout.LayoutParams
|
|
||||||
|
|
||||||
val pagerWidth = screenWidth.toDouble() - 26.7f.dpToPx()
|
|
||||||
val pagerHeight = (pagerWidth * 0.53).roundToInt()
|
|
||||||
layoutParams.width = pagerWidth.roundToInt()
|
|
||||||
layoutParams.height = pagerHeight
|
|
||||||
|
|
||||||
bannerAdapter = AudioContentMainBannerAdapter(
|
|
||||||
requireContext(),
|
|
||||||
pagerWidth.roundToInt(),
|
|
||||||
pagerHeight
|
|
||||||
) {
|
|
||||||
when (it.type) {
|
|
||||||
AudioContentBannerType.EVENT -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), EventDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_EVENT, it.eventItem!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.CREATOR -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it.creatorId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.SERIES -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it.seriesId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.LINK -> {
|
|
||||||
startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(it.link!!)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams = layoutParams
|
|
||||||
|
|
||||||
binding.rvBanner.apply {
|
|
||||||
adapter = bannerAdapter as BaseBannerAdapter<Any>
|
|
||||||
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(1000)
|
|
||||||
setInterval(4 * 1000)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.setIndicatorView(binding.indicatorBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
bannerViewModel.bannerLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (bannerAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.rvBanner.visibility = View.GONE
|
|
||||||
binding.indicatorBanner.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.rvBanner.visibility = View.VISIBLE
|
|
||||||
binding.indicatorBanner.visibility = View.VISIBLE
|
|
||||||
binding.rvBanner.refreshData(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bannerViewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContentTheme() {
|
|
||||||
newContentThemeAdapter = AudioContentMainNewContentThemeAdapter {
|
|
||||||
newContentViewModel.getNewContentOfTheme(theme = it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentThemeAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.adapter = newContentThemeAdapter
|
|
||||||
|
|
||||||
newContentViewModel.themeListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llNewContent.visibility = View.VISIBLE
|
|
||||||
newContentThemeAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
binding.ivNewContentAll.setOnClickListener {
|
|
||||||
startActivity(Intent(requireContext(), AudioContentNewAllActivity::class.java))
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter = AudioContentMainContentAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContent.adapter = newContentAdapter
|
|
||||||
|
|
||||||
newContentViewModel.newContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentViewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
binding.pbNewContent.visibility = if (it) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentViewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentRankingSortType() {
|
|
||||||
contentRankingSortAdapter = AudioContentMainNewContentThemeAdapter {
|
|
||||||
contentRankingViewModel.getContentRanking(sort = it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvContentRankingSort.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvContentRankingSort.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankingSortAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvContentRankingSort.adapter = contentRankingSortAdapter
|
|
||||||
|
|
||||||
contentRankingViewModel.contentRankingSortListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llContentRanking.visibility = View.VISIBLE
|
|
||||||
contentRankingSortAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("SetTextI18n")
|
|
||||||
private fun setupContentRanking() {
|
|
||||||
binding.ivContentRankingAll.setOnClickListener {
|
|
||||||
startActivity(Intent(requireContext(), AudioContentRankingAllActivity::class.java))
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankingAdapter = AudioContentMainRankingAdapter(
|
|
||||||
width = (screenWidth * 0.66).toInt()
|
|
||||||
) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvContentRanking.layoutManager = GridLayoutManager(
|
|
||||||
context,
|
|
||||||
3,
|
|
||||||
GridLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvContentRanking.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
outRect.top = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.left = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.right = 13.3f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvContentRanking.adapter = contentRankingAdapter
|
|
||||||
|
|
||||||
contentRankingViewModel.contentRankingLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llContentRanking.visibility = View.VISIBLE
|
|
||||||
binding.tvDate.text = "${it.startDate}~${it.endDate}"
|
|
||||||
contentRankingAdapter.addItems(it.items)
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankingViewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCuration() {
|
|
||||||
curationAdapter = AudioContentMainCurationAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
|
|
||||||
onClickCurationMore = { curationId, title ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentCurationActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_CURATION_ID, curationId)
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_CURATION_TITLE, title)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.VERTICAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.top = 40f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 20f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
curationAdapter.itemCount - 1 -> {
|
|
||||||
outRect.top = 20f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 40f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.top = 20f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 20f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.addOnScrollListener(object : RecyclerView.OnScrollListener() {
|
|
||||||
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
|
|
||||||
super.onScrolled(recyclerView, dx, dy)
|
|
||||||
|
|
||||||
val lastVisibleItemPosition = (recyclerView.layoutManager as LinearLayoutManager?)!!
|
|
||||||
.findLastCompletelyVisibleItemPosition()
|
|
||||||
val itemTotalCount = recyclerView.adapter!!.itemCount - 1
|
|
||||||
|
|
||||||
// 스크롤이 끝에 도달했는지 확인
|
|
||||||
if (!recyclerView.canScrollVertically(1) &&
|
|
||||||
lastVisibleItemPosition == itemTotalCount
|
|
||||||
) {
|
|
||||||
curationViewModel.getCurationList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = curationAdapter
|
|
||||||
|
|
||||||
curationViewModel.curationListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (curationViewModel.page == 2) {
|
|
||||||
curationAdapter.clear()
|
|
||||||
}
|
|
||||||
|
|
||||||
curationAdapter.addItems(it)
|
|
||||||
|
|
||||||
binding.rvCuration.visibility = if (curationAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
curationViewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
binding.pbCuration.visibility = if (it) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
curationViewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,42 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main
|
|
||||||
|
|
||||||
import android.view.View
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import coil.load
|
|
||||||
import coil.transform.CircleCropTransformation
|
|
||||||
import coil.transform.RoundedCornersTransformation
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
|
|
||||||
class AudioContentMainItemViewHolder(
|
|
||||||
private val binding: ItemAudioContentMainBinding,
|
|
||||||
private val onClickItem: (Long) -> Unit,
|
|
||||||
private val onClickCreator: (Long) -> Unit
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
fun bind(item: GetAudioContentMainItem) {
|
|
||||||
binding.ivPoint.visibility = if (item.isPointAvailable) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.ivAudioContentCoverImage.load(item.coverImageUrl) {
|
|
||||||
crossfade(true)
|
|
||||||
placeholder(R.drawable.ic_place_holder)
|
|
||||||
transformations(RoundedCornersTransformation(2.7f.dpToPx()))
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.ivAudioContentCreator.load(item.creatorProfileImageUrl) {
|
|
||||||
crossfade(true)
|
|
||||||
placeholder(R.drawable.ic_place_holder)
|
|
||||||
transformations(CircleCropTransformation())
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvAudioContentTitle.text = item.title
|
|
||||||
binding.tvAudioContentCreatorNickname.text = item.creatorNickname
|
|
||||||
|
|
||||||
binding.ivAudioContentCreator.setOnClickListener { onClickCreator(item.creatorId) }
|
|
||||||
binding.root.setOnClickListener { onClickItem(item.contentId) }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -4,13 +4,6 @@ import androidx.annotation.Keep
|
|||||||
import com.google.gson.annotations.SerializedName
|
import com.google.gson.annotations.SerializedName
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventItem
|
import kr.co.vividnext.sodalive.settings.event.EventItem
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class ContentCreatorResponse(
|
|
||||||
@SerializedName("creatorId") val creatorId: Long,
|
|
||||||
@SerializedName("creatorNickname") val creatorNickname: String,
|
|
||||||
@SerializedName("creatorProfileImageUrl") val creatorProfileImageUrl: String
|
|
||||||
)
|
|
||||||
|
|
||||||
@Keep
|
@Keep
|
||||||
data class GetAudioContentMainItem(
|
data class GetAudioContentMainItem(
|
||||||
@SerializedName("contentId") val contentId: Long,
|
@SerializedName("contentId") val contentId: Long,
|
||||||
|
|||||||
@@ -1,54 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.banner
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AudioContentMainBannerViewModel(
|
|
||||||
private val repository: AudioContentRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _bannerLiveData = MutableLiveData<List<GetAudioContentBannerResponse>>()
|
|
||||||
val bannerLiveData: LiveData<List<GetAudioContentBannerResponse>>
|
|
||||||
get() = _bannerLiveData
|
|
||||||
|
|
||||||
fun getMainBannerList() {
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getMainBannerList(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_bannerLiveData.postValue(it.data!!)
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"배너를 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"배너를 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,102 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.curation
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentMainContentAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainCurationBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
|
|
||||||
class AudioContentMainCurationAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit,
|
|
||||||
private val onClickCreator: (Long) -> Unit,
|
|
||||||
private val onClickCurationMore: (Long, String) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainCurationAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
private val items = mutableListOf<GetAudioContentCurationResponse>()
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemAudioContentMainCurationBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
fun bind(item: GetAudioContentCurationResponse) {
|
|
||||||
binding.tvTitle.text = item.title
|
|
||||||
binding.tvDesc.text = item.description
|
|
||||||
binding.ivAll.setOnClickListener { onClickCurationMore(item.curationId, item.title) }
|
|
||||||
setAudioContentList(item.audioContents)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setAudioContentList(audioContents: List<GetAudioContentMainItem>) {
|
|
||||||
val adapter = AudioContentMainContentAdapter(onClickItem, onClickCreator)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
if (binding.rvCuration.itemDecorationCount == 0) {
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
adapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
|
||||||
binding.rvCuration.adapter = adapter
|
|
||||||
adapter.addItems(audioContents)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemAudioContentMainCurationBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetAudioContentCurationResponse>) {
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
|
|
||||||
fun clear() {
|
|
||||||
this.items.clear()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,85 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.curation
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AudioContentMainCurationViewModel(
|
|
||||||
private val repository: AudioContentRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _curationListLiveData = MutableLiveData<List<GetAudioContentCurationResponse>>()
|
|
||||||
val curationListLiveData: LiveData<List<GetAudioContentCurationResponse>>
|
|
||||||
get() = _curationListLiveData
|
|
||||||
|
|
||||||
var page = 1
|
|
||||||
var isLast = false
|
|
||||||
private val pageSize = 10
|
|
||||||
|
|
||||||
fun getCurationList() {
|
|
||||||
if (!_isLoading.value!! && !isLast) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getCurationList(
|
|
||||||
page = page,
|
|
||||||
size = pageSize,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
page += 1
|
|
||||||
|
|
||||||
if (it.data.isNotEmpty()) {
|
|
||||||
_curationListLiveData.postValue(it.data!!)
|
|
||||||
} else {
|
|
||||||
_curationListLiveData.postValue(listOf())
|
|
||||||
isLast = true
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"큐레이션을 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"큐레이션을 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun refresh() {
|
|
||||||
page = 1
|
|
||||||
isLast = false
|
|
||||||
getCurationList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,100 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.new_content
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AudioContentMainNewContentViewModel(
|
|
||||||
private val repository: AudioContentRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _newContentListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val newContentListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _newContentListLiveData
|
|
||||||
|
|
||||||
private var _themeListLiveData = MutableLiveData<List<String>>()
|
|
||||||
val themeListLiveData: LiveData<List<String>>
|
|
||||||
get() = _themeListLiveData
|
|
||||||
|
|
||||||
fun getThemeList() {
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getNewContentThemeList(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val themeList = listOf("전체").union(it.data).toList()
|
|
||||||
_themeListLiveData.postValue(themeList)
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getNewContentOfTheme(theme: String) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getNewContentOfTheme(
|
|
||||||
theme = if (theme == "전체") {
|
|
||||||
""
|
|
||||||
} else {
|
|
||||||
theme
|
|
||||||
},
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_newContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
_isLoading.value = false
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,54 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.order
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AudioContentMainOrderListViewModel(
|
|
||||||
private val repository: AudioContentRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _orderListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val orderListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _orderListLiveData
|
|
||||||
|
|
||||||
fun getOrderList() {
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getMainOrderList(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_orderListLiveData.postValue(it.data!!)
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"주문정보를 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"주문정보를 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,55 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.ranking
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentRepository
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.explorer.GetExplorerSectionResponse
|
|
||||||
|
|
||||||
class AudioContentMainCreatorRankingViewModel(
|
|
||||||
private val repository: AudioContentRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private val _creatorRankLiveData = MutableLiveData<GetExplorerSectionResponse>()
|
|
||||||
val creatorRankLiveData: LiveData<GetExplorerSectionResponse>
|
|
||||||
get() = _creatorRankLiveData
|
|
||||||
|
|
||||||
fun getCreatorRank() {
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository
|
|
||||||
.getCreatorRank(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_creatorRankLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"인기 크리에이터를 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"인기 크리에이터를 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,66 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.ranking
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import coil.load
|
|
||||||
import coil.transform.RoundedCornersTransformation
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainRankingBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
|
|
||||||
class AudioContentMainRankingAdapter(
|
|
||||||
private val width: Int,
|
|
||||||
private val onClickItem: (Long) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainRankingAdapter.AudioContentMainRankingItemViewHolder>() {
|
|
||||||
|
|
||||||
inner class AudioContentMainRankingItemViewHolder(
|
|
||||||
private val binding: ItemAudioContentMainRankingBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
@SuppressLint("SetTextI18n")
|
|
||||||
fun bind(item: GetAudioContentRankingItem, index: Int) {
|
|
||||||
val lp = binding.root.layoutParams
|
|
||||||
lp.width = width
|
|
||||||
binding.root.layoutParams = lp
|
|
||||||
|
|
||||||
binding.root.setOnClickListener { onClickItem(item.contentId) }
|
|
||||||
binding.tvTitle.text = item.title
|
|
||||||
binding.tvRank.text = "${index + 1}"
|
|
||||||
binding.tvNickname.text = item.creatorNickname
|
|
||||||
|
|
||||||
binding.ivCover.load(item.coverImageUrl) {
|
|
||||||
crossfade(true)
|
|
||||||
placeholder(R.drawable.ic_place_holder)
|
|
||||||
transformations(RoundedCornersTransformation(2.7f.dpToPx()))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private val items = mutableListOf<GetAudioContentRankingItem>()
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetAudioContentRankingItem>) {
|
|
||||||
this.items.clear()
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(
|
|
||||||
parent: ViewGroup,
|
|
||||||
viewType: Int
|
|
||||||
) = AudioContentMainRankingItemViewHolder(
|
|
||||||
ItemAudioContentMainRankingBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: AudioContentMainRankingItemViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position], index = position)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,86 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.ranking
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRanking
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AudioContentMainRankingViewModel(
|
|
||||||
private val repository: AudioContentRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _contentRankingSortListLiveData = MutableLiveData<List<String>>()
|
|
||||||
val contentRankingSortListLiveData: LiveData<List<String>>
|
|
||||||
get() = _contentRankingSortListLiveData
|
|
||||||
|
|
||||||
private var _contentRankingLiveData = MutableLiveData<GetAudioContentRanking>()
|
|
||||||
val contentRankingLiveData: LiveData<GetAudioContentRanking>
|
|
||||||
get() = _contentRankingLiveData
|
|
||||||
|
|
||||||
fun getContentRankingSortType() {
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentRankingSortType(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_contentRankingSortListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getContentRanking(sort: String = "매출") {
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentRanking(
|
|
||||||
page = 1,
|
|
||||||
size = 12,
|
|
||||||
sortType = sort,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_contentRankingLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,55 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.recommend_series
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.SeriesRepository
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AudioContentMainRecommendSeriesViewModel(
|
|
||||||
private val repository: SeriesRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _seriesListLiveData = MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val seriesListLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _seriesListLiveData
|
|
||||||
|
|
||||||
fun getRecommendSeriesList() {
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository
|
|
||||||
.getRecommendSeriesList(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_seriesListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"추천 시리즈를 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"추천 시리즈를 불러오지 못했습니다. 다시 시도해 주세요.\n" +
|
|
||||||
"계속 같은 문제가 발생할 경우 고객센터로 문의 주시기 바랍니다."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,418 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.BroadcastReceiver
|
|
||||||
import android.content.ComponentName
|
|
||||||
import android.content.Context
|
|
||||||
import android.content.Intent
|
|
||||||
import android.content.IntentFilter
|
|
||||||
import android.content.SharedPreferences
|
|
||||||
import android.graphics.Typeface
|
|
||||||
import android.os.Build
|
|
||||||
import android.os.Handler
|
|
||||||
import android.os.Looper
|
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import android.widget.TextView
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.core.content.res.ResourcesCompat
|
|
||||||
import androidx.media3.common.MediaItem
|
|
||||||
import androidx.media3.common.MediaMetadata
|
|
||||||
import androidx.media3.common.Player
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.media3.session.MediaController
|
|
||||||
import androidx.media3.session.SessionToken
|
|
||||||
import coil.load
|
|
||||||
import coil.transform.RoundedCornersTransformation
|
|
||||||
import com.google.android.material.tabs.TabLayout
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentPlayService
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.box.AudioContentBoxActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.alarm.AudioContentMainTabAlarmFragment
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.asmr.AudioContentMainTabAsmrFragment
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.content.AudioContentMainTabContentFragment
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.free.AudioContentMainTabFreeFragment
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.replay.AudioContentMainTabReplayFragment
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.AudioContentMainTabSeriesFragment
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.player.AudioContentPlayerFragment
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.player.AudioContentPlayerService
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseActivity
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ActivityAudioContentMainBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.mypage.alarm.AlarmListActivity
|
|
||||||
import kotlin.math.min
|
|
||||||
|
|
||||||
enum class AudioContentMainTab {
|
|
||||||
HOME, SERIES, CONTENT, ALARM, ASMR, REPLAY, FREE;
|
|
||||||
|
|
||||||
companion object {
|
|
||||||
fun fromOrdinal(ordinal: Int): AudioContentMainTab? {
|
|
||||||
return values().getOrNull(ordinal)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AudioContentMainActivity : BaseActivity<ActivityAudioContentMainBinding>(
|
|
||||||
ActivityAudioContentMainBinding::inflate
|
|
||||||
) {
|
|
||||||
|
|
||||||
private var fontBold: Typeface? = null
|
|
||||||
private var fontMedium: Typeface? = null
|
|
||||||
|
|
||||||
private var startTabPosition: AudioContentMainTab = AudioContentMainTab.SERIES
|
|
||||||
|
|
||||||
private var mediaController: MediaController? = null
|
|
||||||
private val handler = Handler(Looper.getMainLooper())
|
|
||||||
private val audioContentReceiver = AudioContentReceiver()
|
|
||||||
|
|
||||||
override fun onDestroy() {
|
|
||||||
deInitMiniPlayer()
|
|
||||||
SharedPreferenceManager.unregisterOnSharedPreferenceChangeListener(preferenceChangeListener)
|
|
||||||
super.onDestroy()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun showPlayerFragment() {
|
|
||||||
val playerFragment = AudioContentPlayerFragment(screenWidth, arrayListOf())
|
|
||||||
playerFragment.show(supportFragmentManager, playerFragment.tag)
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("UnspecifiedRegisterReceiverFlag")
|
|
||||||
override fun onResume() {
|
|
||||||
super.onResume()
|
|
||||||
val intentFilter = IntentFilter(Constants.ACTION_MAIN_AUDIO_CONTENT_RECEIVER)
|
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
|
|
||||||
registerReceiver(audioContentReceiver, intentFilter, Context.RECEIVER_NOT_EXPORTED)
|
|
||||||
} else {
|
|
||||||
registerReceiver(audioContentReceiver, intentFilter)
|
|
||||||
}
|
|
||||||
|
|
||||||
startService(
|
|
||||||
Intent(this, AudioContentPlayService::class.java).apply {
|
|
||||||
action = AudioContentPlayService.MusicAction.INIT.name
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onPause() {
|
|
||||||
unregisterReceiver(audioContentReceiver)
|
|
||||||
super.onPause()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun setupView() {
|
|
||||||
startTabPosition = AudioContentMainTab.fromOrdinal(
|
|
||||||
intent.getIntExtra(
|
|
||||||
Constants.EXTRA_START_TAB_POSITION,
|
|
||||||
AudioContentMainTab.SERIES.ordinal
|
|
||||||
)
|
|
||||||
) ?: AudioContentMainTab.SERIES
|
|
||||||
|
|
||||||
setupToolbar()
|
|
||||||
loadFont()
|
|
||||||
setupTabs()
|
|
||||||
|
|
||||||
SharedPreferenceManager.registerOnSharedPreferenceChangeListener(preferenceChangeListener)
|
|
||||||
if (SharedPreferenceManager.isPlayerServiceRunning) {
|
|
||||||
initAndVisibleMiniPlayer()
|
|
||||||
} else {
|
|
||||||
deInitMiniPlayer()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupToolbar() {
|
|
||||||
val toolbar = binding.toolbar
|
|
||||||
|
|
||||||
toolbar.ivContentKeep.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
applicationContext,
|
|
||||||
AudioContentBoxActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
toolbar.ivAlarm.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
applicationContext,
|
|
||||||
AlarmListActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun loadFont() {
|
|
||||||
fontBold = ResourcesCompat.getFont(this, R.font.gmarket_sans_bold)
|
|
||||||
fontMedium = ResourcesCompat.getFont(this, R.font.gmarket_sans_medium)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupTabs() {
|
|
||||||
val tabs = binding.tabs
|
|
||||||
val tabTitles = listOf("홈", "시리즈", "단편", "모닝콜", "ASMR", "다시듣기", "무료")
|
|
||||||
for (title in tabTitles) {
|
|
||||||
tabs.addTab(tabs.newTab().setText(title))
|
|
||||||
}
|
|
||||||
|
|
||||||
tabs.addOnTabSelectedListener(object : TabLayout.OnTabSelectedListener {
|
|
||||||
override fun onTabSelected(tab: TabLayout.Tab) {
|
|
||||||
val selectedTab = AudioContentMainTab.fromOrdinal(tab.position)
|
|
||||||
if (selectedTab == null || selectedTab == AudioContentMainTab.HOME) finish()
|
|
||||||
|
|
||||||
replaceFragment(selectedTab = selectedTab!!)
|
|
||||||
tab.view.isSelected = true
|
|
||||||
setTabFont(tab, fontBold)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onTabUnselected(tab: TabLayout.Tab) {
|
|
||||||
tab.view.isSelected = false
|
|
||||||
setTabFont(tab, fontMedium)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onTabReselected(tab: TabLayout.Tab) {
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
tabs.getTabAt(startTabPosition.ordinal)?.let {
|
|
||||||
it.select()
|
|
||||||
scrollToTab(tabs, startTabPosition.ordinal)
|
|
||||||
}
|
|
||||||
replaceFragment(selectedTab = startTabPosition)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun scrollToTab(tabLayout: TabLayout, position: Int) {
|
|
||||||
tabLayout.post {
|
|
||||||
val layout = tabLayout.getChildAt(0) as ViewGroup
|
|
||||||
val tabView = layout.getChildAt(position)
|
|
||||||
|
|
||||||
// 화면 전체 너비
|
|
||||||
val parentWidth = tabLayout.width
|
|
||||||
// 선택한 탭의 중심 좌표
|
|
||||||
val tabCenterX = tabView.left + tabView.width / 2
|
|
||||||
// 스크롤 할 위치 = 탭의 중심을 화면 중앙에 배치
|
|
||||||
val scrollToX = tabCenterX - parentWidth / 2
|
|
||||||
|
|
||||||
tabLayout.scrollTo(min(tabView.left, scrollToX), 0)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun replaceFragment(selectedTab: AudioContentMainTab) {
|
|
||||||
val startFragment = when (selectedTab) {
|
|
||||||
AudioContentMainTab.CONTENT -> AudioContentMainTabContentFragment()
|
|
||||||
AudioContentMainTab.ALARM -> AudioContentMainTabAlarmFragment()
|
|
||||||
AudioContentMainTab.ASMR -> AudioContentMainTabAsmrFragment()
|
|
||||||
AudioContentMainTab.REPLAY -> AudioContentMainTabReplayFragment()
|
|
||||||
AudioContentMainTab.FREE -> AudioContentMainTabFreeFragment()
|
|
||||||
else -> AudioContentMainTabSeriesFragment()
|
|
||||||
}
|
|
||||||
|
|
||||||
supportFragmentManager.beginTransaction()
|
|
||||||
.replace(
|
|
||||||
R.id.fl_container,
|
|
||||||
startFragment
|
|
||||||
)
|
|
||||||
.commit()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setTabFont(tab: TabLayout.Tab, font: Typeface?) {
|
|
||||||
(tab.view.getChildAt(1) as? TextView)?.typeface = font
|
|
||||||
}
|
|
||||||
|
|
||||||
private val preferenceChangeListener =
|
|
||||||
SharedPreferences.OnSharedPreferenceChangeListener { sharedPreferences, key ->
|
|
||||||
// 특정 키에 대한 값이 변경될 때 UI 업데이트
|
|
||||||
if (key == Constants.PREF_IS_PLAYER_SERVICE_RUNNING) {
|
|
||||||
if (sharedPreferences.getBoolean(key, false)) {
|
|
||||||
handler.postDelayed(
|
|
||||||
{
|
|
||||||
initAndVisibleMiniPlayer()
|
|
||||||
},
|
|
||||||
1500
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
deInitMiniPlayer()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun initAndVisibleMiniPlayer() {
|
|
||||||
binding.clMiniPlayer.visibility = View.VISIBLE
|
|
||||||
binding.clMiniPlayer.setOnClickListener { showPlayerFragment() }
|
|
||||||
binding.ivPlayerStop.setOnClickListener {
|
|
||||||
startService(
|
|
||||||
Intent(applicationContext, AudioContentPlayerService::class.java).apply {
|
|
||||||
action = "STOP_SERVICE"
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
connectPlayerService()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun connectPlayerService() {
|
|
||||||
val componentName = ComponentName(applicationContext, AudioContentPlayerService::class.java)
|
|
||||||
val sessionToken = SessionToken(applicationContext, componentName)
|
|
||||||
val mediaControllerFuture =
|
|
||||||
MediaController.Builder(applicationContext, sessionToken).buildAsync()
|
|
||||||
mediaControllerFuture.addListener(
|
|
||||||
{
|
|
||||||
mediaController = mediaControllerFuture.get()
|
|
||||||
setupMediaController()
|
|
||||||
updateMediaMetadata(mediaController?.mediaMetadata)
|
|
||||||
|
|
||||||
binding.ivPlayerPlayOrPause.setImageResource(
|
|
||||||
if (mediaController!!.isPlaying) {
|
|
||||||
R.drawable.ic_player_pause
|
|
||||||
} else {
|
|
||||||
R.drawable.ic_player_play
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.ivPlayerPlayOrPause.setOnClickListener {
|
|
||||||
mediaController?.let {
|
|
||||||
if (it.playWhenReady) {
|
|
||||||
it.pause()
|
|
||||||
} else {
|
|
||||||
it.play()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
ContextCompat.getMainExecutor(applicationContext)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun updateMediaMetadata(metadata: MediaMetadata?) {
|
|
||||||
metadata?.let {
|
|
||||||
binding.tvPlayerTitle.text = it.title
|
|
||||||
binding.tvPlayerNickname.text = it.artist
|
|
||||||
|
|
||||||
binding.ivPlayerCover.load(it.artworkUri) {
|
|
||||||
crossfade(true)
|
|
||||||
placeholder(R.drawable.ic_place_holder)
|
|
||||||
transformations(RoundedCornersTransformation(4f))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupMediaController() {
|
|
||||||
if (mediaController == null) {
|
|
||||||
deInitMiniPlayer()
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
mediaController!!.addListener(object : Player.Listener {
|
|
||||||
override fun onMediaItemTransition(mediaItem: MediaItem?, reason: Int) {
|
|
||||||
updateMediaMetadata(mediaItem?.mediaMetadata)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onPlayWhenReadyChanged(playWhenReady: Boolean, reason: Int) {
|
|
||||||
binding.ivPlayerPlayOrPause.setImageResource(
|
|
||||||
if (playWhenReady) {
|
|
||||||
R.drawable.ic_player_pause
|
|
||||||
} else {
|
|
||||||
R.drawable.ic_player_play
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun deInitMiniPlayer() {
|
|
||||||
binding.clMiniPlayer.visibility = View.GONE
|
|
||||||
mediaController?.release()
|
|
||||||
mediaController = null
|
|
||||||
}
|
|
||||||
|
|
||||||
inner class AudioContentReceiver : BroadcastReceiver() {
|
|
||||||
override fun onReceive(context: Context?, intent: Intent?) {
|
|
||||||
val contentId = intent?.getLongExtra(Constants.EXTRA_AUDIO_CONTENT_ID, 0)
|
|
||||||
val title = intent?.getStringExtra(Constants.EXTRA_AUDIO_CONTENT_TITLE)
|
|
||||||
val nickname = intent?.getStringExtra(Constants.EXTRA_NICKNAME)
|
|
||||||
val coverImageUrl = intent?.getStringExtra(
|
|
||||||
Constants.EXTRA_AUDIO_CONTENT_COVER_IMAGE_URL
|
|
||||||
)
|
|
||||||
|
|
||||||
val isPlaying = intent?.getBooleanExtra(Constants.EXTRA_AUDIO_CONTENT_PLAYING, false)
|
|
||||||
val isShowing = intent?.getBooleanExtra(Constants.EXTRA_AUDIO_CONTENT_SHOWING, false)
|
|
||||||
|
|
||||||
if (isShowing == true) {
|
|
||||||
binding.rlMiniPlayer.visibility = View.VISIBLE
|
|
||||||
if (contentId != null && contentId > 0) {
|
|
||||||
binding.rlMiniPlayer.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(applicationContext, AudioContentDetailActivity::class.java)
|
|
||||||
.apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, contentId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (isPlaying == true) {
|
|
||||||
binding.ivPlayOrPause.setImageResource(R.drawable.ic_noti_pause)
|
|
||||||
binding.ivPlayOrPause.setOnClickListener {
|
|
||||||
startService(
|
|
||||||
Intent(
|
|
||||||
this@AudioContentMainActivity,
|
|
||||||
AudioContentPlayService::class.java
|
|
||||||
).apply {
|
|
||||||
action = AudioContentPlayService.MusicAction.PAUSE.name
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
binding.ivPlayOrPause.setImageResource(R.drawable.ic_noti_play)
|
|
||||||
binding.ivPlayOrPause.setOnClickListener {
|
|
||||||
startService(
|
|
||||||
Intent(
|
|
||||||
this@AudioContentMainActivity,
|
|
||||||
AudioContentPlayService::class.java
|
|
||||||
).apply {
|
|
||||||
action = AudioContentPlayService.MusicAction.PLAY.name
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.ivStop.setOnClickListener {
|
|
||||||
startService(
|
|
||||||
Intent(
|
|
||||||
this@AudioContentMainActivity,
|
|
||||||
AudioContentPlayService::class.java
|
|
||||||
).apply {
|
|
||||||
action = AudioContentPlayService.MusicAction.STOP.name
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!title.isNullOrBlank()) {
|
|
||||||
binding.tvMiniPlayerTitle.text = title
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!nickname.isNullOrBlank()) {
|
|
||||||
binding.tvNickname.text = nickname
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!coverImageUrl.isNullOrBlank()) {
|
|
||||||
binding.ivCover.load(coverImageUrl) {
|
|
||||||
crossfade(true)
|
|
||||||
placeholder(R.drawable.bg_placeholder)
|
|
||||||
transformations(RoundedCornersTransformation(5.3f.dpToPx()))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
handler.post {
|
|
||||||
binding.ivPlayOrPause.setImageResource(0)
|
|
||||||
binding.ivCover.setImageResource(0)
|
|
||||||
binding.tvMiniPlayerTitle.text = ""
|
|
||||||
binding.tvNickname.text = ""
|
|
||||||
binding.rlMiniPlayer.visibility = View.GONE
|
|
||||||
binding.ivPlayOrPause.setOnClickListener {}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,97 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentMainContentAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainCurationBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
|
|
||||||
class AudioContentMainContentCurationAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit,
|
|
||||||
private val onClickCreator: (Long) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainContentCurationAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
private val items = mutableListOf<GetContentCurationResponse>()
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemAudioContentMainCurationBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
fun bind(item: GetContentCurationResponse) {
|
|
||||||
binding.tvTitle.text = item.title
|
|
||||||
binding.ivAll.visibility = View.GONE
|
|
||||||
binding.tvDesc.visibility = View.GONE
|
|
||||||
setAudioContentList(item.items)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setAudioContentList(audioContents: List<GetAudioContentMainItem>) {
|
|
||||||
val adapter = AudioContentMainContentAdapter(onClickItem, onClickCreator)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
if (binding.rvCuration.itemDecorationCount == 0) {
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
adapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
|
||||||
binding.rvCuration.adapter = adapter
|
|
||||||
adapter.addItems(audioContents)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemAudioContentMainCurationBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetContentCurationResponse>) {
|
|
||||||
this.items.clear()
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,89 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import coil.load
|
|
||||||
import coil.transform.CircleCropTransformation
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemContentRankCreatorBinding
|
|
||||||
|
|
||||||
class ContentRankCreatorAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit,
|
|
||||||
) : RecyclerView.Adapter<ContentRankCreatorAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
private var selectedCreatorId: Long = 0
|
|
||||||
private val items = mutableListOf<ContentCreatorResponse>()
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemContentRankCreatorBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun bind(item: ContentCreatorResponse) {
|
|
||||||
binding.root.setOnClickListener {
|
|
||||||
if (selectedCreatorId != item.creatorId) {
|
|
||||||
selectedCreatorId = item.creatorId
|
|
||||||
onClickItem(item.creatorId)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvNickname.text = item.creatorNickname
|
|
||||||
binding.ivProfile.load(item.creatorProfileImageUrl) {
|
|
||||||
transformations(CircleCropTransformation())
|
|
||||||
placeholder(R.drawable.ic_place_holder)
|
|
||||||
crossfade(true)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (item.creatorId == selectedCreatorId) {
|
|
||||||
binding.ivBg.setImageResource(R.drawable.bg_round_corner_33_3_transparent_3bb9f1)
|
|
||||||
binding.ivBg.visibility = View.VISIBLE
|
|
||||||
binding.tvNickname.setTextColor(
|
|
||||||
ContextCompat.getColor(
|
|
||||||
context,
|
|
||||||
R.color.color_3bb9f1
|
|
||||||
)
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
binding.ivBg.setImageResource(0)
|
|
||||||
binding.ivBg.visibility = View.GONE
|
|
||||||
binding.tvNickname.setTextColor(
|
|
||||||
ContextCompat.getColor(
|
|
||||||
context,
|
|
||||||
R.color.color_bbbbbb
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemContentRankCreatorBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<ContentCreatorResponse>) {
|
|
||||||
this.items.addAll(items)
|
|
||||||
if (this.items.isNotEmpty()) {
|
|
||||||
this.selectedCreatorId = this.items[0].creatorId
|
|
||||||
}
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,11 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetContentCurationResponse(
|
|
||||||
@SerializedName("title") val title: String,
|
|
||||||
@SerializedName("items") val items: List<GetAudioContentMainItem>
|
|
||||||
)
|
|
||||||
@@ -1,112 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.constraintlayout.widget.ConstraintLayout
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.bumptech.glide.Glide
|
|
||||||
import com.bumptech.glide.load.MultiTransformation
|
|
||||||
import com.bumptech.glide.load.resource.bitmap.CenterCrop
|
|
||||||
import com.bumptech.glide.load.resource.bitmap.CircleCrop
|
|
||||||
import com.bumptech.glide.load.resource.bitmap.RoundedCorners
|
|
||||||
import com.bumptech.glide.request.RequestOptions
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainTabPopularContentBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.extensions.moneyFormat
|
|
||||||
|
|
||||||
class PopularContentByCreatorAdapter(
|
|
||||||
private val itemWidth: Int,
|
|
||||||
private val onClickItem: (Long) -> Unit,
|
|
||||||
private val onClickCreator: (Long) -> Unit
|
|
||||||
) : RecyclerView.Adapter<PopularContentByCreatorAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
private val items = mutableListOf<GetAudioContentRankingItem>()
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemAudioContentMainTabPopularContentBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
|
|
||||||
fun bind(item: GetAudioContentRankingItem) {
|
|
||||||
val lp = binding.ivCover.layoutParams as ConstraintLayout.LayoutParams
|
|
||||||
lp.width = itemWidth
|
|
||||||
lp.height = itemWidth
|
|
||||||
binding.ivCover.layoutParams = lp
|
|
||||||
|
|
||||||
binding.ivPoint.visibility = if (item.isPointAvailable) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
Glide
|
|
||||||
.with(context)
|
|
||||||
.load(item.coverImageUrl)
|
|
||||||
.apply(
|
|
||||||
RequestOptions().transform(
|
|
||||||
MultiTransformation(
|
|
||||||
CenterCrop(),
|
|
||||||
RoundedCorners(5.3f.dpToPx().toInt())
|
|
||||||
)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
.placeholder(R.drawable.bg_black)
|
|
||||||
.into(binding.ivCover)
|
|
||||||
|
|
||||||
Glide
|
|
||||||
.with(context)
|
|
||||||
.load(item.creatorProfileImageUrl)
|
|
||||||
.apply(
|
|
||||||
RequestOptions().transform(
|
|
||||||
CircleCrop()
|
|
||||||
)
|
|
||||||
)
|
|
||||||
.placeholder(R.drawable.bg_black)
|
|
||||||
.into(binding.ivCreator)
|
|
||||||
|
|
||||||
binding.tvTitle.text = item.title
|
|
||||||
binding.tvNickname.text = item.creatorNickname
|
|
||||||
|
|
||||||
if (item.price > 0) {
|
|
||||||
binding.ivCan.visibility = View.VISIBLE
|
|
||||||
binding.tvCan.text = item.price.moneyFormat()
|
|
||||||
} else {
|
|
||||||
binding.ivCan.visibility = View.GONE
|
|
||||||
binding.tvCan.text = "무료"
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvTime.text = item.duration
|
|
||||||
|
|
||||||
binding.ivCover.setOnClickListener { onClickItem(item.contentId) }
|
|
||||||
binding.ivCreator.setOnClickListener { onClickCreator(item.creatorId) }
|
|
||||||
binding.tvNickname.setOnClickListener { onClickCreator(item.creatorId) }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemAudioContentMainTabPopularContentBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetAudioContentRankingItem>) {
|
|
||||||
this.items.clear()
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,388 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.alarm
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.LinearLayout
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.zhpan.bannerview.BaseBannerAdapter
|
|
||||||
import com.zhpan.indicator.enums.IndicatorSlideMode
|
|
||||||
import com.zhpan.indicator.enums.IndicatorStyle
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentBannerType
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentMainContentAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.new_content.AudioContentMainNewContentThemeAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.AudioContentMainContentCurationAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.alarm.all.AlarmContentAllActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseFragment
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.FragmentAudioContentMainTabAlarmBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.live.event_banner.EventBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventDetailActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AudioContentMainTabAlarmFragment : BaseFragment<FragmentAudioContentMainTabAlarmBinding>(
|
|
||||||
FragmentAudioContentMainTabAlarmBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AudioContentMainTabAlarmViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var contentBannerAdapter: AudioContentMainBannerAdapter
|
|
||||||
private lateinit var newContentThemeAdapter: AudioContentMainNewContentThemeAdapter
|
|
||||||
private lateinit var newContentAdapter: AudioContentMainContentAdapter
|
|
||||||
private lateinit var curationAdapter: AudioContentMainContentCurationAdapter
|
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
|
||||||
super.onViewCreated(view, savedInstanceState)
|
|
||||||
setupView()
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.fetchData()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(requireActivity(), layoutInflater)
|
|
||||||
|
|
||||||
setupContentBanner()
|
|
||||||
setupNewContentTheme()
|
|
||||||
setupNewContent()
|
|
||||||
setupEventBanner()
|
|
||||||
setupCuration()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentBanner() {
|
|
||||||
val layoutParams = binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams as LinearLayout.LayoutParams
|
|
||||||
|
|
||||||
val pagerWidth = screenWidth.toDouble() - 26.7f.dpToPx()
|
|
||||||
val pagerHeight = (pagerWidth * 0.53).roundToInt()
|
|
||||||
layoutParams.width = pagerWidth.roundToInt()
|
|
||||||
layoutParams.height = pagerHeight
|
|
||||||
|
|
||||||
contentBannerAdapter = AudioContentMainBannerAdapter(
|
|
||||||
requireContext(),
|
|
||||||
pagerWidth.roundToInt(),
|
|
||||||
pagerHeight
|
|
||||||
) {
|
|
||||||
when (it.type) {
|
|
||||||
AudioContentBannerType.EVENT -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), EventDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_EVENT, it.eventItem!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.CREATOR -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it.creatorId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.SERIES -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it.seriesId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.LINK -> {
|
|
||||||
startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(it.link!!)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams = layoutParams
|
|
||||||
|
|
||||||
binding.rvBanner.apply {
|
|
||||||
adapter = contentBannerAdapter as BaseBannerAdapter<Any>
|
|
||||||
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(1000)
|
|
||||||
setInterval(4 * 1000)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.setIndicatorView(binding.indicatorBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.contentBannerLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (contentBannerAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.rvBanner.visibility = View.GONE
|
|
||||||
binding.indicatorBanner.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.rvBanner.visibility = View.VISIBLE
|
|
||||||
binding.indicatorBanner.visibility = View.VISIBLE
|
|
||||||
binding.rvBanner.refreshData(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContentTheme() {
|
|
||||||
newContentThemeAdapter = AudioContentMainNewContentThemeAdapter {
|
|
||||||
viewModel.getContentMainAlarm(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentThemeAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.adapter = newContentThemeAdapter
|
|
||||||
|
|
||||||
viewModel.themeListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llNewContent.visibility = View.VISIBLE
|
|
||||||
newContentThemeAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
binding.ivNewContentAll.setOnClickListener {
|
|
||||||
startActivity(Intent(requireContext(), AlarmContentAllActivity::class.java))
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter = AudioContentMainContentAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContent.adapter = newContentAdapter
|
|
||||||
|
|
||||||
viewModel.newContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupEventBanner() {
|
|
||||||
val imageSliderLp = binding.eventBannerSlider.layoutParams
|
|
||||||
imageSliderLp.width = screenWidth
|
|
||||||
imageSliderLp.height = (screenWidth * 300) / 1000
|
|
||||||
binding.eventBannerSlider.layoutParams = imageSliderLp
|
|
||||||
|
|
||||||
binding.eventBannerSlider.apply {
|
|
||||||
adapter = EventBannerAdapter(requireContext()) {
|
|
||||||
if (it.detailImageUrl != null) {
|
|
||||||
val intent = Intent(requireActivity(), EventDetailActivity::class.java)
|
|
||||||
intent.putExtra(Constants.EXTRA_EVENT, it)
|
|
||||||
startActivity(intent)
|
|
||||||
} else if (!it.link.isNullOrBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
Intent.ACTION_VIEW,
|
|
||||||
Uri.parse(it.link)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} as BaseBannerAdapter<Any>
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(800)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding.eventBannerSlider
|
|
||||||
.setIndicatorView(binding.indicatorEventBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.eventLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.eventBannerSlider.visibility = View.VISIBLE
|
|
||||||
binding.indicatorEventBanner.visibility = View.VISIBLE
|
|
||||||
binding.eventBannerSlider.refreshData(it)
|
|
||||||
} else {
|
|
||||||
binding.eventBannerSlider.visibility = View.GONE
|
|
||||||
binding.indicatorEventBanner.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCuration() {
|
|
||||||
curationAdapter = AudioContentMainContentCurationAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.VERTICAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.top = 30f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
curationAdapter.itemCount - 1 -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 30f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = curationAdapter
|
|
||||||
|
|
||||||
viewModel.curationListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
curationAdapter.addItems(it)
|
|
||||||
|
|
||||||
binding.rvCuration.visibility = if (curationAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,27 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.alarm
|
|
||||||
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentApi
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
|
||||||
|
|
||||||
class AudioContentMainTabAlarmRepository(private val api: AudioContentApi) {
|
|
||||||
fun getContentMainAlarm(token: String) = api.getContentMainAlarm(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getContentMainAlarmAll(
|
|
||||||
theme: String,
|
|
||||||
page: Int,
|
|
||||||
size: Int,
|
|
||||||
token: String
|
|
||||||
) = api.getContentMainAlarmAll(
|
|
||||||
theme = theme,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
page = page - 1,
|
|
||||||
size = size,
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,126 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.alarm
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventItem
|
|
||||||
|
|
||||||
class AudioContentMainTabAlarmViewModel(
|
|
||||||
private val repository: AudioContentMainTabAlarmRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _contentBannerLiveData = MutableLiveData<List<GetAudioContentBannerResponse>>()
|
|
||||||
val contentBannerLiveData: LiveData<List<GetAudioContentBannerResponse>>
|
|
||||||
get() = _contentBannerLiveData
|
|
||||||
|
|
||||||
private var _newContentListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val newContentListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _newContentListLiveData
|
|
||||||
|
|
||||||
private var _themeListLiveData = MutableLiveData<List<String>>()
|
|
||||||
val themeListLiveData: LiveData<List<String>>
|
|
||||||
get() = _themeListLiveData
|
|
||||||
|
|
||||||
private val _eventLiveData = MutableLiveData<List<EventItem>>()
|
|
||||||
val eventLiveData: LiveData<List<EventItem>>
|
|
||||||
get() = _eventLiveData
|
|
||||||
|
|
||||||
private var _curationListLiveData = MutableLiveData<List<GetContentCurationResponse>>()
|
|
||||||
val curationListLiveData: LiveData<List<GetContentCurationResponse>>
|
|
||||||
get() = _curationListLiveData
|
|
||||||
|
|
||||||
fun fetchData() {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainAlarm(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val data = it.data
|
|
||||||
|
|
||||||
_contentBannerLiveData.value = data.contentBannerList
|
|
||||||
|
|
||||||
val themeList = listOf("전체").union(data.alarmThemeList).toList()
|
|
||||||
_themeListLiveData.value = themeList
|
|
||||||
|
|
||||||
_newContentListLiveData.value = data.newAlarmContentList
|
|
||||||
_eventLiveData.value = data.eventBannerList.eventList
|
|
||||||
_curationListLiveData.value = data.curationList
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getContentMainAlarm(selectedTheme: String) {
|
|
||||||
_isLoading.value = true
|
|
||||||
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainAlarmAll(
|
|
||||||
theme = if (selectedTheme == "전체") {
|
|
||||||
""
|
|
||||||
} else {
|
|
||||||
selectedTheme
|
|
||||||
},
|
|
||||||
page = 1,
|
|
||||||
size = 10,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_newContentListLiveData.value = it.data.items
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,25 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.alarm
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.GetEventResponse
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetContentMainTabAlarmResponse(
|
|
||||||
@SerializedName("contentBannerList")
|
|
||||||
val contentBannerList: List<GetAudioContentBannerResponse>,
|
|
||||||
@SerializedName("alarmThemeList")
|
|
||||||
val alarmThemeList: List<String>,
|
|
||||||
@SerializedName("newAlarmContentList")
|
|
||||||
val newAlarmContentList: List<GetAudioContentMainItem>,
|
|
||||||
@SerializedName("rankAlarmContentList")
|
|
||||||
val rankAlarmContentList: List<GetAudioContentRankingItem>,
|
|
||||||
@SerializedName("eventBannerList")
|
|
||||||
val eventBannerList: GetEventResponse,
|
|
||||||
@SerializedName("curationList")
|
|
||||||
val curationList: List<GetContentCurationResponse>
|
|
||||||
)
|
|
||||||
@@ -1,162 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.alarm.all
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.new_content.AudioContentMainNewContentThemeAdapter
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseActivity
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ActivityAlarmContentAllBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AlarmContentAllActivity : BaseActivity<ActivityAlarmContentAllBinding>(
|
|
||||||
ActivityAlarmContentAllBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AlarmContentAllViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
|
|
||||||
private lateinit var newContentThemeAdapter: AudioContentMainNewContentThemeAdapter
|
|
||||||
private lateinit var newContentAdapter: AudioContentNewAllAdapter
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
|
|
||||||
bindData()
|
|
||||||
viewModel.getContentMainAlarmAll()
|
|
||||||
|
|
||||||
newContentThemeAdapter.addItems(listOf("전체", "모닝콜", "슬립콜", "알람"))
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(this, layoutInflater)
|
|
||||||
binding.toolbar.tvBack.text = "새로운 알람"
|
|
||||||
binding.toolbar.tvBack.setOnClickListener { finish() }
|
|
||||||
|
|
||||||
setupNewContentTheme()
|
|
||||||
setupNewContent()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContentTheme() {
|
|
||||||
newContentThemeAdapter = AudioContentMainNewContentThemeAdapter {
|
|
||||||
newContentAdapter.clear()
|
|
||||||
viewModel.selectTheme(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.layoutManager = LinearLayoutManager(
|
|
||||||
this,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentThemeAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.adapter = newContentThemeAdapter
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
val spanCount = 3
|
|
||||||
val spacing = 40
|
|
||||||
newContentAdapter = AudioContentNewAllAdapter(
|
|
||||||
itemWidth = (screenWidth - (spacing * (spanCount + 1))) / 3,
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvContent.layoutManager = GridLayoutManager(this, spanCount)
|
|
||||||
binding.rvContent.addItemDecoration(GridSpacingItemDecoration(spanCount, spacing, true))
|
|
||||||
|
|
||||||
binding.rvContent.addOnScrollListener(object : RecyclerView.OnScrollListener() {
|
|
||||||
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
|
|
||||||
super.onScrolled(recyclerView, dx, dy)
|
|
||||||
|
|
||||||
val lastVisibleItemPosition = (recyclerView.layoutManager as LinearLayoutManager?)!!
|
|
||||||
.findLastCompletelyVisibleItemPosition()
|
|
||||||
val itemTotalCount = recyclerView.adapter!!.itemCount - 1
|
|
||||||
|
|
||||||
// 스크롤이 끝에 도달했는지 확인
|
|
||||||
if (!recyclerView.canScrollVertically(1) &&
|
|
||||||
lastVisibleItemPosition == itemTotalCount
|
|
||||||
) {
|
|
||||||
viewModel.getContentMainAlarmAll()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvContent.adapter = newContentAdapter
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.isLoading.observe(this) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.toastLiveData.observe(this) {
|
|
||||||
it?.let { Toast.makeText(applicationContext, it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.newContentListLiveData.observe(this) {
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.totalCountLiveData.observe(this) {
|
|
||||||
binding.tvTotalCount.text = "$it"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,93 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.alarm.all
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.alarm.AudioContentMainTabAlarmRepository
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AlarmContentAllViewModel(
|
|
||||||
private val repository: AudioContentMainTabAlarmRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _newContentListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val newContentListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _newContentListLiveData
|
|
||||||
|
|
||||||
private var _totalCountLiveData = MutableLiveData<Int>()
|
|
||||||
val totalCountLiveData: LiveData<Int>
|
|
||||||
get() = _totalCountLiveData
|
|
||||||
|
|
||||||
private var isLast = false
|
|
||||||
private var page = 1
|
|
||||||
private val size = 10
|
|
||||||
private var selectedTheme = ""
|
|
||||||
|
|
||||||
fun getContentMainAlarmAll() {
|
|
||||||
if (!_isLoading.value!! && !isLast) {
|
|
||||||
_isLoading.value = true
|
|
||||||
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainAlarmAll(
|
|
||||||
theme = if (selectedTheme == "전체") {
|
|
||||||
""
|
|
||||||
} else {
|
|
||||||
selectedTheme
|
|
||||||
},
|
|
||||||
page = page,
|
|
||||||
size = size,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val data = it.data
|
|
||||||
_totalCountLiveData.value = data.totalCount
|
|
||||||
if (data.items.isNotEmpty()) {
|
|
||||||
page += 1
|
|
||||||
_newContentListLiveData.value = data.items
|
|
||||||
} else {
|
|
||||||
isLast = true
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun selectTheme(theme: String) {
|
|
||||||
isLast = false
|
|
||||||
page = 1
|
|
||||||
selectedTheme = theme
|
|
||||||
getContentMainAlarmAll()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,116 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.asmr
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Intent
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseActivity
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ActivityAsmrNewContentAllBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AsmrNewContentAllActivity : BaseActivity<ActivityAsmrNewContentAllBinding>(
|
|
||||||
ActivityAsmrNewContentAllBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AudioContentNewAllViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
|
|
||||||
private lateinit var newContentAdapter: AudioContentNewAllAdapter
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
|
|
||||||
bindData()
|
|
||||||
viewModel.selectTheme(theme = "ASMR", isFree = false)
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("SetTextI18n")
|
|
||||||
override fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(this, layoutInflater)
|
|
||||||
binding.toolbar.tvBack.text = "새로운 ASMR"
|
|
||||||
binding.toolbar.tvBack.setOnClickListener { finish() }
|
|
||||||
|
|
||||||
binding.tvNotice.text = "※ 최근 2주간 등록된 새로운 ASMR 입니다."
|
|
||||||
|
|
||||||
setupNewContent()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
val spanCount = 3
|
|
||||||
val spacing = 40
|
|
||||||
newContentAdapter = AudioContentNewAllAdapter(
|
|
||||||
itemWidth = (screenWidth - (spacing * (spanCount + 1))) / 3,
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvContent.layoutManager = GridLayoutManager(this, spanCount)
|
|
||||||
binding.rvContent.addItemDecoration(GridSpacingItemDecoration(spanCount, spacing, true))
|
|
||||||
|
|
||||||
binding.rvContent.addOnScrollListener(object : RecyclerView.OnScrollListener() {
|
|
||||||
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
|
|
||||||
super.onScrolled(recyclerView, dx, dy)
|
|
||||||
|
|
||||||
val lastVisibleItemPosition = (recyclerView.layoutManager as LinearLayoutManager?)!!
|
|
||||||
.findLastCompletelyVisibleItemPosition()
|
|
||||||
val itemTotalCount = recyclerView.adapter!!.itemCount - 1
|
|
||||||
|
|
||||||
// 스크롤이 끝에 도달했는지 확인
|
|
||||||
if (!recyclerView.canScrollVertically(1) &&
|
|
||||||
lastVisibleItemPosition == itemTotalCount
|
|
||||||
) {
|
|
||||||
viewModel.getNewContentList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvContent.adapter = newContentAdapter
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.isLoading.observe(this) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.toastLiveData.observe(this) {
|
|
||||||
it?.let { Toast.makeText(applicationContext, it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.newContentListLiveData.observe(this) {
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.newContentTotalCountLiveData.observe(this) {
|
|
||||||
binding.tvTotalCount.text = "$it"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,449 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.asmr
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.LinearLayout
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.zhpan.bannerview.BaseBannerAdapter
|
|
||||||
import com.zhpan.indicator.enums.IndicatorSlideMode
|
|
||||||
import com.zhpan.indicator.enums.IndicatorStyle
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentBannerType
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentMainContentAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.AudioContentMainContentCurationAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.ContentRankCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.PopularContentByCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseFragment
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.FragmentAudioContentMainTabAsmrBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.live.event_banner.EventBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventDetailActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AudioContentMainTabAsmrFragment : BaseFragment<FragmentAudioContentMainTabAsmrBinding>(
|
|
||||||
FragmentAudioContentMainTabAsmrBinding::inflate
|
|
||||||
) {
|
|
||||||
|
|
||||||
private val viewModel: AudioContentMainTabAsmrViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var contentBannerAdapter: AudioContentMainBannerAdapter
|
|
||||||
private lateinit var newContentAdapter: AudioContentMainContentAdapter
|
|
||||||
private lateinit var curationAdapter: AudioContentMainContentCurationAdapter
|
|
||||||
private lateinit var contentRankCreatorAdapter: ContentRankCreatorAdapter
|
|
||||||
private lateinit var popularContentByCreatorAdapter: PopularContentByCreatorAdapter
|
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
|
||||||
super.onViewCreated(view, savedInstanceState)
|
|
||||||
setupView()
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.fetchData()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(requireActivity(), layoutInflater)
|
|
||||||
|
|
||||||
setupContentBanner()
|
|
||||||
setupNewContent()
|
|
||||||
setupPopularContentCreator()
|
|
||||||
setupPopularContentByCreator()
|
|
||||||
setupEventBanner()
|
|
||||||
setupCuration()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentBanner() {
|
|
||||||
val layoutParams = binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams as LinearLayout.LayoutParams
|
|
||||||
|
|
||||||
val pagerWidth = screenWidth.toDouble() - 26.7f.dpToPx()
|
|
||||||
val pagerHeight = (pagerWidth * 0.53).roundToInt()
|
|
||||||
layoutParams.width = pagerWidth.roundToInt()
|
|
||||||
layoutParams.height = pagerHeight
|
|
||||||
|
|
||||||
contentBannerAdapter = AudioContentMainBannerAdapter(
|
|
||||||
requireContext(),
|
|
||||||
pagerWidth.roundToInt(),
|
|
||||||
pagerHeight
|
|
||||||
) {
|
|
||||||
when (it.type) {
|
|
||||||
AudioContentBannerType.EVENT -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), EventDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_EVENT, it.eventItem!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.CREATOR -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it.creatorId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.SERIES -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it.seriesId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.LINK -> {
|
|
||||||
startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(it.link!!)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams = layoutParams
|
|
||||||
|
|
||||||
binding.rvBanner.apply {
|
|
||||||
adapter = contentBannerAdapter as BaseBannerAdapter<Any>
|
|
||||||
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(1000)
|
|
||||||
setInterval(4 * 1000)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.setIndicatorView(binding.indicatorBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.contentBannerLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (contentBannerAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.rvBanner.visibility = View.GONE
|
|
||||||
binding.indicatorBanner.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.rvBanner.visibility = View.VISIBLE
|
|
||||||
binding.indicatorBanner.visibility = View.VISIBLE
|
|
||||||
binding.rvBanner.refreshData(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
binding.ivNewContentAll.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AsmrNewContentAllActivity::class.java)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter = AudioContentMainContentAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContent.adapter = newContentAdapter
|
|
||||||
|
|
||||||
viewModel.newContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llNewContent.visibility = View.VISIBLE
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llNewContent.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupEventBanner() {
|
|
||||||
val imageSliderLp = binding.eventBannerSlider.layoutParams
|
|
||||||
imageSliderLp.width = screenWidth
|
|
||||||
imageSliderLp.height = (screenWidth * 300) / 1000
|
|
||||||
binding.eventBannerSlider.layoutParams = imageSliderLp
|
|
||||||
|
|
||||||
binding.eventBannerSlider.apply {
|
|
||||||
adapter = EventBannerAdapter(requireContext()) {
|
|
||||||
if (it.detailImageUrl != null) {
|
|
||||||
val intent = Intent(requireActivity(), EventDetailActivity::class.java)
|
|
||||||
intent.putExtra(Constants.EXTRA_EVENT, it)
|
|
||||||
startActivity(intent)
|
|
||||||
} else if (!it.link.isNullOrBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
Intent.ACTION_VIEW,
|
|
||||||
Uri.parse(it.link)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} as BaseBannerAdapter<Any>
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(800)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding.eventBannerSlider
|
|
||||||
.setIndicatorView(binding.indicatorEventBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.eventLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.eventBannerSlider.visibility = View.VISIBLE
|
|
||||||
binding.indicatorEventBanner.visibility = View.VISIBLE
|
|
||||||
binding.eventBannerSlider.refreshData(it)
|
|
||||||
} else {
|
|
||||||
binding.eventBannerSlider.visibility = View.GONE
|
|
||||||
binding.indicatorEventBanner.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCuration() {
|
|
||||||
curationAdapter = AudioContentMainContentCurationAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.VERTICAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.top = 30f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
curationAdapter.itemCount - 1 -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 30f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = curationAdapter
|
|
||||||
|
|
||||||
viewModel.curationListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
curationAdapter.addItems(it)
|
|
||||||
|
|
||||||
binding.rvCuration.visibility = if (curationAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentCreator() {
|
|
||||||
contentRankCreatorAdapter = ContentRankCreatorAdapter {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
binding.rvRankingSalesCount.visibility = View.GONE
|
|
||||||
viewModel.getPopularContentByCreator(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvRankingCreator.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvRankingCreator.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankCreatorAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvRankingCreator.adapter = contentRankCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.contentCreatorListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
contentRankCreatorAdapter.addItems(it)
|
|
||||||
if (contentRankCreatorAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentByCreator() {
|
|
||||||
popularContentByCreatorAdapter = PopularContentByCreatorAdapter(
|
|
||||||
itemWidth = ((screenWidth - 13.3f.dpToPx() * 3) / 2).toInt(),
|
|
||||||
onClickItem = { contentId ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, contentId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = { creatorId ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, creatorId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRankingSalesCount
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(requireContext(), 2)
|
|
||||||
recyclerView.addItemDecoration(
|
|
||||||
GridSpacingItemDecoration(
|
|
||||||
2,
|
|
||||||
13.3f.dpToPx().toInt(),
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.adapter = popularContentByCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.salesCountRankContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llNoItems.visibility = View.GONE
|
|
||||||
recyclerView.visibility = View.VISIBLE
|
|
||||||
popularContentByCreatorAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
recyclerView.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,23 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.asmr
|
|
||||||
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentApi
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
|
||||||
|
|
||||||
class AudioContentMainTabAsmrRepository(private val api: AudioContentApi) {
|
|
||||||
fun getContentMainAsmr(token: String) = api.getContentMainAsmr(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(
|
|
||||||
creatorId: Long,
|
|
||||||
token: String
|
|
||||||
) = api.getPopularAsmrContentByCreator(
|
|
||||||
creatorId,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,124 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.asmr
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventItem
|
|
||||||
|
|
||||||
class AudioContentMainTabAsmrViewModel(
|
|
||||||
private val repository: AudioContentMainTabAsmrRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _contentBannerLiveData = MutableLiveData<List<GetAudioContentBannerResponse>>()
|
|
||||||
val contentBannerLiveData: LiveData<List<GetAudioContentBannerResponse>>
|
|
||||||
get() = _contentBannerLiveData
|
|
||||||
|
|
||||||
private var _newContentListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val newContentListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _newContentListLiveData
|
|
||||||
|
|
||||||
private val _contentCreatorListLiveData = MutableLiveData<List<ContentCreatorResponse>>()
|
|
||||||
val contentCreatorListLiveData: LiveData<List<ContentCreatorResponse>>
|
|
||||||
get() = _contentCreatorListLiveData
|
|
||||||
|
|
||||||
private val _salesCountRankContentListLiveData =
|
|
||||||
MutableLiveData<List<GetAudioContentRankingItem>>()
|
|
||||||
val salesCountRankContentListLiveData: LiveData<List<GetAudioContentRankingItem>>
|
|
||||||
get() = _salesCountRankContentListLiveData
|
|
||||||
|
|
||||||
private val _eventLiveData = MutableLiveData<List<EventItem>>()
|
|
||||||
val eventLiveData: LiveData<List<EventItem>>
|
|
||||||
get() = _eventLiveData
|
|
||||||
|
|
||||||
private var _curationListLiveData = MutableLiveData<List<GetContentCurationResponse>>()
|
|
||||||
val curationListLiveData: LiveData<List<GetContentCurationResponse>>
|
|
||||||
get() = _curationListLiveData
|
|
||||||
|
|
||||||
fun fetchData() {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainAsmr(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val data = it.data
|
|
||||||
|
|
||||||
_contentBannerLiveData.value = data.contentBannerList
|
|
||||||
_newContentListLiveData.value = data.newAsmrContentList
|
|
||||||
_contentCreatorListLiveData.value = data.creatorList
|
|
||||||
_salesCountRankContentListLiveData.value =
|
|
||||||
data.salesCountRankContentList
|
|
||||||
_eventLiveData.value = data.eventBannerList.eventList
|
|
||||||
_curationListLiveData.value = data.curationList
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(creatorId: Long) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getPopularContentByCreator(
|
|
||||||
creatorId = creatorId,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_salesCountRankContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,26 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.asmr
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.GetEventResponse
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetContentMainTabAsmrResponse(
|
|
||||||
@SerializedName("contentBannerList")
|
|
||||||
val contentBannerList: List<GetAudioContentBannerResponse>,
|
|
||||||
@SerializedName("newAsmrContentList")
|
|
||||||
val newAsmrContentList: List<GetAudioContentMainItem>,
|
|
||||||
@SerializedName("creatorList")
|
|
||||||
val creatorList: List<ContentCreatorResponse>,
|
|
||||||
@SerializedName("salesCountRankContentList")
|
|
||||||
val salesCountRankContentList: List<GetAudioContentRankingItem>,
|
|
||||||
@SerializedName("eventBannerList")
|
|
||||||
val eventBannerList: GetEventResponse,
|
|
||||||
@SerializedName("curationList")
|
|
||||||
val curationList: List<GetContentCurationResponse>
|
|
||||||
)
|
|
||||||
@@ -1,666 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.content
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Intent
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.LinearLayout
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.zhpan.bannerview.BaseBannerAdapter
|
|
||||||
import com.zhpan.indicator.enums.IndicatorSlideMode
|
|
||||||
import com.zhpan.indicator.enums.IndicatorStyle
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentBannerType
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentMainContentAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.new_content.AudioContentMainNewContentThemeAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ranking.AudioContentMainRankingAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.AudioContentMainContentCurationAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.ContentRankCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.PopularContentByCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseFragment
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.databinding.FragmentAudioContentMainTabContentBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.live.event_banner.EventBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventDetailActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AudioContentMainTabContentFragment : BaseFragment<FragmentAudioContentMainTabContentBinding>(
|
|
||||||
FragmentAudioContentMainTabContentBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AudioContentMainTabContentViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var contentBannerAdapter: AudioContentMainBannerAdapter
|
|
||||||
private lateinit var newContentThemeAdapter: AudioContentMainNewContentThemeAdapter
|
|
||||||
private lateinit var newContentAdapter: AudioContentMainContentAdapter
|
|
||||||
private lateinit var contentRankingSortAdapter: AudioContentMainNewContentThemeAdapter
|
|
||||||
private lateinit var contentRankingAdapter: AudioContentMainRankingAdapter
|
|
||||||
private lateinit var contentRankCreatorAdapter: ContentRankCreatorAdapter
|
|
||||||
private lateinit var curationAdapter: AudioContentMainContentCurationAdapter
|
|
||||||
private lateinit var popularContentByCreatorAdapter: PopularContentByCreatorAdapter
|
|
||||||
private lateinit var contentTagAdapter: AudioContentMainTabContentTagAdapter
|
|
||||||
private lateinit var contentByTagAdapter: AudioContentNewAllAdapter
|
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
|
||||||
super.onViewCreated(view, savedInstanceState)
|
|
||||||
setupView()
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.fetchData()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(requireActivity(), layoutInflater)
|
|
||||||
|
|
||||||
setupContentBanner()
|
|
||||||
setupNewContentTheme()
|
|
||||||
setupNewContent()
|
|
||||||
setupContentRankingSortType()
|
|
||||||
setupContentRanking()
|
|
||||||
setupEventBanner()
|
|
||||||
setupPopularContentCreator()
|
|
||||||
setupPopularContentByCreator()
|
|
||||||
setupContentTag()
|
|
||||||
setupContentByTag()
|
|
||||||
setupCuration()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentBanner() {
|
|
||||||
val layoutParams = binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams as LinearLayout.LayoutParams
|
|
||||||
|
|
||||||
val pagerWidth = screenWidth.toDouble() - 26.7f.dpToPx()
|
|
||||||
val pagerHeight = (pagerWidth * 0.53).roundToInt()
|
|
||||||
layoutParams.width = pagerWidth.roundToInt()
|
|
||||||
layoutParams.height = pagerHeight
|
|
||||||
|
|
||||||
contentBannerAdapter = AudioContentMainBannerAdapter(
|
|
||||||
requireContext(),
|
|
||||||
pagerWidth.roundToInt(),
|
|
||||||
pagerHeight
|
|
||||||
) {
|
|
||||||
when (it.type) {
|
|
||||||
AudioContentBannerType.EVENT -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), EventDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_EVENT, it.eventItem!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.CREATOR -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it.creatorId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.SERIES -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it.seriesId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.LINK -> {
|
|
||||||
startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(it.link!!)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams = layoutParams
|
|
||||||
|
|
||||||
binding.rvBanner.apply {
|
|
||||||
adapter = contentBannerAdapter as BaseBannerAdapter<Any>
|
|
||||||
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(1000)
|
|
||||||
setInterval(4 * 1000)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.setIndicatorView(binding.indicatorBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.contentBannerLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (contentBannerAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.rvBanner.visibility = View.GONE
|
|
||||||
binding.indicatorBanner.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.rvBanner.visibility = View.VISIBLE
|
|
||||||
binding.indicatorBanner.visibility = View.VISIBLE
|
|
||||||
binding.rvBanner.refreshData(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContentTheme() {
|
|
||||||
newContentThemeAdapter = AudioContentMainNewContentThemeAdapter {
|
|
||||||
viewModel.getNewContentOfTheme(theme = it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentThemeAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.adapter = newContentThemeAdapter
|
|
||||||
|
|
||||||
viewModel.themeListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llNewContent.visibility = View.VISIBLE
|
|
||||||
newContentThemeAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
binding.ivNewContentAll.setOnClickListener {
|
|
||||||
startActivity(Intent(requireContext(), AudioContentNewAllActivity::class.java))
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter = AudioContentMainContentAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContent.adapter = newContentAdapter
|
|
||||||
|
|
||||||
viewModel.newContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentRankingSortType() {
|
|
||||||
contentRankingSortAdapter = AudioContentMainNewContentThemeAdapter {
|
|
||||||
viewModel.getContentRanking(sort = it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvContentRankingSort.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvContentRankingSort.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankingSortAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvContentRankingSort.adapter = contentRankingSortAdapter
|
|
||||||
|
|
||||||
viewModel.contentRankingSortListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llContentRanking.visibility = View.VISIBLE
|
|
||||||
contentRankingSortAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("SetTextI18n")
|
|
||||||
private fun setupContentRanking() {
|
|
||||||
contentRankingAdapter = AudioContentMainRankingAdapter(
|
|
||||||
width = (screenWidth * 0.66).toInt()
|
|
||||||
) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvContentRanking.layoutManager = GridLayoutManager(
|
|
||||||
context,
|
|
||||||
3,
|
|
||||||
GridLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvContentRanking.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
outRect.top = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.left = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.right = 13.3f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvContentRanking.adapter = contentRankingAdapter
|
|
||||||
|
|
||||||
viewModel.contentRankingLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llContentRanking.visibility = View.VISIBLE
|
|
||||||
contentRankingAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupEventBanner() {
|
|
||||||
val imageSliderLp = binding.eventBannerSlider.layoutParams
|
|
||||||
imageSliderLp.width = screenWidth
|
|
||||||
imageSliderLp.height = (screenWidth * 300) / 1000
|
|
||||||
binding.eventBannerSlider.layoutParams = imageSliderLp
|
|
||||||
|
|
||||||
binding.eventBannerSlider.apply {
|
|
||||||
adapter = EventBannerAdapter(requireContext()) {
|
|
||||||
if (it.detailImageUrl != null) {
|
|
||||||
val intent = Intent(requireActivity(), EventDetailActivity::class.java)
|
|
||||||
intent.putExtra(Constants.EXTRA_EVENT, it)
|
|
||||||
startActivity(intent)
|
|
||||||
} else if (!it.link.isNullOrBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
Intent.ACTION_VIEW,
|
|
||||||
Uri.parse(it.link)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} as BaseBannerAdapter<Any>
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(800)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding.eventBannerSlider
|
|
||||||
.setIndicatorView(binding.indicatorEventBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.eventLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.eventBannerSlider.visibility = View.VISIBLE
|
|
||||||
binding.indicatorEventBanner.visibility = View.VISIBLE
|
|
||||||
binding.eventBannerSlider.refreshData(it)
|
|
||||||
} else {
|
|
||||||
binding.eventBannerSlider.visibility = View.GONE
|
|
||||||
binding.indicatorEventBanner.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentCreator() {
|
|
||||||
contentRankCreatorAdapter = ContentRankCreatorAdapter {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
binding.rvRankingSalesCount.visibility = View.GONE
|
|
||||||
viewModel.getPopularContentByCreator(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvRankingCreator.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvRankingCreator.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankCreatorAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvRankingCreator.adapter = contentRankCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.contentRankCreatorListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
contentRankCreatorAdapter.addItems(it)
|
|
||||||
if (contentRankCreatorAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentByCreator() {
|
|
||||||
popularContentByCreatorAdapter = PopularContentByCreatorAdapter(
|
|
||||||
itemWidth = ((screenWidth - 13.3f.dpToPx() * 3) / 2).toInt(),
|
|
||||||
onClickItem = { contentId ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, contentId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = { creatorId ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, creatorId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRankingSalesCount
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(requireContext(), 2)
|
|
||||||
recyclerView.addItemDecoration(
|
|
||||||
GridSpacingItemDecoration(
|
|
||||||
2,
|
|
||||||
13.3f.dpToPx().toInt(),
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.adapter = popularContentByCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.salesCountRankContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llNoItems.visibility = View.GONE
|
|
||||||
recyclerView.visibility = View.VISIBLE
|
|
||||||
popularContentByCreatorAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
recyclerView.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentTag() {
|
|
||||||
val spanCount = 4
|
|
||||||
val spacing = 6f.dpToPx()
|
|
||||||
|
|
||||||
contentTagAdapter = AudioContentMainTabContentTagAdapter {
|
|
||||||
viewModel.getRecommendContentByTag(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRecommendContentTag
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(requireContext(), spanCount)
|
|
||||||
recyclerView.addItemDecoration(GridSpacingItemDecoration(spanCount, spacing.toInt(), false))
|
|
||||||
recyclerView.adapter = contentTagAdapter
|
|
||||||
|
|
||||||
viewModel.tagListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
contentTagAdapter.addItems(it)
|
|
||||||
if (
|
|
||||||
contentTagAdapter.itemCount <= 0 ||
|
|
||||||
!SharedPreferenceManager.isAdultContentVisible ||
|
|
||||||
!SharedPreferenceManager.isAuth
|
|
||||||
) {
|
|
||||||
binding.llRecommendContentByTag.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llRecommendContentByTag.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentByTag() {
|
|
||||||
val spanCount = 3
|
|
||||||
val horizontalSpacing = 13.3f.dpToPx().toInt()
|
|
||||||
val verticalSpacing = 26.7f.dpToPx().toInt()
|
|
||||||
val itemWidth = (screenWidth - horizontalSpacing * (spanCount + 1)) / spanCount
|
|
||||||
contentByTagAdapter = AudioContentNewAllAdapter(
|
|
||||||
itemWidth = itemWidth,
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRecommendContent
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(requireContext(), spanCount)
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
outRect.left = horizontalSpacing / 2
|
|
||||||
outRect.right = horizontalSpacing / 2
|
|
||||||
outRect.top = verticalSpacing / 2
|
|
||||||
outRect.bottom = verticalSpacing / 2
|
|
||||||
}
|
|
||||||
})
|
|
||||||
recyclerView.adapter = contentByTagAdapter
|
|
||||||
|
|
||||||
viewModel.tagCurationContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
contentByTagAdapter.clear()
|
|
||||||
contentByTagAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCuration() {
|
|
||||||
curationAdapter = AudioContentMainContentCurationAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.VERTICAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.top = 30f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
curationAdapter.itemCount - 1 -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 30f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = curationAdapter
|
|
||||||
|
|
||||||
viewModel.curationListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
curationAdapter.addItems(it)
|
|
||||||
|
|
||||||
binding.rvCuration.visibility = if (curationAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,49 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.content
|
|
||||||
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentApi
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
|
||||||
|
|
||||||
class AudioContentMainTabContentRepository(private val api: AudioContentApi) {
|
|
||||||
fun getContentMainContent(token: String) = api.getContentMainContent(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getNewContentOfTheme(theme: String, token: String) = api.getContentMainNewContentOfTheme(
|
|
||||||
theme = theme,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getContentRanking(
|
|
||||||
sortType: String = "매출",
|
|
||||||
token: String
|
|
||||||
) = api.getDailyContentRanking(
|
|
||||||
sortType = sortType,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(
|
|
||||||
creatorId: Long,
|
|
||||||
token: String
|
|
||||||
) = api.getContentMainContentPopularContentByCreator(
|
|
||||||
creatorId,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getRecommendedContentByTag(
|
|
||||||
tag: String,
|
|
||||||
token: String
|
|
||||||
) = api.getRecommendedContentByTag(
|
|
||||||
tag = tag,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,77 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.content
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemContentMainTabContentTagBinding
|
|
||||||
|
|
||||||
class AudioContentMainTabContentTagAdapter(
|
|
||||||
private val onClick: (String) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainTabContentTagAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
private val tagList = mutableListOf<String>()
|
|
||||||
|
|
||||||
private var selectedTag = ""
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemContentMainTabContentTagBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun bind(tag: String) {
|
|
||||||
if (tag == selectedTag) {
|
|
||||||
binding.tvTag.setBackgroundResource(
|
|
||||||
R.drawable.bg_round_corner_2_6_transparent_3bb9f1
|
|
||||||
)
|
|
||||||
binding.tvTag.setTextColor(
|
|
||||||
ContextCompat.getColor(context, R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
binding.tvTag.setBackgroundResource(
|
|
||||||
R.drawable.bg_round_corner_2_6_transparent_777777
|
|
||||||
)
|
|
||||||
binding.tvTag.setTextColor(
|
|
||||||
ContextCompat.getColor(context, R.color.color_777777)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvTag.text = tag
|
|
||||||
binding.tvTag.setOnClickListener {
|
|
||||||
selectedTag = tag
|
|
||||||
onClick(tag)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemContentMainTabContentTagBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun getItemCount() = tagList.size
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(tagList[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(tagList: List<String>) {
|
|
||||||
this.tagList.clear()
|
|
||||||
this.tagList.addAll(tagList)
|
|
||||||
|
|
||||||
if (tagList.isNotEmpty()) {
|
|
||||||
selectedTag = tagList[0]
|
|
||||||
}
|
|
||||||
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,259 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.content
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventItem
|
|
||||||
|
|
||||||
class AudioContentMainTabContentViewModel(
|
|
||||||
private val repository: AudioContentMainTabContentRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _contentBannerLiveData = MutableLiveData<List<GetAudioContentBannerResponse>>()
|
|
||||||
val contentBannerLiveData: LiveData<List<GetAudioContentBannerResponse>>
|
|
||||||
get() = _contentBannerLiveData
|
|
||||||
|
|
||||||
private var _newContentListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val newContentListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _newContentListLiveData
|
|
||||||
|
|
||||||
private var _themeListLiveData = MutableLiveData<List<String>>()
|
|
||||||
val themeListLiveData: LiveData<List<String>>
|
|
||||||
get() = _themeListLiveData
|
|
||||||
|
|
||||||
private var _contentRankingSortListLiveData = MutableLiveData<List<String>>()
|
|
||||||
val contentRankingSortListLiveData: LiveData<List<String>>
|
|
||||||
get() = _contentRankingSortListLiveData
|
|
||||||
|
|
||||||
private var _contentRankingLiveData = MutableLiveData<List<GetAudioContentRankingItem>>()
|
|
||||||
val contentRankingLiveData: LiveData<List<GetAudioContentRankingItem>>
|
|
||||||
get() = _contentRankingLiveData
|
|
||||||
|
|
||||||
private val _eventLiveData = MutableLiveData<List<EventItem>>()
|
|
||||||
val eventLiveData: LiveData<List<EventItem>>
|
|
||||||
get() = _eventLiveData
|
|
||||||
|
|
||||||
private var _curationListLiveData = MutableLiveData<List<GetContentCurationResponse>>()
|
|
||||||
val curationListLiveData: LiveData<List<GetContentCurationResponse>>
|
|
||||||
get() = _curationListLiveData
|
|
||||||
|
|
||||||
private val _contentRankCreatorListLiveData = MutableLiveData<List<ContentCreatorResponse>>()
|
|
||||||
val contentRankCreatorListLiveData: LiveData<List<ContentCreatorResponse>>
|
|
||||||
get() = _contentRankCreatorListLiveData
|
|
||||||
|
|
||||||
private val _salesCountRankContentListLiveData =
|
|
||||||
MutableLiveData<List<GetAudioContentRankingItem>>()
|
|
||||||
val salesCountRankContentListLiveData: LiveData<List<GetAudioContentRankingItem>>
|
|
||||||
get() = _salesCountRankContentListLiveData
|
|
||||||
|
|
||||||
private val _tagListLiveData = MutableLiveData<List<String>>()
|
|
||||||
val tagListLiveData: LiveData<List<String>>
|
|
||||||
get() = _tagListLiveData
|
|
||||||
|
|
||||||
private val _tagCurationContentListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val tagCurationContentListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _tagCurationContentListLiveData
|
|
||||||
|
|
||||||
fun fetchData() {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainContent(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val data = it.data
|
|
||||||
|
|
||||||
_contentBannerLiveData.value = data.bannerList
|
|
||||||
|
|
||||||
val themeList = listOf("전체").union(data.contentThemeList).toList()
|
|
||||||
_themeListLiveData.value = themeList
|
|
||||||
_newContentListLiveData.value = data.newContentList
|
|
||||||
|
|
||||||
_contentRankingSortListLiveData.value = data.rankSortTypeList
|
|
||||||
_contentRankingLiveData.value = data.rankContentList
|
|
||||||
|
|
||||||
_eventLiveData.value = data.eventBannerList.eventList
|
|
||||||
_contentRankCreatorListLiveData.value = data.contentRankCreatorList
|
|
||||||
_salesCountRankContentListLiveData.value =
|
|
||||||
data.salesCountRankContentList
|
|
||||||
_curationListLiveData.value = data.curationList
|
|
||||||
|
|
||||||
_tagListLiveData.value = data.tagList
|
|
||||||
_tagCurationContentListLiveData.value = data.tagCurationContentList
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getNewContentOfTheme(theme: String) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getNewContentOfTheme(
|
|
||||||
theme = if (theme == "전체") {
|
|
||||||
""
|
|
||||||
} else {
|
|
||||||
theme
|
|
||||||
},
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_newContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
_isLoading.value = false
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getContentRanking(sort: String = "매출") {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentRanking(
|
|
||||||
sortType = sort,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_contentRankingLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
_isLoading.value = false
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(creatorId: Long) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getPopularContentByCreator(
|
|
||||||
creatorId = creatorId,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_salesCountRankContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getRecommendContentByTag(tag: String) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getRecommendedContentByTag(
|
|
||||||
tag = tag,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_tagCurationContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
_isLoading.value = false
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,25 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.content
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.GetEventResponse
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetContentMainTabContentResponse(
|
|
||||||
@SerializedName("bannerList") val bannerList: List<GetAudioContentBannerResponse>,
|
|
||||||
@SerializedName("contentThemeList") val contentThemeList: List<String>,
|
|
||||||
@SerializedName("newContentList") val newContentList: List<GetAudioContentMainItem>,
|
|
||||||
@SerializedName("rankSortTypeList") val rankSortTypeList: List<String>,
|
|
||||||
@SerializedName("rankContentList") val rankContentList: List<GetAudioContentRankingItem>,
|
|
||||||
@SerializedName("contentRankCreatorList") val contentRankCreatorList: List<ContentCreatorResponse>,
|
|
||||||
@SerializedName("salesCountRankContentList") val salesCountRankContentList: List<GetAudioContentRankingItem>,
|
|
||||||
@SerializedName("eventBannerList") val eventBannerList: GetEventResponse,
|
|
||||||
@SerializedName("tagList") val tagList: List<String>,
|
|
||||||
@SerializedName("tagCurationContentList") val tagCurationContentList: List<GetAudioContentMainItem>,
|
|
||||||
@SerializedName("curationList") val curationList: List<GetContentCurationResponse>
|
|
||||||
)
|
|
||||||
@@ -1,591 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.free
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.LinearLayout
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.zhpan.bannerview.BaseBannerAdapter
|
|
||||||
import com.zhpan.indicator.enums.IndicatorSlideMode
|
|
||||||
import com.zhpan.indicator.enums.IndicatorStyle
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentBannerType
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentMainContentAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.new_content.AudioContentMainNewContentThemeAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.AudioContentMainContentCurationAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.ContentRankCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.PopularContentByCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.free.introduce_creator.IntroduceCreatorActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.new_series.AudioContentMainNewSeriesAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseFragment
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.FragmentAudioContentMainTabFreeBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventDetailActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AudioContentMainTabFreeFragment : BaseFragment<FragmentAudioContentMainTabFreeBinding>(
|
|
||||||
FragmentAudioContentMainTabFreeBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AudioContentMainTabFreeViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var contentBannerAdapter: AudioContentMainBannerAdapter
|
|
||||||
private lateinit var introduceCreatorAdapter: AudioContentMainContentAdapter
|
|
||||||
private lateinit var recommendSeriesAdapter: AudioContentMainNewSeriesAdapter
|
|
||||||
private lateinit var newContentThemeAdapter: AudioContentMainNewContentThemeAdapter
|
|
||||||
private lateinit var newContentAdapter: AudioContentMainContentAdapter
|
|
||||||
private lateinit var curationAdapter: AudioContentMainContentCurationAdapter
|
|
||||||
private lateinit var contentRankCreatorAdapter: ContentRankCreatorAdapter
|
|
||||||
private lateinit var popularContentByCreatorAdapter: PopularContentByCreatorAdapter
|
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
|
||||||
super.onViewCreated(view, savedInstanceState)
|
|
||||||
setupView()
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.fetchData()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(requireActivity(), layoutInflater)
|
|
||||||
|
|
||||||
setupContentBanner()
|
|
||||||
setupIntroduceCreator()
|
|
||||||
setupRecommendSeries()
|
|
||||||
setupNewContentTheme()
|
|
||||||
setupNewContent()
|
|
||||||
setupPopularContentCreator()
|
|
||||||
setupPopularContentByCreator()
|
|
||||||
setupCuration()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentBanner() {
|
|
||||||
val layoutParams = binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams as LinearLayout.LayoutParams
|
|
||||||
|
|
||||||
val pagerWidth = screenWidth.toDouble() - 26.7f.dpToPx()
|
|
||||||
val pagerHeight = (pagerWidth * 0.53).roundToInt()
|
|
||||||
layoutParams.width = pagerWidth.roundToInt()
|
|
||||||
layoutParams.height = pagerHeight
|
|
||||||
|
|
||||||
contentBannerAdapter = AudioContentMainBannerAdapter(
|
|
||||||
requireContext(),
|
|
||||||
pagerWidth.roundToInt(),
|
|
||||||
pagerHeight
|
|
||||||
) {
|
|
||||||
when (it.type) {
|
|
||||||
AudioContentBannerType.EVENT -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), EventDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_EVENT, it.eventItem!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.CREATOR -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it.creatorId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.SERIES -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it.seriesId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.LINK -> {
|
|
||||||
startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(it.link!!)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams = layoutParams
|
|
||||||
|
|
||||||
binding.rvBanner.apply {
|
|
||||||
adapter = contentBannerAdapter as BaseBannerAdapter<Any>
|
|
||||||
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(1000)
|
|
||||||
setInterval(4 * 1000)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.setIndicatorView(binding.indicatorBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.contentBannerLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (contentBannerAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.rvBanner.visibility = View.GONE
|
|
||||||
binding.indicatorBanner.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.rvBanner.visibility = View.VISIBLE
|
|
||||||
binding.indicatorBanner.visibility = View.VISIBLE
|
|
||||||
binding.rvBanner.refreshData(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupIntroduceCreator() {
|
|
||||||
binding.ivIntroduceCreatorAll.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), IntroduceCreatorActivity::class.java)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
introduceCreatorAdapter = AudioContentMainContentAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvIntroduceCreator
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
introduceCreatorAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = introduceCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.introduceCreatorLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.items.isNotEmpty()) {
|
|
||||||
binding.llIntroduceCreator.visibility = View.VISIBLE
|
|
||||||
binding.tvIntroduceCreator.text = it.title
|
|
||||||
introduceCreatorAdapter.addItems(it.items)
|
|
||||||
} else {
|
|
||||||
binding.llIntroduceCreator.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRecommendSeries() {
|
|
||||||
recommendSeriesAdapter = AudioContentMainNewSeriesAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRecommendSeries
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
recommendSeriesAdapter.itemCount - 1 -> {
|
|
||||||
outRect.right = 0
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = recommendSeriesAdapter
|
|
||||||
|
|
||||||
viewModel.recommendSeriesListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
recommendSeriesAdapter.addItems(it)
|
|
||||||
binding.llRecommendSeries.visibility = if (it.isNotEmpty()) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContentTheme() {
|
|
||||||
newContentThemeAdapter = AudioContentMainNewContentThemeAdapter {
|
|
||||||
viewModel.getNewFreeContentOfTheme(theme = it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentThemeAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContentTheme.adapter = newContentThemeAdapter
|
|
||||||
|
|
||||||
viewModel.themeListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llNewContent.visibility = View.VISIBLE
|
|
||||||
newContentThemeAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
binding.ivNewContentAll.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireContext(),
|
|
||||||
AudioContentNewAllActivity::class.java
|
|
||||||
).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_FREE, true)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter = AudioContentMainContentAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContent.adapter = newContentAdapter
|
|
||||||
|
|
||||||
viewModel.newContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentCreator() {
|
|
||||||
contentRankCreatorAdapter = ContentRankCreatorAdapter {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
binding.rvRankingPlayCount.visibility = View.GONE
|
|
||||||
viewModel.getPopularContentByCreator(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvRankingCreator.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvRankingCreator.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankCreatorAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvRankingCreator.adapter = contentRankCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.contentCreatorListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
contentRankCreatorAdapter.addItems(it)
|
|
||||||
if (contentRankCreatorAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentByCreator() {
|
|
||||||
popularContentByCreatorAdapter = PopularContentByCreatorAdapter(
|
|
||||||
itemWidth = ((screenWidth - 13.3f.dpToPx() * 3) / 2).toInt(),
|
|
||||||
onClickItem = { contentId ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, contentId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = { creatorId ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, creatorId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRankingPlayCount
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(requireContext(), 2)
|
|
||||||
recyclerView.addItemDecoration(
|
|
||||||
GridSpacingItemDecoration(
|
|
||||||
2,
|
|
||||||
13.3f.dpToPx().toInt(),
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.adapter = popularContentByCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.playCountRankContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llNoItems.visibility = View.GONE
|
|
||||||
recyclerView.visibility = View.VISIBLE
|
|
||||||
popularContentByCreatorAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
recyclerView.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCuration() {
|
|
||||||
curationAdapter = AudioContentMainContentCurationAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.VERTICAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.top = 30f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
curationAdapter.itemCount - 1 -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 30f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = curationAdapter
|
|
||||||
|
|
||||||
viewModel.curationListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
curationAdapter.addItems(it)
|
|
||||||
|
|
||||||
binding.rvCuration.visibility = if (curationAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,45 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.free
|
|
||||||
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentApi
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
|
||||||
|
|
||||||
class AudioContentMainTabFreeRepository(private val api: AudioContentApi) {
|
|
||||||
fun getContentMainFree(token: String) = api.getContentMainFree(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getIntroduceCreatorList(page: Int, size: Int, token: String) = api.getIntroduceCreatorList(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
page = page - 1,
|
|
||||||
size = size,
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getNewContentOfTheme(
|
|
||||||
theme: String,
|
|
||||||
page: Int = 1,
|
|
||||||
size: Int = 10,
|
|
||||||
token: String
|
|
||||||
) = api.getNewFreeContentOfTheme(
|
|
||||||
theme = theme,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
page = page - 1,
|
|
||||||
size = size,
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(
|
|
||||||
creatorId: Long,
|
|
||||||
token: String
|
|
||||||
) = api.getPopularFreeContentByCreator(
|
|
||||||
creatorId,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,181 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.free
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
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.main.v2.series.GetRecommendSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class AudioContentMainTabFreeViewModel(
|
|
||||||
private val repository: AudioContentMainTabFreeRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _contentBannerLiveData = MutableLiveData<List<GetAudioContentBannerResponse>>()
|
|
||||||
val contentBannerLiveData: LiveData<List<GetAudioContentBannerResponse>>
|
|
||||||
get() = _contentBannerLiveData
|
|
||||||
|
|
||||||
private var _introduceCreatorLiveData = MutableLiveData<GetContentCurationResponse>()
|
|
||||||
val introduceCreatorLiveData: LiveData<GetContentCurationResponse>
|
|
||||||
get() = _introduceCreatorLiveData
|
|
||||||
|
|
||||||
private var _recommendSeriesListLiveData =
|
|
||||||
MutableLiveData<List<GetRecommendSeriesListResponse>>()
|
|
||||||
val recommendSeriesListLiveData: LiveData<List<GetRecommendSeriesListResponse>>
|
|
||||||
get() = _recommendSeriesListLiveData
|
|
||||||
|
|
||||||
private var _newContentListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val newContentListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _newContentListLiveData
|
|
||||||
|
|
||||||
private var _themeListLiveData = MutableLiveData<List<String>>()
|
|
||||||
val themeListLiveData: LiveData<List<String>>
|
|
||||||
get() = _themeListLiveData
|
|
||||||
|
|
||||||
private val _contentCreatorListLiveData = MutableLiveData<List<ContentCreatorResponse>>()
|
|
||||||
val contentCreatorListLiveData: LiveData<List<ContentCreatorResponse>>
|
|
||||||
get() = _contentCreatorListLiveData
|
|
||||||
|
|
||||||
private val _playCountRankContentListLiveData =
|
|
||||||
MutableLiveData<List<GetAudioContentRankingItem>>()
|
|
||||||
val playCountRankContentListLiveData: LiveData<List<GetAudioContentRankingItem>>
|
|
||||||
get() = _playCountRankContentListLiveData
|
|
||||||
|
|
||||||
private var _curationListLiveData = MutableLiveData<List<GetContentCurationResponse>>()
|
|
||||||
val curationListLiveData: LiveData<List<GetContentCurationResponse>>
|
|
||||||
get() = _curationListLiveData
|
|
||||||
|
|
||||||
fun fetchData() {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainFree(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val data = it.data
|
|
||||||
|
|
||||||
_contentBannerLiveData.value = data.contentBannerList
|
|
||||||
|
|
||||||
if (data.introduceCreator != null) {
|
|
||||||
_introduceCreatorLiveData.value = data.introduceCreator!!
|
|
||||||
}
|
|
||||||
|
|
||||||
_recommendSeriesListLiveData.value = data.recommendSeriesList
|
|
||||||
_newContentListLiveData.value = data.newFreeContentList
|
|
||||||
val themeList = listOf("전체").union(data.themeList).toList()
|
|
||||||
_themeListLiveData.value = themeList
|
|
||||||
|
|
||||||
_contentCreatorListLiveData.value = data.creatorList
|
|
||||||
_playCountRankContentListLiveData.value =
|
|
||||||
data.playCountRankContentList
|
|
||||||
|
|
||||||
_curationListLiveData.value = data.curationList
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getNewFreeContentOfTheme(theme: String) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getNewContentOfTheme(
|
|
||||||
theme = if (theme == "전체") {
|
|
||||||
""
|
|
||||||
} else {
|
|
||||||
theme
|
|
||||||
},
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_newContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
_isLoading.value = false
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(creatorId: Long) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getPopularContentByCreator(
|
|
||||||
creatorId = creatorId,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_playCountRankContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,30 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.free
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
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.main.v2.series.GetRecommendSeriesListResponse
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetContentMainTabLiveFreeResponse(
|
|
||||||
@SerializedName("contentBannerList")
|
|
||||||
val contentBannerList: List<GetAudioContentBannerResponse>,
|
|
||||||
@SerializedName("introduceCreator")
|
|
||||||
val introduceCreator: GetContentCurationResponse?,
|
|
||||||
@SerializedName("recommendSeriesList")
|
|
||||||
val recommendSeriesList: List<GetRecommendSeriesListResponse>,
|
|
||||||
@SerializedName("themeList")
|
|
||||||
val themeList: List<String>,
|
|
||||||
@SerializedName("newFreeContentList")
|
|
||||||
val newFreeContentList: List<GetAudioContentMainItem>,
|
|
||||||
@SerializedName("creatorList")
|
|
||||||
val creatorList: List<ContentCreatorResponse>,
|
|
||||||
@SerializedName("playCountRankContentList")
|
|
||||||
val playCountRankContentList: List<GetAudioContentRankingItem>,
|
|
||||||
@SerializedName("curationList")
|
|
||||||
val curationList: List<GetContentCurationResponse>
|
|
||||||
)
|
|
||||||
@@ -1,104 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.free.introduce_creator
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseActivity
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ActivityIntroduceCreatorBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class IntroduceCreatorActivity : BaseActivity<ActivityIntroduceCreatorBinding>(
|
|
||||||
ActivityIntroduceCreatorBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: IntroduceCreatorViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var adapter: AudioContentNewAllAdapter
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
|
|
||||||
bindData()
|
|
||||||
viewModel.getIntroduceCreatorList()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(this, layoutInflater)
|
|
||||||
binding.toolbar.tvBack.text = "크리에이터 소개"
|
|
||||||
binding.toolbar.tvBack.setOnClickListener { finish() }
|
|
||||||
|
|
||||||
val spanCount = 3
|
|
||||||
val spacing = 13.3f.dpToPx().roundToInt()
|
|
||||||
adapter = AudioContentNewAllAdapter(
|
|
||||||
itemWidth = (screenWidth - (spacing * (spanCount + 1))) / 3,
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvContent.layoutManager = GridLayoutManager(this, spanCount)
|
|
||||||
binding.rvContent.addItemDecoration(GridSpacingItemDecoration(spanCount, spacing, true))
|
|
||||||
|
|
||||||
binding.rvContent.addOnScrollListener(object : RecyclerView.OnScrollListener() {
|
|
||||||
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
|
|
||||||
super.onScrolled(recyclerView, dx, dy)
|
|
||||||
|
|
||||||
val lastVisibleItemPosition = (recyclerView.layoutManager as LinearLayoutManager?)!!
|
|
||||||
.findLastCompletelyVisibleItemPosition()
|
|
||||||
val itemTotalCount = recyclerView.adapter!!.itemCount - 1
|
|
||||||
|
|
||||||
// 스크롤이 끝에 도달했는지 확인
|
|
||||||
if (!recyclerView.canScrollVertically(1) &&
|
|
||||||
lastVisibleItemPosition == itemTotalCount
|
|
||||||
) {
|
|
||||||
viewModel.getIntroduceCreatorList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvContent.adapter = adapter
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.isLoading.observe(this) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.toastLiveData.observe(this) {
|
|
||||||
it?.let { Toast.makeText(applicationContext, it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.introduceCreatorListLiveData.observe(this) {
|
|
||||||
adapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,74 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.free.introduce_creator
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.free.AudioContentMainTabFreeRepository
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class IntroduceCreatorViewModel(
|
|
||||||
private val repository: AudioContentMainTabFreeRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _introduceCreatorListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val introduceCreatorListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _introduceCreatorListLiveData
|
|
||||||
|
|
||||||
private var isLast = false
|
|
||||||
private var page = 1
|
|
||||||
private val size = 10
|
|
||||||
|
|
||||||
fun getIntroduceCreatorList() {
|
|
||||||
if (!_isLoading.value!! && !isLast) {
|
|
||||||
_isLoading.value = true
|
|
||||||
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getIntroduceCreatorList(
|
|
||||||
page = page,
|
|
||||||
size = size,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
if (it.data.isNotEmpty()) {
|
|
||||||
page += 1
|
|
||||||
_introduceCreatorListLiveData.postValue(it.data!!)
|
|
||||||
} else {
|
|
||||||
isLast = true
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,761 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.home
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.content.SharedPreferences
|
|
||||||
import android.graphics.Color
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.text.SpannableString
|
|
||||||
import android.text.Spanned
|
|
||||||
import android.text.style.ForegroundColorSpan
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.LinearLayout
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.zhpan.bannerview.BaseBannerAdapter
|
|
||||||
import com.zhpan.indicator.enums.IndicatorSlideMode
|
|
||||||
import com.zhpan.indicator.enums.IndicatorStyle
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentRankingAllActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentBannerType
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.new_content.AudioContentMainNewContentThemeAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ranking.AudioContentMainRankingAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.AudioContentMainActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.AudioContentMainTab
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.ContentRankCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.PopularContentByCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.upload.AudioContentUploadActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseFragment
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.databinding.FragmentAudioContentMainTabHomeBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.ExplorerSectionAdapter
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.series.UserProfileSeriesListAdapter
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.live.event_banner.EventBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.main.MainActivity
|
|
||||||
import kr.co.vividnext.sodalive.mypage.can.charge.CanChargeActivity
|
|
||||||
import kr.co.vividnext.sodalive.search.SearchActivity
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.settings.notice.NoticeDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.settings.notification.MemberRole
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
@UnstableApi
|
|
||||||
class AudioContentMainTabHomeFragment : BaseFragment<FragmentAudioContentMainTabHomeBinding>(
|
|
||||||
FragmentAudioContentMainTabHomeBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AudioContentMainTabHomeViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var rankCreatorAdapter: ExplorerSectionAdapter
|
|
||||||
private lateinit var rankSeriesAdapter: UserProfileSeriesListAdapter
|
|
||||||
private lateinit var contentBannerAdapter: AudioContentMainBannerAdapter
|
|
||||||
private lateinit var rankContentAdapter: AudioContentMainRankingAdapter
|
|
||||||
private lateinit var rankContentSortAdapter: AudioContentMainNewContentThemeAdapter
|
|
||||||
private lateinit var contentRankCreatorAdapter: ContentRankCreatorAdapter
|
|
||||||
private lateinit var popularContentByCreatorAdapter: PopularContentByCreatorAdapter
|
|
||||||
|
|
||||||
private val preferenceChangeListener =
|
|
||||||
SharedPreferences.OnSharedPreferenceChangeListener { sharedPreferences, key ->
|
|
||||||
// 특정 키에 대한 값이 변경될 때 UI 업데이트
|
|
||||||
if (key == Constants.PREF_USER_ROLE) {
|
|
||||||
if (
|
|
||||||
sharedPreferences.getString(
|
|
||||||
key,
|
|
||||||
MemberRole.USER.name
|
|
||||||
) == MemberRole.CREATOR.name
|
|
||||||
) {
|
|
||||||
binding.llUploadContent.visibility = View.VISIBLE
|
|
||||||
binding.llUploadContent.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireActivity(),
|
|
||||||
AudioContentUploadActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
binding.llUploadContent.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
|
||||||
super.onViewCreated(view, savedInstanceState)
|
|
||||||
SharedPreferenceManager.registerOnSharedPreferenceChangeListener(preferenceChangeListener)
|
|
||||||
setupView()
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.fetchData()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onDestroyView() {
|
|
||||||
SharedPreferenceManager.unregisterOnSharedPreferenceChangeListener(preferenceChangeListener)
|
|
||||||
super.onDestroyView()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(requireActivity(), layoutInflater)
|
|
||||||
|
|
||||||
if (SharedPreferenceManager.role == MemberRole.CREATOR.name) {
|
|
||||||
binding.llUploadContent.visibility = View.VISIBLE
|
|
||||||
binding.llUploadContent.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireActivity(),
|
|
||||||
AudioContentUploadActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
binding.llUploadContent.visibility = View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
binding.ivCharge.visibility = View.VISIBLE
|
|
||||||
binding.ivCharge.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireContext(),
|
|
||||||
CanChargeActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
binding.ivCharge.visibility = View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
binding.flSearch.visibility = View.VISIBLE
|
|
||||||
binding.flSearch.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireContext(),
|
|
||||||
SearchActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
binding.flSearch.visibility = View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
setupNotice()
|
|
||||||
setupContentBanner()
|
|
||||||
setupCategory()
|
|
||||||
setupRankCreator()
|
|
||||||
setupRankSeries()
|
|
||||||
setupRankContentSortType()
|
|
||||||
setupRankContent()
|
|
||||||
setupEventBanner()
|
|
||||||
setupPopularContentCreator()
|
|
||||||
setupPopularContentByCreator()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNotice() {
|
|
||||||
viewModel.noticeLiveData.observe(viewLifecycleOwner) { notice ->
|
|
||||||
binding.tvNoticeTitle.text = notice.title
|
|
||||||
binding.tvDetail.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), NoticeDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_NOTICE, notice)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentBanner() {
|
|
||||||
val layoutParams = binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams as LinearLayout.LayoutParams
|
|
||||||
|
|
||||||
val pagerWidth = screenWidth.toDouble() - 26.7f.dpToPx()
|
|
||||||
val pagerHeight = (pagerWidth * 0.53).roundToInt()
|
|
||||||
layoutParams.width = pagerWidth.roundToInt()
|
|
||||||
layoutParams.height = pagerHeight
|
|
||||||
|
|
||||||
contentBannerAdapter = AudioContentMainBannerAdapter(
|
|
||||||
requireContext(),
|
|
||||||
pagerWidth.roundToInt(),
|
|
||||||
pagerHeight
|
|
||||||
) {
|
|
||||||
when (it.type) {
|
|
||||||
AudioContentBannerType.EVENT -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), EventDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_EVENT, it.eventItem!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.CREATOR -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it.creatorId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.SERIES -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it.seriesId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.LINK -> {
|
|
||||||
startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(it.link!!)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams = layoutParams
|
|
||||||
|
|
||||||
binding.rvBanner.apply {
|
|
||||||
adapter = contentBannerAdapter as BaseBannerAdapter<Any>
|
|
||||||
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(1000)
|
|
||||||
setInterval(4 * 1000)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.setIndicatorView(binding.indicatorBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.contentBannerLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (
|
|
||||||
SharedPreferenceManager.token.isBlank() ||
|
|
||||||
(contentBannerAdapter.itemCount <= 0 && it.isEmpty())
|
|
||||||
) {
|
|
||||||
binding.rvBanner.visibility = View.GONE
|
|
||||||
binding.indicatorBanner.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.rvBanner.visibility = View.VISIBLE
|
|
||||||
binding.indicatorBanner.visibility = View.VISIBLE
|
|
||||||
binding.rvBanner.refreshData(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCategory() {
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
binding.llCategoryContainer.visibility = View.VISIBLE
|
|
||||||
} else {
|
|
||||||
binding.llCategoryContainer.visibility = View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rlCategoryAudioBook.setOnClickListener {
|
|
||||||
showToast("준비중 입니다.")
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rlCategoryAudioToon.setOnClickListener {
|
|
||||||
showToast("준비중 입니다.")
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rlCategorySeries.setOnClickListener {
|
|
||||||
startAudioContentMainActivity(AudioContentMainTab.SERIES)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rlCategoryContent.setOnClickListener {
|
|
||||||
startAudioContentMainActivity(AudioContentMainTab.CONTENT)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rlCategoryAlarm.setOnClickListener {
|
|
||||||
startAudioContentMainActivity(AudioContentMainTab.ALARM)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rlCategoryAsmr.setOnClickListener {
|
|
||||||
startAudioContentMainActivity(AudioContentMainTab.ASMR)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rlCategoryReplay.setOnClickListener {
|
|
||||||
startAudioContentMainActivity(AudioContentMainTab.REPLAY)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rlCategoryFree.setOnClickListener {
|
|
||||||
startAudioContentMainActivity(AudioContentMainTab.FREE)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun startAudioContentMainActivity(tab: AudioContentMainTab) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentMainActivity::class.java).apply {
|
|
||||||
putExtra(
|
|
||||||
Constants.EXTRA_START_TAB_POSITION,
|
|
||||||
tab.ordinal
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRankCreator() {
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
binding.llCreatorRankDate.visibility = View.VISIBLE
|
|
||||||
|
|
||||||
val lp = binding.tvCreatorRankTitle.layoutParams as LinearLayout.LayoutParams
|
|
||||||
lp.topMargin = 30f.dpToPx().toInt()
|
|
||||||
binding.tvCreatorRankTitle.layoutParams = lp
|
|
||||||
} else {
|
|
||||||
binding.llCreatorRankDate.visibility = View.GONE
|
|
||||||
|
|
||||||
val lp = binding.tvCreatorRankTitle.layoutParams as LinearLayout.LayoutParams
|
|
||||||
lp.topMargin = 0
|
|
||||||
binding.tvCreatorRankTitle.layoutParams = lp
|
|
||||||
}
|
|
||||||
|
|
||||||
rankCreatorAdapter = ExplorerSectionAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
(requireActivity() as MainActivity).showLoginActivity()
|
|
||||||
}
|
|
||||||
},
|
|
||||||
isVisibleRanking = true
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCreatorRank.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCreatorRank.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
rankCreatorAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCreatorRank.adapter = rankCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.rankCreatorLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.tvDesc.text = it.desc
|
|
||||||
binding.tvCreatorRankTitle.text = if (
|
|
||||||
!it.coloredTitle.isNullOrBlank() &&
|
|
||||||
!it.color.isNullOrBlank()
|
|
||||||
) {
|
|
||||||
val spStr = SpannableString(it.title)
|
|
||||||
|
|
||||||
try {
|
|
||||||
spStr.setSpan(
|
|
||||||
ForegroundColorSpan(
|
|
||||||
Color.parseColor("#${it.color}")
|
|
||||||
),
|
|
||||||
it.title.indexOf(it.coloredTitle),
|
|
||||||
it.title.indexOf(it.coloredTitle) + it.coloredTitle.length,
|
|
||||||
Spanned.SPAN_EXCLUSIVE_EXCLUSIVE
|
|
||||||
)
|
|
||||||
|
|
||||||
spStr
|
|
||||||
} catch (e: IllegalArgumentException) {
|
|
||||||
it.title
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
it.title
|
|
||||||
}
|
|
||||||
|
|
||||||
rankCreatorAdapter.addItems(it.creators)
|
|
||||||
if (rankCreatorAdapter.itemCount <= 0 && it.creators.isEmpty()) {
|
|
||||||
binding.llCreatorRank.visibility = View.GONE
|
|
||||||
binding.rvCreatorRank.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llCreatorRank.visibility = View.VISIBLE
|
|
||||||
binding.rvCreatorRank.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRankSeries() {
|
|
||||||
rankSeriesAdapter = UserProfileSeriesListAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
(requireActivity() as MainActivity).showLoginActivity()
|
|
||||||
}
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
(requireActivity() as MainActivity).showLoginActivity()
|
|
||||||
}
|
|
||||||
},
|
|
||||||
isVisibleCreator = true
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRankSeries
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
rankSeriesAdapter.itemCount - 1 -> {
|
|
||||||
outRect.right = 0
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = rankSeriesAdapter
|
|
||||||
|
|
||||||
viewModel.rankSeriesLiveData.observe(viewLifecycleOwner) {
|
|
||||||
rankSeriesAdapter.addItems(it)
|
|
||||||
binding.llRankSeries.visibility = if (
|
|
||||||
SharedPreferenceManager.token.isBlank() ||
|
|
||||||
rankSeriesAdapter.itemCount <= 0 && it.isEmpty()
|
|
||||||
) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRankContentSortType() {
|
|
||||||
rankContentSortAdapter = AudioContentMainNewContentThemeAdapter {
|
|
||||||
viewModel.getContentRanking(sort = it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvRankContentSort.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvRankContentSort.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
rankContentSortAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvRankContentSort.adapter = rankContentSortAdapter
|
|
||||||
|
|
||||||
viewModel.rankContentSortListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llRankContent.visibility = View.VISIBLE
|
|
||||||
rankContentSortAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRankContent() {
|
|
||||||
binding.ivRankContentAll.setOnClickListener {
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
startActivity(Intent(requireContext(), AudioContentRankingAllActivity::class.java))
|
|
||||||
} else {
|
|
||||||
(requireActivity() as MainActivity).showLoginActivity()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
rankContentAdapter = AudioContentMainRankingAdapter(
|
|
||||||
width = (screenWidth * 0.66).toInt()
|
|
||||||
) {
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
(requireActivity() as MainActivity).showLoginActivity()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvRankContent.layoutManager = GridLayoutManager(
|
|
||||||
context,
|
|
||||||
3,
|
|
||||||
GridLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvRankContent.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
outRect.top = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.left = 13.3f.dpToPx().toInt()
|
|
||||||
outRect.right = 13.3f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvRankContent.adapter = rankContentAdapter
|
|
||||||
|
|
||||||
viewModel.rankContentLiveData.observe(viewLifecycleOwner) {
|
|
||||||
binding.llRankContent.visibility = View.VISIBLE
|
|
||||||
rankContentAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupEventBanner() {
|
|
||||||
val imageSliderLp = binding.eventBannerSlider.layoutParams
|
|
||||||
imageSliderLp.width = screenWidth
|
|
||||||
imageSliderLp.height = (screenWidth * 300) / 1000
|
|
||||||
binding.eventBannerSlider.layoutParams = imageSliderLp
|
|
||||||
|
|
||||||
binding.eventBannerSlider.apply {
|
|
||||||
adapter = EventBannerAdapter(requireContext()) {
|
|
||||||
if (it.detailImageUrl != null) {
|
|
||||||
val intent = Intent(requireActivity(), EventDetailActivity::class.java)
|
|
||||||
intent.putExtra(Constants.EXTRA_EVENT, it)
|
|
||||||
startActivity(intent)
|
|
||||||
} else if (!it.link.isNullOrBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
Intent.ACTION_VIEW,
|
|
||||||
Uri.parse(it.link)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} as BaseBannerAdapter<Any>
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(800)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding.eventBannerSlider
|
|
||||||
.setIndicatorView(binding.indicatorEventBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.eventLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty() && SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
binding.eventBannerSlider.visibility = View.VISIBLE
|
|
||||||
binding.eventBannerSlider.refreshData(it)
|
|
||||||
} else {
|
|
||||||
binding.eventBannerSlider.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentCreator() {
|
|
||||||
contentRankCreatorAdapter = ContentRankCreatorAdapter {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
binding.rvRankingSalesCount.visibility = View.GONE
|
|
||||||
viewModel.getPopularContentByCreator(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvRankingCreator.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvRankingCreator.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankCreatorAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvRankingCreator.adapter = contentRankCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.contentRankCreatorListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
contentRankCreatorAdapter.addItems(it)
|
|
||||||
if (contentRankCreatorAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentByCreator() {
|
|
||||||
popularContentByCreatorAdapter = PopularContentByCreatorAdapter(
|
|
||||||
itemWidth = ((screenWidth - 13.3f.dpToPx() * 3) / 2).toInt(),
|
|
||||||
onClickItem = { contentId ->
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, contentId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
(requireActivity() as MainActivity).showLoginActivity()
|
|
||||||
}
|
|
||||||
},
|
|
||||||
onClickCreator = { creatorId ->
|
|
||||||
if (SharedPreferenceManager.token.isNotBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, creatorId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
} else {
|
|
||||||
(requireActivity() as MainActivity).showLoginActivity()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRankingSalesCount
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(requireContext(), 2)
|
|
||||||
recyclerView.addItemDecoration(
|
|
||||||
GridSpacingItemDecoration(
|
|
||||||
2,
|
|
||||||
13.3f.dpToPx().toInt(),
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.adapter = popularContentByCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.salesCountRankContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llNoItems.visibility = View.GONE
|
|
||||||
recyclerView.visibility = View.VISIBLE
|
|
||||||
popularContentByCreatorAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
recyclerView.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,30 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.home
|
|
||||||
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentApi
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
|
||||||
|
|
||||||
class AudioContentMainTabHomeRepository(private val api: AudioContentApi) {
|
|
||||||
fun getContentMainHome(token: String) = api.getContentMainHome(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(
|
|
||||||
creatorId: Long,
|
|
||||||
token: String
|
|
||||||
) = api.getPopularContentByCreator(
|
|
||||||
creatorId,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getContentRanking(sort: String, token: String) = api.getContentMainHomeContentRanking(
|
|
||||||
sortType = sort,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,175 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.home
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
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.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.explorer.GetExplorerSectionResponse
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventItem
|
|
||||||
import kr.co.vividnext.sodalive.settings.notice.NoticeItem
|
|
||||||
|
|
||||||
class AudioContentMainTabHomeViewModel(
|
|
||||||
private val repository: AudioContentMainTabHomeRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _noticeLiveData = MutableLiveData<NoticeItem>()
|
|
||||||
val noticeLiveData: LiveData<NoticeItem>
|
|
||||||
get() = _noticeLiveData
|
|
||||||
|
|
||||||
private var _contentBannerLiveData = MutableLiveData<List<GetAudioContentBannerResponse>>()
|
|
||||||
val contentBannerLiveData: LiveData<List<GetAudioContentBannerResponse>>
|
|
||||||
get() = _contentBannerLiveData
|
|
||||||
|
|
||||||
private val _rankCreatorLiveData = MutableLiveData<GetExplorerSectionResponse>()
|
|
||||||
val rankCreatorLiveData: LiveData<GetExplorerSectionResponse>
|
|
||||||
get() = _rankCreatorLiveData
|
|
||||||
|
|
||||||
private var _rankSeriesLiveData = MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val rankSeriesLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _rankSeriesLiveData
|
|
||||||
|
|
||||||
private var _rankContentSortListLiveData = MutableLiveData<List<String>>()
|
|
||||||
val rankContentSortListLiveData: LiveData<List<String>>
|
|
||||||
get() = _rankContentSortListLiveData
|
|
||||||
|
|
||||||
private var _rankContentLiveData = MutableLiveData<List<GetAudioContentRankingItem>>()
|
|
||||||
val rankContentLiveData: LiveData<List<GetAudioContentRankingItem>>
|
|
||||||
get() = _rankContentLiveData
|
|
||||||
|
|
||||||
private val _eventLiveData = MutableLiveData<List<EventItem>>()
|
|
||||||
val eventLiveData: LiveData<List<EventItem>>
|
|
||||||
get() = _eventLiveData
|
|
||||||
|
|
||||||
private val _contentRankCreatorListLiveData = MutableLiveData<List<ContentCreatorResponse>>()
|
|
||||||
val contentRankCreatorListLiveData: LiveData<List<ContentCreatorResponse>>
|
|
||||||
get() = _contentRankCreatorListLiveData
|
|
||||||
|
|
||||||
private val _salesCountRankContentListLiveData =
|
|
||||||
MutableLiveData<List<GetAudioContentRankingItem>>()
|
|
||||||
val salesCountRankContentListLiveData: LiveData<List<GetAudioContentRankingItem>>
|
|
||||||
get() = _salesCountRankContentListLiveData
|
|
||||||
|
|
||||||
fun fetchData() {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainHome(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val data = it.data
|
|
||||||
|
|
||||||
if (data.latestNotice != null) {
|
|
||||||
_noticeLiveData.value = data.latestNotice!!
|
|
||||||
}
|
|
||||||
_contentBannerLiveData.value = data.bannerList
|
|
||||||
_rankCreatorLiveData.value = data.rankCreatorList
|
|
||||||
_rankSeriesLiveData.value = data.rankSeriesList
|
|
||||||
_rankContentLiveData.value = data.rankContentList
|
|
||||||
_rankContentSortListLiveData.value = data.rankSortTypeList
|
|
||||||
_eventLiveData.value = data.eventBannerList.eventList
|
|
||||||
_contentRankCreatorListLiveData.value = data.contentRankCreatorList
|
|
||||||
_salesCountRankContentListLiveData.value =
|
|
||||||
data.salesCountRankContentList
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getContentRanking(sort: String = "매출") {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentRanking(
|
|
||||||
sort = sort,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_rankContentLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(creatorId: Long) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getPopularContentByCreator(
|
|
||||||
creatorId = creatorId,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_salesCountRankContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,23 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.home
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
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.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.explorer.GetExplorerSectionResponse
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.GetEventResponse
|
|
||||||
import kr.co.vividnext.sodalive.settings.notice.NoticeItem
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetContentMainTabHomeResponse(
|
|
||||||
val latestNotice: NoticeItem?,
|
|
||||||
val bannerList: List<GetAudioContentBannerResponse>,
|
|
||||||
val rankCreatorList: GetExplorerSectionResponse,
|
|
||||||
val rankSeriesList: List<GetSeriesListResponse.SeriesListItem>,
|
|
||||||
val rankSortTypeList: List<String>,
|
|
||||||
val rankContentList: List<GetAudioContentRankingItem>,
|
|
||||||
val eventBannerList: GetEventResponse,
|
|
||||||
val contentRankCreatorList: List<ContentCreatorResponse>,
|
|
||||||
val salesCountRankContentList: List<GetAudioContentRankingItem>
|
|
||||||
)
|
|
||||||
@@ -1,448 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.replay
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.LinearLayout
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.zhpan.bannerview.BaseBannerAdapter
|
|
||||||
import com.zhpan.indicator.enums.IndicatorSlideMode
|
|
||||||
import com.zhpan.indicator.enums.IndicatorStyle
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentBannerType
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentMainContentAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.AudioContentMainContentCurationAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.ContentRankCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.PopularContentByCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseFragment
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.FragmentAudioContentMainTabReplayBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.live.event_banner.EventBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventDetailActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class AudioContentMainTabReplayFragment : BaseFragment<FragmentAudioContentMainTabReplayBinding>(
|
|
||||||
FragmentAudioContentMainTabReplayBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AudioContentMainTabReplayViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var contentBannerAdapter: AudioContentMainBannerAdapter
|
|
||||||
private lateinit var newContentAdapter: AudioContentMainContentAdapter
|
|
||||||
private lateinit var curationAdapter: AudioContentMainContentCurationAdapter
|
|
||||||
private lateinit var contentRankCreatorAdapter: ContentRankCreatorAdapter
|
|
||||||
private lateinit var popularContentByCreatorAdapter: PopularContentByCreatorAdapter
|
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
|
||||||
super.onViewCreated(view, savedInstanceState)
|
|
||||||
setupView()
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.fetchData()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(requireActivity(), layoutInflater)
|
|
||||||
|
|
||||||
setupContentBanner()
|
|
||||||
setupNewContent()
|
|
||||||
setupPopularContentCreator()
|
|
||||||
setupPopularContentByCreator()
|
|
||||||
setupEventBanner()
|
|
||||||
setupCuration()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentBanner() {
|
|
||||||
val layoutParams = binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams as LinearLayout.LayoutParams
|
|
||||||
|
|
||||||
val pagerWidth = screenWidth.toDouble() - 26.7f.dpToPx()
|
|
||||||
val pagerHeight = (pagerWidth * 0.53).roundToInt()
|
|
||||||
layoutParams.width = pagerWidth.roundToInt()
|
|
||||||
layoutParams.height = pagerHeight
|
|
||||||
|
|
||||||
contentBannerAdapter = AudioContentMainBannerAdapter(
|
|
||||||
requireContext(),
|
|
||||||
pagerWidth.roundToInt(),
|
|
||||||
pagerHeight
|
|
||||||
) {
|
|
||||||
when (it.type) {
|
|
||||||
AudioContentBannerType.EVENT -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), EventDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_EVENT, it.eventItem!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.CREATOR -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it.creatorId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.SERIES -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it.seriesId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.LINK -> {
|
|
||||||
startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(it.link!!)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams = layoutParams
|
|
||||||
|
|
||||||
binding.rvBanner.apply {
|
|
||||||
adapter = contentBannerAdapter as BaseBannerAdapter<Any>
|
|
||||||
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(1000)
|
|
||||||
setInterval(4 * 1000)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.setIndicatorView(binding.indicatorBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.contentBannerLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (contentBannerAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.rvBanner.visibility = View.GONE
|
|
||||||
binding.indicatorBanner.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.rvBanner.visibility = View.VISIBLE
|
|
||||||
binding.indicatorBanner.visibility = View.VISIBLE
|
|
||||||
binding.rvBanner.refreshData(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
binding.ivNewContentAll.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), ReplayNewContentAllActivity::class.java)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter = AudioContentMainContentAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvNewContent.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
newContentAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvNewContent.adapter = newContentAdapter
|
|
||||||
|
|
||||||
viewModel.newContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llNewContent.visibility = View.VISIBLE
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llNewContent.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentCreator() {
|
|
||||||
contentRankCreatorAdapter = ContentRankCreatorAdapter {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
binding.rvRankingSalesCount.visibility = View.GONE
|
|
||||||
viewModel.getPopularContentByCreator(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvRankingCreator.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvRankingCreator.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
contentRankCreatorAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvRankingCreator.adapter = contentRankCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.contentCreatorListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
contentRankCreatorAdapter.addItems(it)
|
|
||||||
if (contentRankCreatorAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llCreatorContentRanking.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupPopularContentByCreator() {
|
|
||||||
popularContentByCreatorAdapter = PopularContentByCreatorAdapter(
|
|
||||||
itemWidth = ((screenWidth - 13.3f.dpToPx() * 3) / 2).toInt(),
|
|
||||||
onClickItem = { contentId ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, contentId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = { creatorId ->
|
|
||||||
startActivity(
|
|
||||||
Intent(requireActivity(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, creatorId)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRankingSalesCount
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(requireContext(), 2)
|
|
||||||
recyclerView.addItemDecoration(
|
|
||||||
GridSpacingItemDecoration(
|
|
||||||
2,
|
|
||||||
13.3f.dpToPx().toInt(),
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.adapter = popularContentByCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.salesCountRankContentListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llNoItems.visibility = View.GONE
|
|
||||||
recyclerView.visibility = View.VISIBLE
|
|
||||||
popularContentByCreatorAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
recyclerView.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupEventBanner() {
|
|
||||||
val imageSliderLp = binding.eventBannerSlider.layoutParams
|
|
||||||
imageSliderLp.width = screenWidth
|
|
||||||
imageSliderLp.height = (screenWidth * 300) / 1000
|
|
||||||
binding.eventBannerSlider.layoutParams = imageSliderLp
|
|
||||||
|
|
||||||
binding.eventBannerSlider.apply {
|
|
||||||
adapter = EventBannerAdapter(requireContext()) {
|
|
||||||
if (it.detailImageUrl != null) {
|
|
||||||
val intent = Intent(requireActivity(), EventDetailActivity::class.java)
|
|
||||||
intent.putExtra(Constants.EXTRA_EVENT, it)
|
|
||||||
startActivity(intent)
|
|
||||||
} else if (!it.link.isNullOrBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
Intent.ACTION_VIEW,
|
|
||||||
Uri.parse(it.link)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} as BaseBannerAdapter<Any>
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(800)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding.eventBannerSlider
|
|
||||||
.setIndicatorView(binding.indicatorEventBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.eventLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.eventBannerSlider.visibility = View.VISIBLE
|
|
||||||
binding.indicatorEventBanner.visibility = View.VISIBLE
|
|
||||||
binding.eventBannerSlider.refreshData(it)
|
|
||||||
} else {
|
|
||||||
binding.eventBannerSlider.visibility = View.GONE
|
|
||||||
binding.indicatorEventBanner.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCuration() {
|
|
||||||
curationAdapter = AudioContentMainContentCurationAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.VERTICAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.top = 30f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
curationAdapter.itemCount - 1 -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 30f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = curationAdapter
|
|
||||||
|
|
||||||
viewModel.curationListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
curationAdapter.addItems(it)
|
|
||||||
|
|
||||||
binding.rvCuration.visibility = if (curationAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,23 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.replay
|
|
||||||
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentApi
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
|
||||||
|
|
||||||
class AudioContentMainTabReplayRepository(private val api: AudioContentApi) {
|
|
||||||
fun getContentMainReplay(token: String) = api.getContentMainReplay(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(
|
|
||||||
creatorId: Long,
|
|
||||||
token: String
|
|
||||||
) = api.getPopularReplayContentByCreator(
|
|
||||||
creatorId,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,124 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.replay
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventItem
|
|
||||||
|
|
||||||
class AudioContentMainTabReplayViewModel(
|
|
||||||
private val repository: AudioContentMainTabReplayRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _contentBannerLiveData = MutableLiveData<List<GetAudioContentBannerResponse>>()
|
|
||||||
val contentBannerLiveData: LiveData<List<GetAudioContentBannerResponse>>
|
|
||||||
get() = _contentBannerLiveData
|
|
||||||
|
|
||||||
private var _newContentListLiveData = MutableLiveData<List<GetAudioContentMainItem>>()
|
|
||||||
val newContentListLiveData: LiveData<List<GetAudioContentMainItem>>
|
|
||||||
get() = _newContentListLiveData
|
|
||||||
|
|
||||||
private val _contentCreatorListLiveData = MutableLiveData<List<ContentCreatorResponse>>()
|
|
||||||
val contentCreatorListLiveData: LiveData<List<ContentCreatorResponse>>
|
|
||||||
get() = _contentCreatorListLiveData
|
|
||||||
|
|
||||||
private val _salesCountRankContentListLiveData =
|
|
||||||
MutableLiveData<List<GetAudioContentRankingItem>>()
|
|
||||||
val salesCountRankContentListLiveData: LiveData<List<GetAudioContentRankingItem>>
|
|
||||||
get() = _salesCountRankContentListLiveData
|
|
||||||
|
|
||||||
private val _eventLiveData = MutableLiveData<List<EventItem>>()
|
|
||||||
val eventLiveData: LiveData<List<EventItem>>
|
|
||||||
get() = _eventLiveData
|
|
||||||
|
|
||||||
private var _curationListLiveData = MutableLiveData<List<GetContentCurationResponse>>()
|
|
||||||
val curationListLiveData: LiveData<List<GetContentCurationResponse>>
|
|
||||||
get() = _curationListLiveData
|
|
||||||
|
|
||||||
fun fetchData() {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainReplay(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val data = it.data
|
|
||||||
|
|
||||||
_contentBannerLiveData.value = data.contentBannerList
|
|
||||||
_newContentListLiveData.value = data.newLiveReplayContentList
|
|
||||||
_contentCreatorListLiveData.value = data.creatorList
|
|
||||||
_salesCountRankContentListLiveData.value =
|
|
||||||
data.salesCountRankContentList
|
|
||||||
_eventLiveData.value = data.eventBannerList.eventList
|
|
||||||
_curationListLiveData.value = data.curationList
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getPopularContentByCreator(creatorId: Long) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getPopularContentByCreator(
|
|
||||||
creatorId = creatorId,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_salesCountRankContentListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,26 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.replay
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentMainItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentRankingItem
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.GetContentCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.GetEventResponse
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetContentMainTabLiveReplayResponse(
|
|
||||||
@SerializedName("contentBannerList")
|
|
||||||
val contentBannerList: List<GetAudioContentBannerResponse>,
|
|
||||||
@SerializedName("newLiveReplayContentList")
|
|
||||||
val newLiveReplayContentList: List<GetAudioContentMainItem>,
|
|
||||||
@SerializedName("creatorList")
|
|
||||||
val creatorList: List<ContentCreatorResponse>,
|
|
||||||
@SerializedName("salesCountRankContentList")
|
|
||||||
val salesCountRankContentList: List<GetAudioContentRankingItem>,
|
|
||||||
@SerializedName("eventBannerList")
|
|
||||||
val eventBannerList: GetEventResponse,
|
|
||||||
@SerializedName("curationList")
|
|
||||||
val curationList: List<GetContentCurationResponse>
|
|
||||||
)
|
|
||||||
@@ -1,114 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.replay
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.annotation.OptIn
|
|
||||||
import androidx.media3.common.util.UnstableApi
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.all.AudioContentNewAllViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseActivity
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.GridSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ActivityAsmrNewContentAllBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
|
|
||||||
@OptIn(UnstableApi::class)
|
|
||||||
class ReplayNewContentAllActivity : BaseActivity<ActivityAsmrNewContentAllBinding>(
|
|
||||||
ActivityAsmrNewContentAllBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AudioContentNewAllViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
|
|
||||||
private lateinit var newContentAdapter: AudioContentNewAllAdapter
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
|
|
||||||
bindData()
|
|
||||||
viewModel.selectTheme(theme = "다시듣기", isFree = false)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(this, layoutInflater)
|
|
||||||
binding.toolbar.tvBack.text = "새로운 라이브 다시듣기"
|
|
||||||
binding.toolbar.tvBack.setOnClickListener { finish() }
|
|
||||||
|
|
||||||
binding.tvNotice.text = "※ 최근 2주간 등록된 새로운 라이브 다시듣기 입니다."
|
|
||||||
|
|
||||||
setupNewContent()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewContent() {
|
|
||||||
val spanCount = 3
|
|
||||||
val spacing = 40
|
|
||||||
newContentAdapter = AudioContentNewAllAdapter(
|
|
||||||
itemWidth = (screenWidth - (spacing * (spanCount + 1))) / 3,
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, AudioContentDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_AUDIO_CONTENT_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(this, UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvContent.layoutManager = GridLayoutManager(this, spanCount)
|
|
||||||
binding.rvContent.addItemDecoration(GridSpacingItemDecoration(spanCount, spacing, true))
|
|
||||||
|
|
||||||
binding.rvContent.addOnScrollListener(object : RecyclerView.OnScrollListener() {
|
|
||||||
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
|
|
||||||
super.onScrolled(recyclerView, dx, dy)
|
|
||||||
|
|
||||||
val lastVisibleItemPosition = (recyclerView.layoutManager as LinearLayoutManager?)!!
|
|
||||||
.findLastCompletelyVisibleItemPosition()
|
|
||||||
val itemTotalCount = recyclerView.adapter!!.itemCount - 1
|
|
||||||
|
|
||||||
// 스크롤이 끝에 도달했는지 확인
|
|
||||||
if (!recyclerView.canScrollVertically(1) &&
|
|
||||||
lastVisibleItemPosition == itemTotalCount
|
|
||||||
) {
|
|
||||||
viewModel.getNewContentList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvContent.adapter = newContentAdapter
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.isLoading.observe(this) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.toastLiveData.observe(this) {
|
|
||||||
it?.let { Toast.makeText(applicationContext, it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.newContentListLiveData.observe(this) {
|
|
||||||
newContentAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.newContentTotalCountLiveData.observe(this) {
|
|
||||||
binding.tvTotalCount.text = "$it"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,787 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.net.Uri
|
|
||||||
import android.os.Bundle
|
|
||||||
import android.view.View
|
|
||||||
import android.widget.LinearLayout
|
|
||||||
import android.widget.Toast
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.zhpan.bannerview.BaseBannerAdapter
|
|
||||||
import com.zhpan.indicator.enums.IndicatorSlideMode
|
|
||||||
import com.zhpan.indicator.enums.IndicatorStyle
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.AudioContentBannerType
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.ContentRankCreatorAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.completed.CompletedSeriesActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.curation.AudioContentMainSeriesCurationAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.new_series.AudioContentMainNewSeriesAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.origianl_audio_drama.AudioContentMainTabSeriesOriginalAudioDramaAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.origianl_audio_drama.OriginalAudioDramaContentAllActivity
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.rank_series.AudioContentMainSeriesRankingAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.recommend_by_genre.AudioContentMainRecommendSeriesGenreAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseFragment
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.FragmentAudioContentMainTabSeriesBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.UserProfileActivity
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.series.UserProfileSeriesListAdapter
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import kr.co.vividnext.sodalive.live.event_banner.EventBannerAdapter
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventDetailActivity
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
class AudioContentMainTabSeriesFragment : BaseFragment<FragmentAudioContentMainTabSeriesBinding>(
|
|
||||||
FragmentAudioContentMainTabSeriesBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: AudioContentMainTabSeriesViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var contentBannerAdapter: AudioContentMainBannerAdapter
|
|
||||||
private lateinit var audioDramaAdapter: AudioContentMainTabSeriesOriginalAudioDramaAdapter
|
|
||||||
private lateinit var rankDailySeriesAdapter: AudioContentMainSeriesRankingAdapter
|
|
||||||
private lateinit var seriesGenreAdapter: AudioContentMainRecommendSeriesGenreAdapter
|
|
||||||
private lateinit var recommendSeriesByGenreAdapter: UserProfileSeriesListAdapter
|
|
||||||
private lateinit var newSeriesAdapter: AudioContentMainNewSeriesAdapter
|
|
||||||
private lateinit var completedSeriesAdapter: UserProfileSeriesListAdapter
|
|
||||||
private lateinit var recommendSeriesCreatorAdapter: ContentRankCreatorAdapter
|
|
||||||
private lateinit var recommendSeriesByChannelAdapter: UserProfileSeriesListAdapter
|
|
||||||
private lateinit var curationAdapter: AudioContentMainSeriesCurationAdapter
|
|
||||||
|
|
||||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
|
||||||
super.onViewCreated(view, savedInstanceState)
|
|
||||||
setupView()
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.fetchData()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(requireActivity(), layoutInflater)
|
|
||||||
|
|
||||||
setupContentBanner()
|
|
||||||
setupOriginalAudioDrama()
|
|
||||||
setupRankSeries()
|
|
||||||
setupRecommendSeriesGenre()
|
|
||||||
setupRecommendSeriesByGenre()
|
|
||||||
setupNewSeries()
|
|
||||||
setupCompleteSeries()
|
|
||||||
setupRecommendSeriesByChannelCreator()
|
|
||||||
setupRecommendSeriesByChannel()
|
|
||||||
setupEventBanner()
|
|
||||||
setupCuration()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupContentBanner() {
|
|
||||||
val layoutParams = binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams as LinearLayout.LayoutParams
|
|
||||||
|
|
||||||
val pagerWidth = screenWidth.toDouble() - 26.7f.dpToPx()
|
|
||||||
val pagerHeight = (pagerWidth * 0.53).roundToInt()
|
|
||||||
layoutParams.width = pagerWidth.roundToInt()
|
|
||||||
layoutParams.height = pagerHeight
|
|
||||||
|
|
||||||
contentBannerAdapter = AudioContentMainBannerAdapter(
|
|
||||||
requireContext(),
|
|
||||||
pagerWidth.roundToInt(),
|
|
||||||
pagerHeight
|
|
||||||
) {
|
|
||||||
when (it.type) {
|
|
||||||
AudioContentBannerType.EVENT -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), EventDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_EVENT, it.eventItem!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.CREATOR -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it.creatorId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.SERIES -> {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it.seriesId!!)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
AudioContentBannerType.LINK -> {
|
|
||||||
startActivity(Intent(Intent.ACTION_VIEW, Uri.parse(it.link!!)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.layoutParams = layoutParams
|
|
||||||
|
|
||||||
binding.rvBanner.apply {
|
|
||||||
adapter = contentBannerAdapter as BaseBannerAdapter<Any>
|
|
||||||
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(1000)
|
|
||||||
setInterval(4 * 1000)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding
|
|
||||||
.rvBanner
|
|
||||||
.setIndicatorView(binding.indicatorBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.contentBannerLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (contentBannerAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.rvBanner.visibility = View.GONE
|
|
||||||
binding.indicatorBanner.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.rvBanner.visibility = View.VISIBLE
|
|
||||||
binding.indicatorBanner.visibility = View.VISIBLE
|
|
||||||
binding.rvBanner.refreshData(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupOriginalAudioDrama() {
|
|
||||||
audioDramaAdapter = AudioContentMainTabSeriesOriginalAudioDramaAdapter {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
val recyclerView = binding.rvOriginalAudio
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
audioDramaAdapter.itemCount - 1 -> {
|
|
||||||
outRect.right = 0
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = audioDramaAdapter
|
|
||||||
|
|
||||||
viewModel.originalAudioDramaLiveData.observe(viewLifecycleOwner) {
|
|
||||||
audioDramaAdapter.addItems(it)
|
|
||||||
binding.llOriginalAudioDrama.visibility =
|
|
||||||
if (audioDramaAdapter.isVisibleRecyclerView()) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.ivOriginalAudioDramaAll.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireContext(),
|
|
||||||
OriginalAudioDramaContentAllActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRankSeries() {
|
|
||||||
rankDailySeriesAdapter = AudioContentMainSeriesRankingAdapter {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRankSeries
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(
|
|
||||||
context,
|
|
||||||
3,
|
|
||||||
GridLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
outRect.top = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = rankDailySeriesAdapter
|
|
||||||
|
|
||||||
viewModel.rankSeriesListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llRankSeries.visibility = View.VISIBLE
|
|
||||||
rankDailySeriesAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llRankSeries.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRecommendSeriesGenre() {
|
|
||||||
seriesGenreAdapter = AudioContentMainRecommendSeriesGenreAdapter {
|
|
||||||
binding.llNoItemsSeriesByGenre.visibility = View.VISIBLE
|
|
||||||
binding.rvSeriesByGenre.visibility = View.GONE
|
|
||||||
viewModel.selectGenre(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
val recyclerView = binding.rvSeriesGenre
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
seriesGenreAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 4f.dpToPx().toInt()
|
|
||||||
outRect.right = 4f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = seriesGenreAdapter
|
|
||||||
|
|
||||||
viewModel.genreListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llSeriesByGenre.visibility = View.VISIBLE
|
|
||||||
seriesGenreAdapter.addItems(it)
|
|
||||||
} else {
|
|
||||||
binding.llSeriesByGenre.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRecommendSeriesByGenre() {
|
|
||||||
recommendSeriesByGenreAdapter = UserProfileSeriesListAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
isVisibleCreator = true
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvSeriesByGenre
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
recommendSeriesByGenreAdapter.itemCount - 1 -> {
|
|
||||||
outRect.right = 0
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = recommendSeriesByGenreAdapter
|
|
||||||
|
|
||||||
viewModel.recommendSeriesListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.llNoItemsSeriesByGenre.visibility = View.GONE
|
|
||||||
binding.rvSeriesByGenre.visibility = View.VISIBLE
|
|
||||||
recommendSeriesByGenreAdapter.clear()
|
|
||||||
recommendSeriesByGenreAdapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupNewSeries() {
|
|
||||||
newSeriesAdapter = AudioContentMainNewSeriesAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvNewSeries
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
recommendSeriesByGenreAdapter.itemCount - 1 -> {
|
|
||||||
outRect.right = 0
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = newSeriesAdapter
|
|
||||||
|
|
||||||
viewModel.newSeriesListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
newSeriesAdapter.addItems(it)
|
|
||||||
binding.llNewSeries.visibility = if (it.isNotEmpty()) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCompleteSeries() {
|
|
||||||
binding.ivCompleteSeriesAll.setOnClickListener {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
requireContext(),
|
|
||||||
CompletedSeriesActivity::class.java
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
completedSeriesAdapter = UserProfileSeriesListAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
isVisibleCreator = true
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvCompleteSeries
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
completedSeriesAdapter.itemCount - 1 -> {
|
|
||||||
outRect.right = 0
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = completedSeriesAdapter
|
|
||||||
|
|
||||||
viewModel.rankCompleteSeriesListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
completedSeriesAdapter.addItems(it)
|
|
||||||
binding.llCompleteSeries.visibility = if (
|
|
||||||
completedSeriesAdapter.itemCount <= 0 && it.isEmpty()
|
|
||||||
) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRecommendSeriesByChannelCreator() {
|
|
||||||
recommendSeriesCreatorAdapter = ContentRankCreatorAdapter {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
binding.rvRecommendSeriesByChannel.visibility = View.GONE
|
|
||||||
viewModel.getRecommendSeriesByCreator(it)
|
|
||||||
}
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRecommendSeriesChannel
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
recommendSeriesCreatorAdapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 11f.dpToPx().toInt()
|
|
||||||
outRect.right = 11f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = recommendSeriesCreatorAdapter
|
|
||||||
|
|
||||||
viewModel.seriesRankCreatorListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
recommendSeriesCreatorAdapter.addItems(it)
|
|
||||||
if (recommendSeriesCreatorAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
binding.llRecommendSeriesByChannel.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llRecommendSeriesByChannel.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupRecommendSeriesByChannel() {
|
|
||||||
recommendSeriesByChannelAdapter = UserProfileSeriesListAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
isVisibleCreator = true
|
|
||||||
)
|
|
||||||
|
|
||||||
val recyclerView = binding.rvRecommendSeriesByChannel
|
|
||||||
recyclerView.layoutManager = LinearLayoutManager(
|
|
||||||
requireContext(),
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
recommendSeriesByChannelAdapter.itemCount - 1 -> {
|
|
||||||
outRect.right = 0
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = recommendSeriesByChannelAdapter
|
|
||||||
|
|
||||||
viewModel.recommendSeriesByChannelLiveData.observe(viewLifecycleOwner) {
|
|
||||||
recommendSeriesByChannelAdapter.clear()
|
|
||||||
recommendSeriesByChannelAdapter.addItems(it)
|
|
||||||
if (recommendSeriesCreatorAdapter.itemCount <= 0) {
|
|
||||||
binding.llNoItems.visibility = View.VISIBLE
|
|
||||||
binding.rvRecommendSeriesByChannel.visibility = View.GONE
|
|
||||||
} else {
|
|
||||||
binding.llNoItems.visibility = View.GONE
|
|
||||||
binding.rvRecommendSeriesByChannel.visibility = View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupEventBanner() {
|
|
||||||
val imageSliderLp = binding.eventBannerSlider.layoutParams
|
|
||||||
imageSliderLp.width = screenWidth
|
|
||||||
imageSliderLp.height = (screenWidth * 300) / 1000
|
|
||||||
binding.eventBannerSlider.layoutParams = imageSliderLp
|
|
||||||
|
|
||||||
binding.eventBannerSlider.apply {
|
|
||||||
adapter = EventBannerAdapter(requireContext()) {
|
|
||||||
if (it.detailImageUrl != null) {
|
|
||||||
val intent = Intent(requireActivity(), EventDetailActivity::class.java)
|
|
||||||
intent.putExtra(Constants.EXTRA_EVENT, it)
|
|
||||||
startActivity(intent)
|
|
||||||
} else if (!it.link.isNullOrBlank()) {
|
|
||||||
startActivity(
|
|
||||||
Intent(
|
|
||||||
Intent.ACTION_VIEW,
|
|
||||||
Uri.parse(it.link)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
} as BaseBannerAdapter<Any>
|
|
||||||
setLifecycleRegistry(lifecycle)
|
|
||||||
setScrollDuration(800)
|
|
||||||
}.create()
|
|
||||||
|
|
||||||
binding.eventBannerSlider
|
|
||||||
.setIndicatorView(binding.indicatorEventBanner)
|
|
||||||
.setIndicatorStyle(IndicatorStyle.ROUND_RECT)
|
|
||||||
.setIndicatorSlideMode(IndicatorSlideMode.SMOOTH)
|
|
||||||
.setIndicatorVisibility(View.GONE)
|
|
||||||
.setIndicatorSliderColor(
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_909090),
|
|
||||||
ContextCompat.getColor(requireContext(), R.color.color_3bb9f1)
|
|
||||||
)
|
|
||||||
.setIndicatorSliderWidth(4f.dpToPx().toInt(), 10f.dpToPx().toInt())
|
|
||||||
.setIndicatorHeight(4f.dpToPx().toInt())
|
|
||||||
|
|
||||||
viewModel.eventLiveData.observe(viewLifecycleOwner) {
|
|
||||||
if (it.isNotEmpty()) {
|
|
||||||
binding.eventBannerSlider.visibility = View.VISIBLE
|
|
||||||
binding.indicatorEventBanner.visibility = View.VISIBLE
|
|
||||||
binding.eventBannerSlider.refreshData(it)
|
|
||||||
} else {
|
|
||||||
binding.eventBannerSlider.visibility = View.GONE
|
|
||||||
binding.indicatorEventBanner.visibility = View.GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCuration() {
|
|
||||||
curationAdapter = AudioContentMainSeriesCurationAdapter(
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {
|
|
||||||
startActivity(
|
|
||||||
Intent(requireContext(), UserProfileActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_USER_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.VERTICAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.top = 30f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
curationAdapter.itemCount - 1 -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 30f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.top = 15f.dpToPx().toInt()
|
|
||||||
outRect.bottom = 15f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = curationAdapter
|
|
||||||
|
|
||||||
viewModel.curationListLiveData.observe(viewLifecycleOwner) {
|
|
||||||
curationAdapter.addItems(it)
|
|
||||||
|
|
||||||
binding.rvCuration.visibility = if (curationAdapter.itemCount <= 0 && it.isEmpty()) {
|
|
||||||
View.GONE
|
|
||||||
} else {
|
|
||||||
View.VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(viewLifecycleOwner) {
|
|
||||||
it?.let { Toast.makeText(requireContext(), it, Toast.LENGTH_LONG).show() }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(viewLifecycleOwner) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,45 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series
|
|
||||||
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentApi
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
|
||||||
|
|
||||||
class AudioContentMainTabSeriesRepository(private val api: AudioContentApi) {
|
|
||||||
fun getContentMainSeries(token: String) = api.getContentMainSeries(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getRecommendSeriesListByGenre(
|
|
||||||
genreId: Long,
|
|
||||||
token: String
|
|
||||||
) = api.getRecommendSeriesListByGenre(
|
|
||||||
genreId,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getRecommendSeriesByCreator(
|
|
||||||
creatorId: Long,
|
|
||||||
token: String
|
|
||||||
) = api.getRecommendSeriesByCreator(
|
|
||||||
creatorId,
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
|
|
||||||
fun getCompletedSeries(
|
|
||||||
page: Int,
|
|
||||||
size: Int,
|
|
||||||
token: String
|
|
||||||
) = api.getCompletedSeries(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
page = page - 1,
|
|
||||||
size = size,
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,183 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.EventItem
|
|
||||||
|
|
||||||
class AudioContentMainTabSeriesViewModel(
|
|
||||||
private val repository: AudioContentMainTabSeriesRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _contentBannerLiveData = MutableLiveData<List<GetAudioContentBannerResponse>>()
|
|
||||||
val contentBannerLiveData: LiveData<List<GetAudioContentBannerResponse>>
|
|
||||||
get() = _contentBannerLiveData
|
|
||||||
|
|
||||||
private var _originalAudioDramaLiveData =
|
|
||||||
MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val originalAudioDramaLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _originalAudioDramaLiveData
|
|
||||||
|
|
||||||
private var _rankSeriesListLiveData =
|
|
||||||
MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val rankSeriesListLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _rankSeriesListLiveData
|
|
||||||
|
|
||||||
private var _genreListLiveData = MutableLiveData<List<GetSeriesGenreListResponse>>()
|
|
||||||
val genreListLiveData: LiveData<List<GetSeriesGenreListResponse>>
|
|
||||||
get() = _genreListLiveData
|
|
||||||
|
|
||||||
private var _recommendSeriesListLiveData =
|
|
||||||
MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val recommendSeriesListLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _recommendSeriesListLiveData
|
|
||||||
|
|
||||||
private var _newSeriesListLiveData = MutableLiveData<List<GetRecommendSeriesListResponse>>()
|
|
||||||
val newSeriesListLiveData: LiveData<List<GetRecommendSeriesListResponse>>
|
|
||||||
get() = _newSeriesListLiveData
|
|
||||||
|
|
||||||
private var _rankCompleteSeriesListLiveData =
|
|
||||||
MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val rankCompleteSeriesListLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _rankCompleteSeriesListLiveData
|
|
||||||
|
|
||||||
private var _seriesRankCreatorListLiveData = MutableLiveData<List<ContentCreatorResponse>>()
|
|
||||||
val seriesRankCreatorListLiveData: LiveData<List<ContentCreatorResponse>>
|
|
||||||
get() = _seriesRankCreatorListLiveData
|
|
||||||
|
|
||||||
private var _recommendSeriesByChannelLiveData =
|
|
||||||
MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val recommendSeriesByChannelLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _recommendSeriesByChannelLiveData
|
|
||||||
|
|
||||||
private val _eventLiveData = MutableLiveData<List<EventItem>>()
|
|
||||||
val eventLiveData: LiveData<List<EventItem>>
|
|
||||||
get() = _eventLiveData
|
|
||||||
|
|
||||||
private val _curationListLiveData = MutableLiveData<List<GetSeriesCurationResponse>>()
|
|
||||||
val curationListLiveData: LiveData<List<GetSeriesCurationResponse>>
|
|
||||||
get() = _curationListLiveData
|
|
||||||
|
|
||||||
fun fetchData() {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getContentMainSeries(token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
val data = it.data
|
|
||||||
|
|
||||||
_contentBannerLiveData.value = data.contentBannerList
|
|
||||||
_originalAudioDramaLiveData.value = data.originalAudioDrama
|
|
||||||
_rankSeriesListLiveData.value = data.rankSeriesList
|
|
||||||
_genreListLiveData.value = data.genreList
|
|
||||||
_recommendSeriesListLiveData.value = data.recommendSeriesList
|
|
||||||
_newSeriesListLiveData.value = data.newSeriesList
|
|
||||||
_rankCompleteSeriesListLiveData.value = data.rankCompleteSeriesList
|
|
||||||
_seriesRankCreatorListLiveData.value = data.seriesRankCreatorList
|
|
||||||
_recommendSeriesByChannelLiveData.value = data.recommendSeriesByChannel
|
|
||||||
_eventLiveData.value = data.eventBannerList.eventList
|
|
||||||
_curationListLiveData.value = data.curationList
|
|
||||||
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun selectGenre(genreId: Long) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getRecommendSeriesListByGenre(
|
|
||||||
genreId,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_recommendSeriesListLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getRecommendSeriesByCreator(creatorId: Long) {
|
|
||||||
_isLoading.value = true
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getRecommendSeriesByCreator(creatorId, token = "Bearer ${SharedPreferenceManager.token}")
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
_recommendSeriesByChannelLiveData.value = it.data!!
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.postValue(it.message)
|
|
||||||
} else {
|
|
||||||
_toastLiveData.postValue(
|
|
||||||
"알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,34 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ContentCreatorResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.GetAudioContentBannerResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.settings.event.GetEventResponse
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetContentMainTabSeriesResponse(
|
|
||||||
@SerializedName("contentBannerList")
|
|
||||||
val contentBannerList: List<GetAudioContentBannerResponse>,
|
|
||||||
@SerializedName("originalAudioDrama")
|
|
||||||
val originalAudioDrama: List<GetSeriesListResponse.SeriesListItem>,
|
|
||||||
@SerializedName("rankSeriesList")
|
|
||||||
val rankSeriesList: List<GetSeriesListResponse.SeriesListItem>,
|
|
||||||
@SerializedName("genreList")
|
|
||||||
val genreList: List<GetSeriesGenreListResponse>,
|
|
||||||
@SerializedName("recommendSeriesList")
|
|
||||||
val recommendSeriesList: List<GetSeriesListResponse.SeriesListItem>,
|
|
||||||
@SerializedName("newSeriesList")
|
|
||||||
val newSeriesList: List<GetRecommendSeriesListResponse>,
|
|
||||||
@SerializedName("rankCompleteSeriesList")
|
|
||||||
val rankCompleteSeriesList: List<GetSeriesListResponse.SeriesListItem>,
|
|
||||||
@SerializedName("seriesRankCreatorList")
|
|
||||||
val seriesRankCreatorList: List<ContentCreatorResponse>,
|
|
||||||
@SerializedName("recommendSeriesByChannel")
|
|
||||||
val recommendSeriesByChannel: List<GetSeriesListResponse.SeriesListItem>,
|
|
||||||
@SerializedName("eventBannerList")
|
|
||||||
val eventBannerList: GetEventResponse,
|
|
||||||
@SerializedName("curationList")
|
|
||||||
val curationList: List<GetSeriesCurationResponse>
|
|
||||||
)
|
|
||||||
@@ -1,14 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetRecommendSeriesListResponse(
|
|
||||||
@SerializedName("seriesId") val seriesId: Long,
|
|
||||||
@SerializedName("title") val title: String,
|
|
||||||
@SerializedName("imageUrl") val imageUrl: String,
|
|
||||||
@SerializedName("creatorId") val creatorId: Long,
|
|
||||||
@SerializedName("creatorNickname") val creatorNickname: String,
|
|
||||||
@SerializedName("creatorProfileImageUrl") val creatorProfileImageUrl: String
|
|
||||||
)
|
|
||||||
@@ -1,11 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetSeriesCurationResponse(
|
|
||||||
@SerializedName("title") val title: String,
|
|
||||||
@SerializedName("items") val items: List<GetSeriesListResponse.SeriesListItem>
|
|
||||||
)
|
|
||||||
@@ -1,10 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series
|
|
||||||
|
|
||||||
import androidx.annotation.Keep
|
|
||||||
import com.google.gson.annotations.SerializedName
|
|
||||||
|
|
||||||
@Keep
|
|
||||||
data class GetSeriesGenreListResponse(
|
|
||||||
@SerializedName("id") val id: Long,
|
|
||||||
@SerializedName("genre") val genre: String
|
|
||||||
)
|
|
||||||
@@ -1,109 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.completed
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.os.Bundle
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.SeriesListAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseActivity
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.DifferentSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ActivityCompletedSeriesBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
class CompletedSeriesActivity : BaseActivity<ActivityCompletedSeriesBinding>(
|
|
||||||
ActivityCompletedSeriesBinding::inflate
|
|
||||||
) {
|
|
||||||
|
|
||||||
private val viewModel: CompletedSeriesViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var adapter: SeriesListAdapter
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.getCompletedSeries()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(this, layoutInflater)
|
|
||||||
binding.toolbar.tvBack.text = "완결 시리즈"
|
|
||||||
binding.toolbar.tvBack.setOnClickListener { finish() }
|
|
||||||
|
|
||||||
setupCompletedSeriesListView()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupCompletedSeriesListView() {
|
|
||||||
val spacing = 13.3f.dpToPx().roundToInt()
|
|
||||||
|
|
||||||
adapter = SeriesListAdapter(
|
|
||||||
itemWidth = ((screenWidth - spacing * 4) / 3f).roundToInt(),
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(applicationContext, SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {},
|
|
||||||
isVisibleCreator = true
|
|
||||||
)
|
|
||||||
|
|
||||||
val spanCount = 3
|
|
||||||
val recyclerView = binding.rvSeries
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(this, spanCount)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(
|
|
||||||
DifferentSpacingItemDecoration(
|
|
||||||
spanCount = spanCount,
|
|
||||||
horizontalSpacing = spacing,
|
|
||||||
verticalSpacing = spacing,
|
|
||||||
includeEdge = true
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addOnScrollListener(object : RecyclerView.OnScrollListener() {
|
|
||||||
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
|
|
||||||
super.onScrolled(recyclerView, dx, dy)
|
|
||||||
|
|
||||||
val lastVisibleItemPosition = (recyclerView.layoutManager as LinearLayoutManager?)!!
|
|
||||||
.findLastCompletelyVisibleItemPosition()
|
|
||||||
val itemTotalCount = recyclerView.adapter!!.itemCount - 1
|
|
||||||
|
|
||||||
// 스크롤이 끝에 도달했는지 확인
|
|
||||||
if (!recyclerView.canScrollVertically(1) &&
|
|
||||||
lastVisibleItemPosition == itemTotalCount
|
|
||||||
) {
|
|
||||||
viewModel.getCompletedSeries()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = adapter
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(this) {
|
|
||||||
it?.let { showToast(it) }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(this) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.completedSeriesLiveData.observe(this) {
|
|
||||||
adapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,75 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.completed
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.AudioContentMainTabSeriesRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class CompletedSeriesViewModel(
|
|
||||||
private val repository: AudioContentMainTabSeriesRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _completedSeriesLiveData =
|
|
||||||
MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val completedSeriesLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _completedSeriesLiveData
|
|
||||||
|
|
||||||
var isLast = false
|
|
||||||
var page = 1
|
|
||||||
private val size = 20
|
|
||||||
|
|
||||||
fun getCompletedSeries() {
|
|
||||||
if (!_isLoading.value!! && !isLast) {
|
|
||||||
_isLoading.value = true
|
|
||||||
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getCompletedSeries(
|
|
||||||
page = page,
|
|
||||||
size = size,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
page += 1
|
|
||||||
|
|
||||||
if (it.data.items.isNotEmpty()) {
|
|
||||||
_completedSeriesLiveData.value = it.data.items
|
|
||||||
} else {
|
|
||||||
isLast = true
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.value = it.message
|
|
||||||
} else {
|
|
||||||
_toastLiveData.value = "알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,105 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.curation
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.graphics.Rect
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.GetSeriesCurationResponse
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainCurationBinding
|
|
||||||
import kr.co.vividnext.sodalive.explorer.profile.series.UserProfileSeriesListAdapter
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
|
|
||||||
class AudioContentMainSeriesCurationAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit,
|
|
||||||
private val onClickCreator: (Long) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainSeriesCurationAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
private val items = mutableListOf<GetSeriesCurationResponse>()
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemAudioContentMainCurationBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
fun bind(item: GetSeriesCurationResponse) {
|
|
||||||
binding.tvDesc.visibility = View.GONE
|
|
||||||
binding.ivAll.visibility = View.GONE
|
|
||||||
|
|
||||||
binding.tvTitle.text = item.title
|
|
||||||
setSeriesList(item.items)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setSeriesList(items: List<GetSeriesListResponse.SeriesListItem>) {
|
|
||||||
val adapter = UserProfileSeriesListAdapter(
|
|
||||||
onClickItem = onClickItem,
|
|
||||||
onClickCreator = onClickCreator,
|
|
||||||
isVisibleCreator = true
|
|
||||||
)
|
|
||||||
|
|
||||||
binding.rvCuration.layoutManager = LinearLayoutManager(
|
|
||||||
context,
|
|
||||||
LinearLayoutManager.HORIZONTAL,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
|
|
||||||
if (binding.rvCuration.itemDecorationCount == 0) {
|
|
||||||
binding.rvCuration.addItemDecoration(object : RecyclerView.ItemDecoration() {
|
|
||||||
override fun getItemOffsets(
|
|
||||||
outRect: Rect,
|
|
||||||
view: View,
|
|
||||||
parent: RecyclerView,
|
|
||||||
state: RecyclerView.State
|
|
||||||
) {
|
|
||||||
super.getItemOffsets(outRect, view, parent, state)
|
|
||||||
|
|
||||||
when (parent.getChildAdapterPosition(view)) {
|
|
||||||
0 -> {
|
|
||||||
outRect.left = 0
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
|
|
||||||
adapter.itemCount - 1 -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
else -> {
|
|
||||||
outRect.left = 6.7f.dpToPx().toInt()
|
|
||||||
outRect.right = 6.7f.dpToPx().toInt()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.rvCuration.adapter = adapter
|
|
||||||
adapter.addItems(items)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetSeriesCurationResponse>) {
|
|
||||||
this.items.clear()
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemAudioContentMainCurationBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
}
|
|
||||||
@@ -1,77 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.new_series
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import coil.load
|
|
||||||
import coil.transform.CircleCropTransformation
|
|
||||||
import com.bumptech.glide.Glide
|
|
||||||
import com.bumptech.glide.load.resource.bitmap.CenterCrop
|
|
||||||
import com.bumptech.glide.load.resource.bitmap.RoundedCorners
|
|
||||||
import com.bumptech.glide.request.RequestOptions
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.GetRecommendSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainNewSeriesBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
|
|
||||||
class AudioContentMainNewSeriesAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit,
|
|
||||||
private val onClickCreator: (Long) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainNewSeriesAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
private val items = mutableListOf<GetRecommendSeriesListResponse>()
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemAudioContentMainNewSeriesBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
fun bind(item: GetRecommendSeriesListResponse) {
|
|
||||||
Glide
|
|
||||||
.with(context)
|
|
||||||
.load(item.imageUrl)
|
|
||||||
.apply(
|
|
||||||
RequestOptions().transform(
|
|
||||||
CenterCrop(),
|
|
||||||
RoundedCorners(5f.dpToPx().toInt())
|
|
||||||
)
|
|
||||||
)
|
|
||||||
.into(binding.ivCover)
|
|
||||||
|
|
||||||
binding.ivCreatorProfile.load(item.creatorProfileImageUrl) {
|
|
||||||
crossfade(true)
|
|
||||||
placeholder(R.drawable.ic_place_holder)
|
|
||||||
transformations(CircleCropTransformation())
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvTitle.text = item.title
|
|
||||||
binding.tvCreatorNickname.text = item.creatorNickname
|
|
||||||
|
|
||||||
binding.root.setOnClickListener { onClickItem(item.seriesId) }
|
|
||||||
binding.tvTitle.setOnClickListener { onClickCreator(item.creatorId) }
|
|
||||||
binding.tvCreatorNickname.setOnClickListener { onClickCreator(item.creatorId) }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemAudioContentMainNewSeriesBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetRecommendSeriesListResponse>) {
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,89 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.origianl_audio_drama
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.View
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import com.bumptech.glide.Glide
|
|
||||||
import com.bumptech.glide.load.resource.bitmap.CenterCrop
|
|
||||||
import com.bumptech.glide.load.resource.bitmap.RoundedCorners
|
|
||||||
import com.bumptech.glide.request.RequestOptions
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemSeriesOriginalAudioDramaBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
|
|
||||||
class AudioContentMainTabSeriesOriginalAudioDramaAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainTabSeriesOriginalAudioDramaAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
val items = mutableListOf<GetSeriesListResponse.SeriesListItem>()
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemSeriesOriginalAudioDramaBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
@SuppressLint("SetTextI18n")
|
|
||||||
fun bind(item: GetSeriesListResponse.SeriesListItem) {
|
|
||||||
Glide
|
|
||||||
.with(context)
|
|
||||||
.load(item.coverImage)
|
|
||||||
.apply(
|
|
||||||
RequestOptions().transform(
|
|
||||||
CenterCrop(),
|
|
||||||
RoundedCorners(5f.dpToPx().toInt())
|
|
||||||
)
|
|
||||||
)
|
|
||||||
.into(binding.ivCover)
|
|
||||||
|
|
||||||
binding.tvTitle.text = item.title
|
|
||||||
binding.tvSeriesContentCount.text = "총 ${item.numberOfContent}화"
|
|
||||||
binding.tvNew.visibility = if (item.isNew) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvPopular.visibility = if (item.isPopular) {
|
|
||||||
View.VISIBLE
|
|
||||||
} else {
|
|
||||||
View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
if (item.isComplete) {
|
|
||||||
binding.tvNew.visibility = View.GONE
|
|
||||||
binding.tvComplete.visibility = View.VISIBLE
|
|
||||||
} else {
|
|
||||||
binding.tvComplete.visibility = View.GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.root.setOnClickListener { onClickItem(item.seriesId) }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemSeriesOriginalAudioDramaBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun getItemCount() = items.count()
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetSeriesListResponse.SeriesListItem>) {
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isVisibleRecyclerView(): Boolean {
|
|
||||||
return items.isNotEmpty()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,109 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.origianl_audio_drama
|
|
||||||
|
|
||||||
import android.content.Intent
|
|
||||||
import android.os.Bundle
|
|
||||||
import androidx.recyclerview.widget.GridLayoutManager
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.SeriesListAdapter
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.detail.SeriesDetailActivity
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseActivity
|
|
||||||
import kr.co.vividnext.sodalive.common.Constants
|
|
||||||
import kr.co.vividnext.sodalive.common.DifferentSpacingItemDecoration
|
|
||||||
import kr.co.vividnext.sodalive.common.LoadingDialog
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ActivityOriginalAudioDramaContentAllBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
import org.koin.android.ext.android.inject
|
|
||||||
import kotlin.math.roundToInt
|
|
||||||
|
|
||||||
class OriginalAudioDramaContentAllActivity :
|
|
||||||
BaseActivity<ActivityOriginalAudioDramaContentAllBinding>(
|
|
||||||
ActivityOriginalAudioDramaContentAllBinding::inflate
|
|
||||||
) {
|
|
||||||
private val viewModel: OriginalAudioDramaContentAllViewModel by inject()
|
|
||||||
|
|
||||||
private lateinit var loadingDialog: LoadingDialog
|
|
||||||
private lateinit var adapter: SeriesListAdapter
|
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
|
||||||
super.onCreate(savedInstanceState)
|
|
||||||
bindData()
|
|
||||||
|
|
||||||
viewModel.getOriginalAudioDramaList()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun setupView() {
|
|
||||||
loadingDialog = LoadingDialog(this, layoutInflater)
|
|
||||||
binding.toolbar.tvBack.text = "오리지널 오디오 드라마"
|
|
||||||
binding.toolbar.tvBack.setOnClickListener { finish() }
|
|
||||||
|
|
||||||
setupOriginalAudioDramaListView()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setupOriginalAudioDramaListView() {
|
|
||||||
val spacing = 13.3f.dpToPx().roundToInt()
|
|
||||||
|
|
||||||
adapter = SeriesListAdapter(
|
|
||||||
itemWidth = ((screenWidth - spacing * 3) / 2f).roundToInt(),
|
|
||||||
onClickItem = {
|
|
||||||
startActivity(
|
|
||||||
Intent(applicationContext, SeriesDetailActivity::class.java).apply {
|
|
||||||
putExtra(Constants.EXTRA_SERIES_ID, it)
|
|
||||||
}
|
|
||||||
)
|
|
||||||
},
|
|
||||||
onClickCreator = {},
|
|
||||||
isVisibleCreator = false
|
|
||||||
)
|
|
||||||
|
|
||||||
val spanCount = 2
|
|
||||||
val recyclerView = binding.rvSeries
|
|
||||||
recyclerView.layoutManager = GridLayoutManager(this, spanCount)
|
|
||||||
|
|
||||||
recyclerView.addItemDecoration(
|
|
||||||
DifferentSpacingItemDecoration(
|
|
||||||
spanCount = spanCount,
|
|
||||||
horizontalSpacing = spacing,
|
|
||||||
verticalSpacing = spacing,
|
|
||||||
includeEdge = true
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
recyclerView.addOnScrollListener(object : RecyclerView.OnScrollListener() {
|
|
||||||
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
|
|
||||||
super.onScrolled(recyclerView, dx, dy)
|
|
||||||
|
|
||||||
val lastVisibleItemPosition = (recyclerView.layoutManager as LinearLayoutManager?)!!
|
|
||||||
.findLastCompletelyVisibleItemPosition()
|
|
||||||
val itemTotalCount = recyclerView.adapter!!.itemCount - 1
|
|
||||||
|
|
||||||
// 스크롤이 끝에 도달했는지 확인
|
|
||||||
if (!recyclerView.canScrollVertically(1) &&
|
|
||||||
lastVisibleItemPosition == itemTotalCount
|
|
||||||
) {
|
|
||||||
viewModel.getOriginalAudioDramaList()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
recyclerView.adapter = adapter
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun bindData() {
|
|
||||||
viewModel.toastLiveData.observe(this) {
|
|
||||||
it?.let { showToast(it) }
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.isLoading.observe(this) {
|
|
||||||
if (it) {
|
|
||||||
loadingDialog.show(screenWidth)
|
|
||||||
} else {
|
|
||||||
loadingDialog.dismiss()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
viewModel.originalAudioDramaLiveData.observe(this) {
|
|
||||||
adapter.addItems(it)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,19 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.origianl_audio_drama
|
|
||||||
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.AudioContentApi
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
import kr.co.vividnext.sodalive.settings.ContentType
|
|
||||||
|
|
||||||
class OriginalAudioDramaContentAllRepository(private val api: AudioContentApi) {
|
|
||||||
fun getOriginalAudioDramaList(
|
|
||||||
page: Int,
|
|
||||||
size: Int,
|
|
||||||
token: String
|
|
||||||
) = api.getOriginalAudioDramaList(
|
|
||||||
isAdultContentVisible = SharedPreferenceManager.isAdultContentVisible,
|
|
||||||
contentType = ContentType.values()[SharedPreferenceManager.contentPreference],
|
|
||||||
page = page - 1,
|
|
||||||
size = size,
|
|
||||||
authHeader = token
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,74 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.origianl_audio_drama
|
|
||||||
|
|
||||||
import androidx.lifecycle.LiveData
|
|
||||||
import androidx.lifecycle.MutableLiveData
|
|
||||||
import com.orhanobut.logger.Logger
|
|
||||||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
|
||||||
import io.reactivex.rxjava3.schedulers.Schedulers
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.base.BaseViewModel
|
|
||||||
import kr.co.vividnext.sodalive.common.SharedPreferenceManager
|
|
||||||
|
|
||||||
class OriginalAudioDramaContentAllViewModel(
|
|
||||||
private val repository: OriginalAudioDramaContentAllRepository
|
|
||||||
) : BaseViewModel() {
|
|
||||||
private val _toastLiveData = MutableLiveData<String?>()
|
|
||||||
val toastLiveData: LiveData<String?>
|
|
||||||
get() = _toastLiveData
|
|
||||||
|
|
||||||
private var _isLoading = MutableLiveData(false)
|
|
||||||
val isLoading: LiveData<Boolean>
|
|
||||||
get() = _isLoading
|
|
||||||
|
|
||||||
private var _originalAudioDramaLiveData =
|
|
||||||
MutableLiveData<List<GetSeriesListResponse.SeriesListItem>>()
|
|
||||||
val originalAudioDramaLiveData: LiveData<List<GetSeriesListResponse.SeriesListItem>>
|
|
||||||
get() = _originalAudioDramaLiveData
|
|
||||||
|
|
||||||
var isLast = false
|
|
||||||
var page = 1
|
|
||||||
private val size = 15
|
|
||||||
|
|
||||||
fun getOriginalAudioDramaList() {
|
|
||||||
if (!_isLoading.value!! && !isLast) {
|
|
||||||
_isLoading.value = true
|
|
||||||
|
|
||||||
compositeDisposable.add(
|
|
||||||
repository.getOriginalAudioDramaList(
|
|
||||||
page = page,
|
|
||||||
size = size,
|
|
||||||
token = "Bearer ${SharedPreferenceManager.token}"
|
|
||||||
)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(
|
|
||||||
{
|
|
||||||
if (it.success && it.data != null) {
|
|
||||||
page += 1
|
|
||||||
|
|
||||||
if (it.data.items.isNotEmpty()) {
|
|
||||||
_originalAudioDramaLiveData.value = it.data.items
|
|
||||||
} else {
|
|
||||||
isLast = true
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (it.message != null) {
|
|
||||||
_toastLiveData.value = it.message
|
|
||||||
} else {
|
|
||||||
_toastLiveData.value = "알 수 없는 오류가 발생했습니다. 다시 시도해 주세요."
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_isLoading.value = false
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_isLoading.value = false
|
|
||||||
it.message?.let { message -> Logger.e(message) }
|
|
||||||
_toastLiveData.postValue("알 수 없는 오류가 발생했습니다. 다시 시도해 주세요.")
|
|
||||||
}
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,57 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.rank_series
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import coil.load
|
|
||||||
import coil.transform.RoundedCornersTransformation
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.series.GetSeriesListResponse
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainSeriesRankingBinding
|
|
||||||
import kr.co.vividnext.sodalive.extensions.dpToPx
|
|
||||||
|
|
||||||
class AudioContentMainSeriesRankingAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainSeriesRankingAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
val items = mutableListOf<GetSeriesListResponse.SeriesListItem>()
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val binding: ItemAudioContentMainSeriesRankingBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
@SuppressLint("SetTextI18n")
|
|
||||||
fun bind(item: GetSeriesListResponse.SeriesListItem, index: Int) {
|
|
||||||
binding.root.setOnClickListener { onClickItem(item.seriesId) }
|
|
||||||
binding.tvTitle.text = item.title
|
|
||||||
binding.tvRank.text = "${index + 1}"
|
|
||||||
binding.tvNickname.text = item.creator.nickname
|
|
||||||
|
|
||||||
binding.ivCover.load(item.coverImage) {
|
|
||||||
crossfade(true)
|
|
||||||
placeholder(R.drawable.bg_placeholder)
|
|
||||||
transformations(RoundedCornersTransformation(5f.dpToPx()))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
ItemAudioContentMainSeriesRankingBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position], index = position)
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetSeriesListResponse.SeriesListItem>) {
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,73 +0,0 @@
|
|||||||
package kr.co.vividnext.sodalive.audio_content.main.v2.series.recommend_by_genre
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
|
||||||
import android.content.Context
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import android.view.ViewGroup
|
|
||||||
import androidx.core.content.ContextCompat
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
|
||||||
import kr.co.vividnext.sodalive.R
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.GetSeriesGenreListResponse
|
|
||||||
import kr.co.vividnext.sodalive.databinding.ItemAudioContentMainNewContentThemeBinding
|
|
||||||
|
|
||||||
class AudioContentMainRecommendSeriesGenreAdapter(
|
|
||||||
private val onClickItem: (Long) -> Unit
|
|
||||||
) : RecyclerView.Adapter<AudioContentMainRecommendSeriesGenreAdapter.ViewHolder>() {
|
|
||||||
|
|
||||||
private var items = mutableListOf<GetSeriesGenreListResponse>()
|
|
||||||
private var selectedGenreId = 0L
|
|
||||||
|
|
||||||
inner class ViewHolder(
|
|
||||||
private val context: Context,
|
|
||||||
private val binding: ItemAudioContentMainNewContentThemeBinding
|
|
||||||
) : RecyclerView.ViewHolder(binding.root) {
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun bind(item: GetSeriesGenreListResponse) {
|
|
||||||
if (item.id == selectedGenreId) {
|
|
||||||
binding.tvTheme.setBackgroundResource(
|
|
||||||
R.drawable.bg_round_corner_16_7_transparent_3bb9f1
|
|
||||||
)
|
|
||||||
binding.tvTheme.setTextColor(ContextCompat.getColor(context, R.color.color_3bb9f1))
|
|
||||||
} else {
|
|
||||||
binding.tvTheme.setBackgroundResource(
|
|
||||||
R.drawable.bg_round_corner_16_7_transparent_777777
|
|
||||||
)
|
|
||||||
binding.tvTheme.setTextColor(ContextCompat.getColor(context, R.color.color_777777))
|
|
||||||
}
|
|
||||||
|
|
||||||
binding.tvTheme.text = item.genre
|
|
||||||
binding.root.setOnClickListener {
|
|
||||||
onClickItem(item.id)
|
|
||||||
selectedGenreId = item.id
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("NotifyDataSetChanged")
|
|
||||||
fun addItems(items: List<GetSeriesGenreListResponse>) {
|
|
||||||
this.selectedGenreId = if (items.isNotEmpty()) {
|
|
||||||
items[0].id
|
|
||||||
} else {
|
|
||||||
0
|
|
||||||
}
|
|
||||||
this.items.clear()
|
|
||||||
this.items.addAll(items)
|
|
||||||
notifyDataSetChanged()
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int) = ViewHolder(
|
|
||||||
parent.context,
|
|
||||||
ItemAudioContentMainNewContentThemeBinding.inflate(
|
|
||||||
LayoutInflater.from(parent.context),
|
|
||||||
parent,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
override fun getItemCount() = items.size
|
|
||||||
|
|
||||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
|
||||||
holder.bind(items[position])
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -14,36 +14,9 @@ import kr.co.vividnext.sodalive.audio_content.category.CategoryApi
|
|||||||
import kr.co.vividnext.sodalive.audio_content.comment.AudioContentCommentListViewModel
|
import kr.co.vividnext.sodalive.audio_content.comment.AudioContentCommentListViewModel
|
||||||
import kr.co.vividnext.sodalive.audio_content.comment.AudioContentCommentReplyViewModel
|
import kr.co.vividnext.sodalive.audio_content.comment.AudioContentCommentReplyViewModel
|
||||||
import kr.co.vividnext.sodalive.audio_content.comment.AudioContentCommentRepository
|
import kr.co.vividnext.sodalive.audio_content.comment.AudioContentCommentRepository
|
||||||
import kr.co.vividnext.sodalive.audio_content.curation.AudioContentCurationViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.db.PlaybackTrackingDao
|
import kr.co.vividnext.sodalive.audio_content.db.PlaybackTrackingDao
|
||||||
import kr.co.vividnext.sodalive.audio_content.db.PlaybackTrackingDatabase
|
import kr.co.vividnext.sodalive.audio_content.db.PlaybackTrackingDatabase
|
||||||
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailViewModel
|
import kr.co.vividnext.sodalive.audio_content.detail.AudioContentDetailViewModel
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.banner.AudioContentMainBannerViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.curation.AudioContentMainCurationViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.new_content.AudioContentMainNewContentViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.order.AudioContentMainOrderListViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ranking.AudioContentMainCreatorRankingViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.ranking.AudioContentMainRankingViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.recommend_series.AudioContentMainRecommendSeriesViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.alarm.AudioContentMainTabAlarmRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.alarm.AudioContentMainTabAlarmViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.alarm.all.AlarmContentAllViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.asmr.AudioContentMainTabAsmrRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.asmr.AudioContentMainTabAsmrViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.content.AudioContentMainTabContentRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.content.AudioContentMainTabContentViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.free.AudioContentMainTabFreeRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.free.AudioContentMainTabFreeViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.free.introduce_creator.IntroduceCreatorViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.home.AudioContentMainTabHomeRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.home.AudioContentMainTabHomeViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.replay.AudioContentMainTabReplayRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.replay.AudioContentMainTabReplayViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.AudioContentMainTabSeriesRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.AudioContentMainTabSeriesViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.completed.CompletedSeriesViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.origianl_audio_drama.OriginalAudioDramaContentAllRepository
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.main.v2.series.origianl_audio_drama.OriginalAudioDramaContentAllViewModel
|
|
||||||
import kr.co.vividnext.sodalive.audio_content.modify.AudioContentModifyViewModel
|
import kr.co.vividnext.sodalive.audio_content.modify.AudioContentModifyViewModel
|
||||||
import kr.co.vividnext.sodalive.audio_content.order.AudioContentOrderListViewModel
|
import kr.co.vividnext.sodalive.audio_content.order.AudioContentOrderListViewModel
|
||||||
import kr.co.vividnext.sodalive.audio_content.player.AudioContentGenerateUrlRepository
|
import kr.co.vividnext.sodalive.audio_content.player.AudioContentGenerateUrlRepository
|
||||||
@@ -82,6 +55,7 @@ import kr.co.vividnext.sodalive.chat.character.newcharacters.NewCharactersReposi
|
|||||||
import kr.co.vividnext.sodalive.chat.original.OriginalWorkApi
|
import kr.co.vividnext.sodalive.chat.original.OriginalWorkApi
|
||||||
import kr.co.vividnext.sodalive.chat.original.OriginalWorkRepository
|
import kr.co.vividnext.sodalive.chat.original.OriginalWorkRepository
|
||||||
import kr.co.vividnext.sodalive.chat.original.OriginalWorkViewModel
|
import kr.co.vividnext.sodalive.chat.original.OriginalWorkViewModel
|
||||||
|
import kr.co.vividnext.sodalive.chat.original.detail.OriginalWorkDetailViewModel
|
||||||
import kr.co.vividnext.sodalive.chat.talk.TalkApi
|
import kr.co.vividnext.sodalive.chat.talk.TalkApi
|
||||||
import kr.co.vividnext.sodalive.chat.talk.TalkTabRepository
|
import kr.co.vividnext.sodalive.chat.talk.TalkTabRepository
|
||||||
import kr.co.vividnext.sodalive.chat.talk.TalkTabViewModel
|
import kr.co.vividnext.sodalive.chat.talk.TalkTabViewModel
|
||||||
@@ -310,12 +284,6 @@ class AppDI(private val context: Context, isDebugMode: Boolean) {
|
|||||||
viewModel { SignOutViewModel(get()) }
|
viewModel { SignOutViewModel(get()) }
|
||||||
viewModel { TextMessageDetailViewModel(get()) }
|
viewModel { TextMessageDetailViewModel(get()) }
|
||||||
viewModel { LiveReservationStatusViewModel(get()) }
|
viewModel { LiveReservationStatusViewModel(get()) }
|
||||||
viewModel { AudioContentMainBannerViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainRankingViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainCurationViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainOrderListViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainNewContentViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainRecommendSeriesViewModel(get()) }
|
|
||||||
viewModel { AudioContentViewModel(get()) }
|
viewModel { AudioContentViewModel(get()) }
|
||||||
viewModel { AudioContentOrderListViewModel(get()) }
|
viewModel { AudioContentOrderListViewModel(get()) }
|
||||||
viewModel { AudioContentUploadViewModel(get()) }
|
viewModel { AudioContentUploadViewModel(get()) }
|
||||||
@@ -330,7 +298,6 @@ class AppDI(private val context: Context, isDebugMode: Boolean) {
|
|||||||
viewModel { NicknameUpdateViewModel(get()) }
|
viewModel { NicknameUpdateViewModel(get()) }
|
||||||
viewModel { MemberTagViewModel(get()) }
|
viewModel { MemberTagViewModel(get()) }
|
||||||
viewModel { UserProfileDonationAllViewModel(get(), get()) }
|
viewModel { UserProfileDonationAllViewModel(get(), get()) }
|
||||||
viewModel { AudioContentCurationViewModel(get()) }
|
|
||||||
viewModel { AudioContentNewAllViewModel(get()) }
|
viewModel { AudioContentNewAllViewModel(get()) }
|
||||||
viewModel { AudioContentAllByThemeViewModel(get()) }
|
viewModel { AudioContentAllByThemeViewModel(get()) }
|
||||||
viewModel { AudioContentRankingAllViewModel(get()) }
|
viewModel { AudioContentRankingAllViewModel(get()) }
|
||||||
@@ -353,18 +320,6 @@ class AppDI(private val context: Context, isDebugMode: Boolean) {
|
|||||||
viewModel { AuditionViewModel(get(), get()) }
|
viewModel { AuditionViewModel(get(), get()) }
|
||||||
viewModel { AuditionDetailViewModel(get()) }
|
viewModel { AuditionDetailViewModel(get()) }
|
||||||
viewModel { AuditionRoleDetailViewModel(get()) }
|
viewModel { AuditionRoleDetailViewModel(get()) }
|
||||||
viewModel { AudioContentMainCreatorRankingViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainTabHomeViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainTabSeriesViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainTabContentViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainTabAlarmViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainTabAsmrViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainTabReplayViewModel(get()) }
|
|
||||||
viewModel { AudioContentMainTabFreeViewModel(get()) }
|
|
||||||
viewModel { OriginalAudioDramaContentAllViewModel(get()) }
|
|
||||||
viewModel { IntroduceCreatorViewModel(get()) }
|
|
||||||
viewModel { CompletedSeriesViewModel(get()) }
|
|
||||||
viewModel { AlarmContentAllViewModel(get()) }
|
|
||||||
viewModel { SearchViewModel(get()) }
|
viewModel { SearchViewModel(get()) }
|
||||||
viewModel { PointStatusViewModel(get()) }
|
viewModel { PointStatusViewModel(get()) }
|
||||||
viewModel { HomeViewModel(get(), get()) }
|
viewModel { HomeViewModel(get(), get()) }
|
||||||
@@ -376,7 +331,7 @@ class AppDI(private val context: Context, isDebugMode: Boolean) {
|
|||||||
viewModel { CharacterCommentReplyViewModel(get()) }
|
viewModel { CharacterCommentReplyViewModel(get()) }
|
||||||
viewModel { NewCharactersAllViewModel(get()) }
|
viewModel { NewCharactersAllViewModel(get()) }
|
||||||
viewModel { OriginalWorkViewModel(get()) }
|
viewModel { OriginalWorkViewModel(get()) }
|
||||||
viewModel { kr.co.vividnext.sodalive.chat.original.detail.OriginalWorkDetailViewModel(get()) }
|
viewModel { OriginalWorkDetailViewModel(get()) }
|
||||||
}
|
}
|
||||||
|
|
||||||
private val repositoryModule = module {
|
private val repositoryModule = module {
|
||||||
@@ -394,7 +349,7 @@ class AppDI(private val context: Context, isDebugMode: Boolean) {
|
|||||||
factory { ExplorerRepository(get()) }
|
factory { ExplorerRepository(get()) }
|
||||||
factory { MessageRepository(get()) }
|
factory { MessageRepository(get()) }
|
||||||
factory { NoticeRepository(get()) }
|
factory { NoticeRepository(get()) }
|
||||||
factory { AudioContentRepository(get(), get(), get()) }
|
factory { AudioContentRepository(get(), get()) }
|
||||||
factory { AudioContentCommentRepository(get()) }
|
factory { AudioContentCommentRepository(get()) }
|
||||||
factory { PlaybackTrackingRepository(get()) }
|
factory { PlaybackTrackingRepository(get()) }
|
||||||
factory { FollowingCreatorRepository(get()) }
|
factory { FollowingCreatorRepository(get()) }
|
||||||
@@ -408,14 +363,6 @@ class AppDI(private val context: Context, isDebugMode: Boolean) {
|
|||||||
factory { AudioContentPlaylistRepository(get()) }
|
factory { AudioContentPlaylistRepository(get()) }
|
||||||
factory { AudioContentGenerateUrlRepository(get()) }
|
factory { AudioContentGenerateUrlRepository(get()) }
|
||||||
factory { AuditionRepository(get()) }
|
factory { AuditionRepository(get()) }
|
||||||
factory { AudioContentMainTabHomeRepository(get()) }
|
|
||||||
factory { AudioContentMainTabSeriesRepository(get()) }
|
|
||||||
factory { AudioContentMainTabContentRepository(get()) }
|
|
||||||
factory { AudioContentMainTabAlarmRepository(get()) }
|
|
||||||
factory { AudioContentMainTabAsmrRepository(get()) }
|
|
||||||
factory { AudioContentMainTabReplayRepository(get()) }
|
|
||||||
factory { AudioContentMainTabFreeRepository(get()) }
|
|
||||||
factory { OriginalAudioDramaContentAllRepository(get()) }
|
|
||||||
factory { AdTrackingRepository(get()) }
|
factory { AdTrackingRepository(get()) }
|
||||||
factory { SearchRepository(get()) }
|
factory { SearchRepository(get()) }
|
||||||
factory { UserEventRepository(get()) }
|
factory { UserEventRepository(get()) }
|
||||||
|
|||||||
Reference in New Issue
Block a user