feat(creator): 채널 홈 시리즈, 커뮤니티, 팬 Talk 섹션을 재구성한다
This commit is contained in:
@@ -82,11 +82,8 @@ data class CreatorChannelSeriesResponse(
|
||||
@SerializedName("seriesId") val seriesId: Long,
|
||||
@SerializedName("title") val title: String,
|
||||
@SerializedName("coverImageUrl") val coverImageUrl: String,
|
||||
@SerializedName("publishedDaysOfWeek") val publishedDaysOfWeek: String,
|
||||
@SerializedName("isComplete") val isComplete: Boolean,
|
||||
@SerializedName("numberOfContent") val numberOfContent: Int,
|
||||
@SerializedName("isNew") val isNew: Boolean,
|
||||
@SerializedName("isPopular") val isPopular: Boolean,
|
||||
@SerializedName("isOriginal") val isOriginal: Boolean
|
||||
)
|
||||
|
||||
|
||||
@@ -18,7 +18,7 @@ fun CreatorChannelHomeResponse.toUiContent(): CreatorChannelHomeUiState.Content
|
||||
audioContents.takeIf { it.isNotEmpty() }?.let { add(CreatorChannelHomeSection.AudioContents(it)) }
|
||||
series.takeIf { it.isNotEmpty() }?.let { add(CreatorChannelHomeSection.Series(it)) }
|
||||
communities.takeIf { it.isNotEmpty() }?.let { add(CreatorChannelHomeSection.Communities(it)) }
|
||||
fanTalk.takeIf { it.totalCount > 0 || it.latestFanTalk != null }?.let { add(CreatorChannelHomeSection.FanTalk(it)) }
|
||||
add(CreatorChannelHomeSection.FanTalk(fanTalk))
|
||||
introduce.takeIf { it.isNotBlank() }?.let { add(CreatorChannelHomeSection.Introduce(it)) }
|
||||
add(CreatorChannelHomeSection.Activity(activity))
|
||||
sns.toUiItems().takeIf { it.isNotEmpty() }?.let { add(CreatorChannelHomeSection.Sns(it)) }
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
package kr.co.vividnext.sodalive.v2.creator.channel.ui
|
||||
|
||||
import android.content.Context
|
||||
import android.graphics.Outline
|
||||
import android.util.AttributeSet
|
||||
import android.view.View
|
||||
import android.view.ViewOutlineProvider
|
||||
import android.widget.LinearLayout
|
||||
import kr.co.vividnext.sodalive.R
|
||||
|
||||
class CreatorChannelFanTalkCardView @JvmOverloads constructor(
|
||||
context: Context,
|
||||
attrs: AttributeSet? = null,
|
||||
defStyleAttr: Int = 0
|
||||
) : LinearLayout(context, attrs, defStyleAttr) {
|
||||
|
||||
init {
|
||||
clipToOutline = true
|
||||
outlineProvider = object : ViewOutlineProvider() {
|
||||
override fun getOutline(view: View, outline: Outline) {
|
||||
outline.setRoundRect(0, 0, view.width, view.height, resources.getDimension(R.dimen.radius_14))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -5,7 +5,6 @@ import android.view.Gravity
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import android.widget.HorizontalScrollView
|
||||
import android.widget.ImageView
|
||||
import android.widget.LinearLayout
|
||||
import android.widget.TextView
|
||||
@@ -18,11 +17,17 @@ import androidx.recyclerview.widget.GridLayoutManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import kr.co.vividnext.sodalive.R
|
||||
import coil.transform.CircleCropTransformation
|
||||
import kr.co.vividnext.sodalive.common.image.BlurTransformation
|
||||
import kr.co.vividnext.sodalive.extensions.loadUrl
|
||||
import kr.co.vividnext.sodalive.extensions.moneyFormat
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.data.CreatorChannelAudioContentResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.data.CreatorChannelCommunityPostResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.data.CreatorChannelScheduleResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.data.CreatorChannelSeriesResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.model.CreatorChannelHomeSection
|
||||
import kr.co.vividnext.sodalive.v2.widget.feed.FeedCommunityView
|
||||
import kr.co.vividnext.sodalive.v2.widget.feed.FeedItem
|
||||
import kr.co.vividnext.sodalive.v2.widget.feed.FeedSize
|
||||
import java.text.SimpleDateFormat
|
||||
import java.util.Locale
|
||||
import java.util.TimeZone
|
||||
@@ -30,7 +35,8 @@ import kotlin.math.roundToInt
|
||||
|
||||
class CreatorChannelHomeSectionAdapter(
|
||||
private val onScheduleClick: (CreatorChannelScheduleResponse) -> Unit = {},
|
||||
private val onAudioContentClick: (CreatorChannelAudioContentResponse) -> Unit = {}
|
||||
private val onAudioContentClick: (CreatorChannelAudioContentResponse) -> Unit = {},
|
||||
private val onSeriesClick: (CreatorChannelSeriesResponse) -> Unit = {}
|
||||
) : RecyclerView.Adapter<CreatorChannelHomeSectionAdapter.SectionViewHolder>() {
|
||||
|
||||
private var items: List<CreatorChannelHomeSection> = emptyList()
|
||||
@@ -44,7 +50,7 @@ class CreatorChannelHomeSectionAdapter(
|
||||
|
||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): SectionViewHolder {
|
||||
val view = LayoutInflater.from(parent.context).inflate(viewType, parent, false)
|
||||
return SectionViewHolder(view, onScheduleClick, onAudioContentClick)
|
||||
return SectionViewHolder(view, onScheduleClick, onAudioContentClick, onSeriesClick)
|
||||
}
|
||||
|
||||
override fun onBindViewHolder(holder: SectionViewHolder, position: Int) {
|
||||
@@ -56,7 +62,8 @@ class CreatorChannelHomeSectionAdapter(
|
||||
class SectionViewHolder(
|
||||
view: View,
|
||||
private val onScheduleClick: (CreatorChannelScheduleResponse) -> Unit,
|
||||
private val onAudioContentClick: (CreatorChannelAudioContentResponse) -> Unit
|
||||
private val onAudioContentClick: (CreatorChannelAudioContentResponse) -> Unit,
|
||||
private val onSeriesClick: (CreatorChannelSeriesResponse) -> Unit
|
||||
) : RecyclerView.ViewHolder(view) {
|
||||
private val title: TextView? = view.findViewById(R.id.tv_section_title)
|
||||
private val sectionItems: LinearLayout? = view.findViewById(R.id.ll_section_items)
|
||||
@@ -74,6 +81,15 @@ class CreatorChannelHomeSectionAdapter(
|
||||
private val scheduleTimeline: LinearLayout? = view.findViewById(R.id.ll_schedule_timeline)
|
||||
private val scheduleItems: LinearLayout? = view.findViewById(R.id.ll_schedule_items)
|
||||
private val audioContentsRecyclerView: RecyclerView? = view.findViewById(R.id.rv_audio_contents)
|
||||
private val seriesItems: LinearLayout? = view.findViewById(R.id.ll_series_items)
|
||||
private val communityItems: LinearLayout? = view.findViewById(R.id.ll_community_items)
|
||||
private val fanTalkCard: View? = view.findViewById(R.id.layout_fantalk_card)
|
||||
private val fanTalkTotalRow: View? = view.findViewById(R.id.layout_fantalk_total_row)
|
||||
private val fanTalkLatestRow: View? = view.findViewById(R.id.layout_fantalk_latest_row)
|
||||
private val fanTalkEmpty: View? = view.findViewById(R.id.layout_fantalk_empty)
|
||||
private val fanTalkTotalCount: TextView? = view.findViewById(R.id.tv_fantalk_total_count)
|
||||
private val fanTalkProfile: ImageView? = view.findViewById(R.id.iv_fantalk_profile)
|
||||
private val fanTalkContent: TextView? = view.findViewById(R.id.tv_fantalk_content)
|
||||
private val audioContentGridAdapter = AudioContentGridAdapter(
|
||||
itemWidth = calculateCreatorChannelAudioItemWidthDp(itemView.resources.configuration.screenWidthDp).dp(),
|
||||
onAudioContentClick = onAudioContentClick
|
||||
@@ -90,6 +106,8 @@ class CreatorChannelHomeSectionAdapter(
|
||||
noticeItems?.removeAllViews()
|
||||
scheduleTimeline?.removeAllViews()
|
||||
scheduleItems?.removeAllViews()
|
||||
seriesItems?.removeAllViews()
|
||||
communityItems?.removeAllViews()
|
||||
when (item) {
|
||||
is CreatorChannelHomeSection.CurrentLive -> bindCurrentLive(item)
|
||||
is CreatorChannelHomeSection.LatestAudioContent -> bindLatestAudioContent(item)
|
||||
@@ -256,54 +274,118 @@ class CreatorChannelHomeSectionAdapter(
|
||||
}
|
||||
|
||||
private fun bindSeries(item: CreatorChannelHomeSection.Series) {
|
||||
val row = createHorizontalRow()
|
||||
item.series.forEach { series ->
|
||||
row.addView(
|
||||
createContentTile(
|
||||
title = series.title,
|
||||
body = itemView.context.getString(
|
||||
R.string.creator_channel_series_summary,
|
||||
series.numberOfContent,
|
||||
series.publishedDaysOfWeek
|
||||
),
|
||||
imageUrl = series.coverImageUrl,
|
||||
imageWidth = 163.dp(),
|
||||
imageHeight = 230.dp()
|
||||
)
|
||||
val visibleSeries = item.series.take(MAX_SERIES_ITEM_COUNT)
|
||||
visibleSeries.forEachIndexed { index, series ->
|
||||
val seriesWidthDp = calculateCreatorChannelSeriesCardWidthDp(itemView.resources.configuration.screenWidthDp)
|
||||
val row = LayoutInflater.from(itemView.context).inflate(
|
||||
R.layout.item_creator_channel_home_series_content,
|
||||
seriesItems,
|
||||
false
|
||||
)
|
||||
row.layoutParams = LinearLayout.LayoutParams(
|
||||
seriesWidthDp.dp(),
|
||||
LinearLayout.LayoutParams.WRAP_CONTENT
|
||||
).apply {
|
||||
marginEnd = if (index == visibleSeries.lastIndex) 0 else 4.dp()
|
||||
}
|
||||
(row as CreatorChannelHomeSeriesCardView).apply {
|
||||
setThumbnailSize(seriesWidthDp, calculateCreatorChannelSeriesCardHeightDp(seriesWidthDp))
|
||||
bind(series)
|
||||
}
|
||||
row.setOnClickListener { onSeriesClick(series) }
|
||||
seriesItems?.addView(row)
|
||||
}
|
||||
sectionItems?.addView(createHorizontalScrollRow(row))
|
||||
}
|
||||
|
||||
private fun bindCommunities(item: CreatorChannelHomeSection.Communities) {
|
||||
item.communities.forEach { community ->
|
||||
addFeedCard(
|
||||
title = community.content,
|
||||
body = itemView.context.getString(
|
||||
R.string.creator_channel_community_summary,
|
||||
community.creatorNickname,
|
||||
community.likeCount,
|
||||
community.commentCount
|
||||
),
|
||||
imageUrl = community.imageUrl
|
||||
val visibleCommunities = item.communities.take(MAX_COMMUNITY_ITEM_COUNT)
|
||||
visibleCommunities.forEachIndexed { index, community ->
|
||||
val communityWidthDp = calculateCreatorChannelCommunityCardWidthDp(
|
||||
itemView.resources.configuration.screenWidthDp
|
||||
)
|
||||
val row = LayoutInflater.from(itemView.context).inflate(
|
||||
R.layout.view_feed_community,
|
||||
communityItems,
|
||||
false
|
||||
)
|
||||
(row as FeedCommunityView).apply {
|
||||
setFeedSize(
|
||||
FeedSize(
|
||||
rootWidthDp = communityWidthDp
|
||||
)
|
||||
)
|
||||
setHideEmptyTextRows(true)
|
||||
bind(community.toFeedCommunityItem())
|
||||
}
|
||||
bindCommunityImages(row, community)
|
||||
row.layoutParams = LinearLayout.LayoutParams(
|
||||
communityWidthDp.dp(),
|
||||
LinearLayout.LayoutParams.WRAP_CONTENT
|
||||
).apply {
|
||||
bottomMargin = if (index == visibleCommunities.lastIndex) 0 else 8.dp()
|
||||
}
|
||||
communityItems?.addView(row)
|
||||
}
|
||||
}
|
||||
|
||||
private fun bindFanTalk(item: CreatorChannelHomeSection.FanTalk) {
|
||||
item.fanTalk.latestFanTalk?.let { fanTalk ->
|
||||
addCommentCard(
|
||||
title = fanTalk.content,
|
||||
body = itemView.context.getString(
|
||||
R.string.creator_channel_fantalk_summary,
|
||||
fanTalk.nickname,
|
||||
item.fanTalk.totalCount
|
||||
),
|
||||
imageUrl = fanTalk.profileImageUrl
|
||||
)
|
||||
fanTalkCard?.layoutParams = fanTalkCard.layoutParams?.apply {
|
||||
width = calculateCreatorChannelFanTalkCardWidthDp(itemView.resources.configuration.screenWidthDp).dp()
|
||||
}
|
||||
fanTalkTotalCount?.text = item.fanTalk.totalCount.toString()
|
||||
val fanTalk = item.fanTalk.latestFanTalk
|
||||
fanTalkTotalRow?.isVisible = fanTalk != null && item.fanTalk.totalCount > 0
|
||||
fanTalkLatestRow?.isVisible = fanTalk != null && item.fanTalk.totalCount > 0
|
||||
fanTalkEmpty?.isVisible = fanTalk == null || item.fanTalk.totalCount <= 0
|
||||
if (fanTalk != null) {
|
||||
fanTalkContent?.text = fanTalk.content
|
||||
fanTalkProfile?.loadUrl(fanTalk.profileImageUrl) {
|
||||
placeholder(R.drawable.ic_placeholder_profile)
|
||||
transformations(CircleCropTransformation())
|
||||
}
|
||||
} else {
|
||||
fanTalkContent?.text = ""
|
||||
fanTalkProfile?.setImageResource(R.drawable.ic_placeholder_profile)
|
||||
}
|
||||
}
|
||||
|
||||
private fun bindCommunityImages(row: View, community: CreatorChannelCommunityPostResponse) {
|
||||
val communityRow = row as FeedCommunityView
|
||||
communityRow.profileImageView().loadUrl(community.creatorProfileUrl) {
|
||||
placeholder(R.drawable.ic_placeholder_profile)
|
||||
transformations(CircleCropTransformation())
|
||||
}
|
||||
val isCommunityLocked = community.price > 0 && !community.existOrdered
|
||||
val communityImageUrl = community.imageUrl.takeIf { !it.isNullOrBlank() }
|
||||
if (communityImageUrl != null) {
|
||||
communityRow.communityImageView().loadUrl(communityImageUrl) {
|
||||
if (isCommunityLocked) {
|
||||
transformations(BlurTransformation(itemView.context, 25f, 2.5f))
|
||||
}
|
||||
}
|
||||
} else {
|
||||
communityRow.communityImageView().setImageDrawable(null)
|
||||
}
|
||||
}
|
||||
|
||||
private fun CreatorChannelCommunityPostResponse.toFeedCommunityItem(): FeedItem.Community = FeedItem.Community(
|
||||
feedId = postId.toString(),
|
||||
creatorId = creatorId.toString(),
|
||||
creatorName = creatorNickname,
|
||||
creatorImageUrl = creatorProfileUrl,
|
||||
postId = postId.toString(),
|
||||
bodyText = content,
|
||||
keywordText = "",
|
||||
createdAtText = dateUtc,
|
||||
commentCount = commentCount,
|
||||
likeCount = likeCount,
|
||||
imageUrl = imageUrl,
|
||||
audioUrl = audioUrl,
|
||||
price = price,
|
||||
existOrdered = existOrdered,
|
||||
showKeyword = false
|
||||
)
|
||||
|
||||
private fun bindIntroduce(item: CreatorChannelHomeSection.Introduce) {
|
||||
addTextCard(title = item.introduce, body = "", imageUrl = null)
|
||||
}
|
||||
@@ -371,26 +453,6 @@ class CreatorChannelHomeSectionAdapter(
|
||||
sectionItems?.addView(card)
|
||||
}
|
||||
|
||||
private fun addFeedCard(title: String, body: String, imageUrl: String?) {
|
||||
val card = LinearLayout(itemView.context).apply {
|
||||
orientation = LinearLayout.VERTICAL
|
||||
setPadding(14.dp(), 14.dp(), 14.dp(), 14.dp())
|
||||
setBackgroundResource(R.drawable.bg_round_corner_16_7_222222)
|
||||
layoutParams = defaultBlockLayoutParams()
|
||||
}
|
||||
card.addView(createText(body, R.style.Typography_Caption2, R.color.gray_500, maxLines = 1))
|
||||
card.addView(createText(title, R.style.Typography_Body2, R.color.white, maxLines = 4))
|
||||
card.addView(createImage(imageUrl, LinearLayout.LayoutParams.MATCH_PARENT, 180.dp()))
|
||||
sectionItems?.addView(card)
|
||||
}
|
||||
|
||||
private fun addCommentCard(title: String, body: String, imageUrl: String?) {
|
||||
val card = createHorizontalCard()
|
||||
card.addView(createImage(imageUrl, 28.dp(), 28.dp()))
|
||||
card.addView(createTextGroup(title, body, bodyMaxLines = 2))
|
||||
sectionItems?.addView(card)
|
||||
}
|
||||
|
||||
private fun createHorizontalCard(): LinearLayout =
|
||||
LinearLayout(itemView.context).apply {
|
||||
orientation = LinearLayout.HORIZONTAL
|
||||
@@ -412,22 +474,6 @@ class CreatorChannelHomeSectionAdapter(
|
||||
return textGroup
|
||||
}
|
||||
|
||||
private fun createContentTile(
|
||||
title: String,
|
||||
body: String,
|
||||
imageUrl: String?,
|
||||
imageWidth: Int,
|
||||
imageHeight: Int
|
||||
): LinearLayout = LinearLayout(itemView.context).apply {
|
||||
orientation = LinearLayout.VERTICAL
|
||||
layoutParams = LinearLayout.LayoutParams(imageWidth, LinearLayout.LayoutParams.WRAP_CONTENT).apply {
|
||||
marginEnd = 12.dp()
|
||||
}
|
||||
addView(createImage(imageUrl, imageWidth, imageHeight))
|
||||
addView(createText(title, R.style.Typography_Body2, R.color.white, maxLines = 2))
|
||||
addView(createText(body, R.style.Typography_Caption2, R.color.gray_500, maxLines = 1))
|
||||
}
|
||||
|
||||
private fun createImage(imageUrl: String?, width: Int, height: Int): ImageView = ImageView(itemView.context).apply {
|
||||
layoutParams = LinearLayout.LayoutParams(width, height).apply {
|
||||
bottomMargin = 8.dp()
|
||||
@@ -438,19 +484,6 @@ class CreatorChannelHomeSectionAdapter(
|
||||
imageUrl?.let(::loadUrl)
|
||||
}
|
||||
|
||||
private fun createHorizontalRow(): LinearLayout = LinearLayout(itemView.context).apply {
|
||||
orientation = LinearLayout.HORIZONTAL
|
||||
layoutParams = defaultBlockLayoutParams()
|
||||
}
|
||||
|
||||
private fun createHorizontalScrollRow(row: LinearLayout): HorizontalScrollView =
|
||||
HorizontalScrollView(itemView.context).apply {
|
||||
isHorizontalScrollBarEnabled = false
|
||||
overScrollMode = View.OVER_SCROLL_NEVER
|
||||
layoutParams = defaultBlockLayoutParams()
|
||||
addView(row)
|
||||
}
|
||||
|
||||
private fun defaultBlockLayoutParams(): LinearLayout.LayoutParams = LinearLayout.LayoutParams(
|
||||
LinearLayout.LayoutParams.MATCH_PARENT,
|
||||
LinearLayout.LayoutParams.WRAP_CONTENT
|
||||
@@ -618,6 +651,8 @@ class CreatorChannelHomeSectionAdapter(
|
||||
private const val MAX_NOTICE_ITEM_COUNT = 3
|
||||
private const val MAX_SCHEDULE_ITEM_COUNT = 3
|
||||
private const val MAX_AUDIO_ITEM_COUNT = 9
|
||||
private const val MAX_SERIES_ITEM_COUNT = 10
|
||||
private const val MAX_COMMUNITY_ITEM_COUNT = 3
|
||||
private const val AUDIO_GRID_SPAN_COUNT = 3
|
||||
|
||||
fun List<String>.joinToText(): String = filter(String::isNotBlank).joinToString(separator = " · ")
|
||||
@@ -699,4 +734,33 @@ internal fun calculateCreatorChannelAudioItemWidthDp(screenWidthDp: Int): Int {
|
||||
}
|
||||
}
|
||||
|
||||
internal fun calculateCreatorChannelSeriesCardWidthDp(screenWidthDp: Int): Int {
|
||||
val width = screenWidthDp.takeIf { it > 0 } ?: 402
|
||||
return if (width >= 402) {
|
||||
163
|
||||
} else {
|
||||
(163f * width / 402f).roundToInt()
|
||||
}
|
||||
}
|
||||
|
||||
internal fun calculateCreatorChannelSeriesCardHeightDp(widthDp: Int): Int = (widthDp * 230f / 163f).roundToInt()
|
||||
|
||||
internal fun calculateCreatorChannelCommunityCardWidthDp(screenWidthDp: Int): Int {
|
||||
val width = screenWidthDp.takeIf { it > 0 } ?: 402
|
||||
return if (width >= 402) {
|
||||
374
|
||||
} else {
|
||||
(374f * width / 402f).roundToInt()
|
||||
}
|
||||
}
|
||||
|
||||
internal fun calculateCreatorChannelFanTalkCardWidthDp(screenWidthDp: Int): Int {
|
||||
val width = screenWidthDp.takeIf { it > 0 } ?: 402
|
||||
return if (width >= 402) {
|
||||
374
|
||||
} else {
|
||||
(374f * width / 402f).roundToInt()
|
||||
}
|
||||
}
|
||||
|
||||
internal fun calculateCreatorChannelScheduleTimelineLineCount(scheduleCount: Int): Int = (scheduleCount - 1).coerceAtLeast(0)
|
||||
|
||||
@@ -0,0 +1,49 @@
|
||||
package kr.co.vividnext.sodalive.v2.creator.channel.ui
|
||||
|
||||
import android.content.Context
|
||||
import android.graphics.Outline
|
||||
import android.util.AttributeSet
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import android.view.ViewOutlineProvider
|
||||
import android.widget.FrameLayout
|
||||
import android.widget.ImageView
|
||||
import androidx.core.view.isVisible
|
||||
import kr.co.vividnext.sodalive.R
|
||||
import kr.co.vividnext.sodalive.extensions.loadUrl
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.data.CreatorChannelSeriesResponse
|
||||
|
||||
class CreatorChannelHomeSeriesCardView @JvmOverloads constructor(
|
||||
context: Context,
|
||||
attrs: AttributeSet? = null,
|
||||
defStyleAttr: Int = 0
|
||||
) : FrameLayout(context, attrs, defStyleAttr) {
|
||||
|
||||
private val thumbnailContainer: View by lazy { findViewById(R.id.layout_series_thumbnail) }
|
||||
private val thumbnail: ImageView by lazy { findViewById(R.id.iv_series_thumbnail) }
|
||||
private val originalTag: View by lazy { findViewById(R.id.layout_series_original_tag) }
|
||||
|
||||
override fun onFinishInflate() {
|
||||
super.onFinishInflate()
|
||||
thumbnailContainer.clipToOutline = true
|
||||
thumbnailContainer.outlineProvider = object : ViewOutlineProvider() {
|
||||
override fun getOutline(view: View, outline: Outline) {
|
||||
outline.setRoundRect(0, 0, view.width, view.height, resources.getDimension(R.dimen.radius_14))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun bind(series: CreatorChannelSeriesResponse) {
|
||||
thumbnail.loadUrl(series.coverImageUrl)
|
||||
originalTag.isVisible = series.isOriginal
|
||||
}
|
||||
|
||||
fun setThumbnailSize(widthDp: Int, heightDp: Int) {
|
||||
thumbnailContainer.layoutParams = thumbnailContainer.layoutParams.apply {
|
||||
width = widthDp.dp()
|
||||
height = heightDp.dp()
|
||||
} ?: ViewGroup.LayoutParams(widthDp.dp(), heightDp.dp())
|
||||
}
|
||||
|
||||
private fun Int.dp(): Int = (this * resources.displayMetrics.density).toInt()
|
||||
}
|
||||
@@ -5,6 +5,7 @@ import android.view.ViewGroup
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import coil.dispose
|
||||
import kr.co.vividnext.sodalive.R
|
||||
import kr.co.vividnext.sodalive.common.image.BlurTransformation
|
||||
import kr.co.vividnext.sodalive.extensions.loadUrl
|
||||
import kr.co.vividnext.sodalive.v2.main.home.model.HomeRecommendationPopularCommunityPostSection
|
||||
import kr.co.vividnext.sodalive.v2.main.home.model.HomeRecommendationPopularCommunityPostUiModel
|
||||
@@ -49,15 +50,27 @@ class HomePopularCommunityAdapter(
|
||||
view.bind(item.item)
|
||||
view.setOnFeedClick { feedItem -> onClickItem(feedItem as FeedItem.Community) }
|
||||
bindImage(item.item.creatorImageUrl, view.profileImageView())
|
||||
bindImage(item.item.imageUrl.takeIf { item.item.price <= 0 || item.item.existOrdered }, view.communityImageView())
|
||||
bindImage(
|
||||
imageUrl = item.item.imageUrl,
|
||||
imageView = view.communityImageView(),
|
||||
shouldBlur = item.item.price > 0 && !item.item.existOrdered
|
||||
)
|
||||
}
|
||||
|
||||
private fun bindImage(imageUrl: String?, imageView: android.widget.ImageView) {
|
||||
private fun bindImage(
|
||||
imageUrl: String?,
|
||||
imageView: android.widget.ImageView,
|
||||
shouldBlur: Boolean = false
|
||||
) {
|
||||
if (imageUrl.isNullOrBlank()) {
|
||||
imageView.dispose()
|
||||
imageView.setImageDrawable(null)
|
||||
} else {
|
||||
imageView.loadUrl(imageUrl)
|
||||
imageView.loadUrl(imageUrl) {
|
||||
if (shouldBlur) {
|
||||
transformations(BlurTransformation(imageView.context, 25f, 2.5f))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,6 +9,7 @@ import android.view.ViewOutlineProvider
|
||||
import android.widget.ImageView
|
||||
import android.widget.LinearLayout
|
||||
import android.widget.TextView
|
||||
import androidx.core.view.isVisible
|
||||
import kr.co.vividnext.sodalive.R
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
@@ -22,7 +23,6 @@ class FeedCommunityView @JvmOverloads constructor(
|
||||
private var creatorText: TextView? = null
|
||||
private var createdAtText: TextView? = null
|
||||
private var bodyText: TextView? = null
|
||||
private var keywordText: TextView? = null
|
||||
private var communityImageContainer: View? = null
|
||||
private var communityImage: ImageView? = null
|
||||
private var paidOverlay: View? = null
|
||||
@@ -39,7 +39,6 @@ class FeedCommunityView @JvmOverloads constructor(
|
||||
creatorText = findViewById(R.id.tv_feed_community_creator)
|
||||
createdAtText = findViewById(R.id.tv_feed_community_created_at)
|
||||
bodyText = findViewById(R.id.tv_feed_community_body)
|
||||
keywordText = findViewById(R.id.tv_feed_community_keyword)
|
||||
communityImageContainer = findViewById(R.id.fl_feed_community_image_container)
|
||||
communityImage = findViewById(R.id.iv_feed_community_image)
|
||||
paidOverlay = findViewById(R.id.ll_feed_community_paid_overlay)
|
||||
@@ -54,21 +53,20 @@ class FeedCommunityView @JvmOverloads constructor(
|
||||
requireNotNull(communityImageContainer).outlineProvider = roundedOutlineProvider(COMMUNITY_IMAGE_RADIUS_DP)
|
||||
}
|
||||
|
||||
override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
|
||||
updateCommunityImageHeight(MeasureSpec.getSize(widthMeasureSpec))
|
||||
super.onMeasure(widthMeasureSpec, heightMeasureSpec)
|
||||
}
|
||||
|
||||
fun bind(item: FeedItem.Community) {
|
||||
currentItem = item
|
||||
requireNotNull(creatorText).text = item.creatorName
|
||||
requireNotNull(createdAtText).text = item.createdAtText
|
||||
requireNotNull(bodyText).text = item.bodyText
|
||||
requireNotNull(keywordText).text = item.keywordText
|
||||
requireNotNull(bodyText).visibility = visibilityForText(item.bodyText)
|
||||
requireNotNull(keywordText).visibility = if (item.showKeyword) visibilityForText(item.keywordText) else View.GONE
|
||||
requireNotNull(communityImageContainer).visibility = if (item.imageUrl.isNullOrBlank()) View.GONE else View.VISIBLE
|
||||
requireNotNull(paidOverlay).visibility = if (item.price > 0 && !item.existOrdered) View.VISIBLE else View.GONE
|
||||
val isLocked = item.price > 0 && !item.existOrdered
|
||||
val hasImage = !item.imageUrl.isNullOrBlank()
|
||||
requireNotNull(communityImageContainer).isVisible = hasImage || isLocked
|
||||
requireNotNull(communityImage).isVisible = hasImage
|
||||
if (!hasImage || isLocked) {
|
||||
requireNotNull(communityImage).setImageDrawable(null)
|
||||
}
|
||||
requireNotNull(paidOverlay).isVisible = isLocked
|
||||
requireNotNull(priceText).text = item.price.toString()
|
||||
requireNotNull(commentCountText).text = item.commentCount.toString()
|
||||
requireNotNull(likeCountText).text = item.likeCount.toString()
|
||||
@@ -113,20 +111,6 @@ class FeedCommunityView @JvmOverloads constructor(
|
||||
}
|
||||
}
|
||||
|
||||
private fun updateCommunityImageHeight(rootWidth: Int) {
|
||||
val imageWidth = rootWidth - paddingLeft - paddingRight
|
||||
if (imageWidth <= 0) return
|
||||
|
||||
val container = requireNotNull(communityImageContainer)
|
||||
val currentLayoutParams = container.layoutParams
|
||||
val nextHeight = (imageWidth * COMMUNITY_IMAGE_FIGMA_HEIGHT_DP / COMMUNITY_IMAGE_FIGMA_WIDTH_DP.toFloat())
|
||||
.roundToInt()
|
||||
if (currentLayoutParams.height != nextHeight) {
|
||||
currentLayoutParams.height = nextHeight
|
||||
container.layoutParams = currentLayoutParams
|
||||
}
|
||||
}
|
||||
|
||||
private fun circleOutlineProvider() = object : ViewOutlineProvider() {
|
||||
override fun getOutline(view: View, outline: Outline) {
|
||||
outline.setOval(0, 0, view.width, view.height)
|
||||
@@ -144,7 +128,5 @@ class FeedCommunityView @JvmOverloads constructor(
|
||||
private companion object {
|
||||
const val CARD_RADIUS_DP = 14
|
||||
const val COMMUNITY_IMAGE_RADIUS_DP = 14
|
||||
const val COMMUNITY_IMAGE_FIGMA_WIDTH_DP = 346
|
||||
const val COMMUNITY_IMAGE_FIGMA_HEIGHT_DP = 236
|
||||
}
|
||||
}
|
||||
|
||||
BIN
app/src/main/res/drawable-mdpi/ic_chevron_down_white.png
Normal file
BIN
app/src/main/res/drawable-mdpi/ic_chevron_down_white.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 225 B |
BIN
app/src/main/res/drawable-mdpi/ic_new_fantalk_plus.png
Normal file
BIN
app/src/main/res/drawable-mdpi/ic_new_fantalk_plus.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 245 B |
@@ -0,0 +1,5 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<solid android:color="@color/white" />
|
||||
<corners android:radius="100dp" />
|
||||
</shape>
|
||||
@@ -0,0 +1,8 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<shape xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<solid android:color="@android:color/transparent" />
|
||||
<stroke
|
||||
android:width="1dp"
|
||||
android:color="@color/color_4dffffff" />
|
||||
<corners android:radius="100dp" />
|
||||
</shape>
|
||||
@@ -1,25 +1,30 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
android:paddingHorizontal="@dimen/spacing_20"
|
||||
android:paddingTop="@dimen/spacing_20">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_section_title"
|
||||
style="@style/Typography.Heading3"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:textColor="@color/white"
|
||||
tools:text="섹션" />
|
||||
<include layout="@layout/view_section_title" />
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/ll_section_items"
|
||||
android:id="@+id/ll_community_items"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="@dimen/spacing_8"
|
||||
android:layout_marginTop="@dimen/spacing_14"
|
||||
android:gravity="center_horizontal"
|
||||
android:orientation="vertical" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/layout_community_more_button"
|
||||
style="@style/Typography.Body3"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="44dp"
|
||||
android:layout_marginHorizontal="@dimen/spacing_14"
|
||||
android:layout_marginTop="@dimen/spacing_8"
|
||||
android:background="@drawable/bg_creator_channel_more_button"
|
||||
android:gravity="center"
|
||||
android:includeFontPadding="false"
|
||||
android:text="@string/view_all"
|
||||
android:textColor="@color/white" />
|
||||
</LinearLayout>
|
||||
|
||||
@@ -4,22 +4,131 @@
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
android:paddingHorizontal="@dimen/spacing_20"
|
||||
android:paddingTop="@dimen/spacing_20">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_section_title"
|
||||
style="@style/Typography.Heading3"
|
||||
<include layout="@layout/view_section_title" />
|
||||
|
||||
<kr.co.vividnext.sodalive.v2.creator.channel.ui.CreatorChannelFanTalkCardView
|
||||
android:id="@+id/layout_fantalk_card"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:textColor="@color/white"
|
||||
tools:text="섹션" />
|
||||
android:layout_marginHorizontal="@dimen/spacing_14"
|
||||
android:layout_marginTop="@dimen/spacing_14"
|
||||
android:background="@drawable/bg_feed_card"
|
||||
android:orientation="vertical"
|
||||
android:padding="@dimen/spacing_14">
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/ll_section_items"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="@dimen/spacing_8"
|
||||
android:orientation="vertical" />
|
||||
<LinearLayout
|
||||
android:id="@+id/layout_fantalk_total_row"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:visibility="gone">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_fantalk_total_label"
|
||||
style="@style/Typography.Body3"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:includeFontPadding="false"
|
||||
android:text="@string/screen_chat_filter_all"
|
||||
android:textColor="@color/white" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_fantalk_total_count"
|
||||
style="@style/Typography.Body3"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_4"
|
||||
android:includeFontPadding="false"
|
||||
android:textColor="@color/gray_500"
|
||||
tools:text="23" />
|
||||
</LinearLayout>
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/layout_fantalk_latest_row"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="@dimen/spacing_8"
|
||||
android:gravity="center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:visibility="gone">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_fantalk_profile"
|
||||
android:layout_width="28dp"
|
||||
android:layout_height="28dp"
|
||||
android:contentDescription="@null"
|
||||
android:scaleType="centerCrop"
|
||||
android:src="@drawable/ic_placeholder_profile" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_fantalk_content"
|
||||
style="@style/Typography.Body6"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="40dp"
|
||||
android:layout_marginStart="@dimen/spacing_14"
|
||||
android:layout_weight="1"
|
||||
android:ellipsize="end"
|
||||
android:includeFontPadding="false"
|
||||
android:maxLines="2"
|
||||
android:textColor="@color/white"
|
||||
tools:text="팬이 쓴 응원이 보이는 부분입니다. 두 줄까지만 보여주고 초과 시 말줄임 처리." />
|
||||
|
||||
<ImageView
|
||||
android:layout_width="18dp"
|
||||
android:layout_height="18dp"
|
||||
android:layout_marginStart="@dimen/spacing_14"
|
||||
android:contentDescription="@null"
|
||||
android:src="@drawable/ic_chevron_down_white" />
|
||||
</LinearLayout>
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/layout_fantalk_empty"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="169dp"
|
||||
android:visibility="gone"
|
||||
tools:visibility="visible">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_fantalk_empty_title"
|
||||
style="@style/Typography.Heading1"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="top|start"
|
||||
android:layout_marginStart="@dimen/spacing_6"
|
||||
android:layout_marginTop="@dimen/spacing_6"
|
||||
android:includeFontPadding="false"
|
||||
android:text="@string/creator_channel_fantalk_empty_title"
|
||||
android:textColor="@color/white" />
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/layout_fantalk_support_button"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="bottom|center_horizontal"
|
||||
android:layout_marginBottom="@dimen/spacing_6"
|
||||
android:background="@drawable/bg_round_corner_999_white"
|
||||
android:gravity="center"
|
||||
android:orientation="horizontal"
|
||||
android:padding="@dimen/spacing_12">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="20dp"
|
||||
android:layout_height="20dp"
|
||||
android:contentDescription="@null"
|
||||
android:src="@drawable/ic_new_fantalk_plus" />
|
||||
|
||||
<TextView
|
||||
style="@style/Typography.Body2"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_6"
|
||||
android:includeFontPadding="false"
|
||||
android:text="@string/creator_channel_fantalk_support_action"
|
||||
android:textColor="@color/black" />
|
||||
</LinearLayout>
|
||||
</FrameLayout>
|
||||
</kr.co.vividnext.sodalive.v2.creator.channel.ui.CreatorChannelFanTalkCardView>
|
||||
</LinearLayout>
|
||||
|
||||
@@ -1,25 +1,27 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
android:paddingHorizontal="@dimen/spacing_20"
|
||||
android:paddingTop="@dimen/spacing_20">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_section_title"
|
||||
style="@style/Typography.Heading3"
|
||||
<include layout="@layout/view_section_title" />
|
||||
|
||||
<HorizontalScrollView
|
||||
android:id="@+id/hsv_series_items"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:textColor="@color/white"
|
||||
tools:text="섹션" />
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/ll_section_items"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="@dimen/spacing_8"
|
||||
android:orientation="vertical" />
|
||||
android:layout_marginTop="@dimen/spacing_14"
|
||||
android:clipToPadding="false"
|
||||
android:overScrollMode="never"
|
||||
android:paddingStart="@dimen/spacing_14"
|
||||
android:paddingEnd="@dimen/spacing_20"
|
||||
android:scrollbars="none">
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/ll_series_items"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal" />
|
||||
</HorizontalScrollView>
|
||||
</LinearLayout>
|
||||
|
||||
@@ -0,0 +1,51 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<kr.co.vividnext.sodalive.v2.creator.channel.ui.CreatorChannelHomeSeriesCardView xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/layout_series_content_card"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content">
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/layout_series_thumbnail"
|
||||
android:layout_width="163dp"
|
||||
android:layout_height="230dp"
|
||||
android:background="@drawable/bg_series_content_thumbnail">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_series_thumbnail"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:contentDescription="@null"
|
||||
android:scaleType="centerCrop"
|
||||
tools:src="@drawable/ic_launcher_background" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/layout_series_original_tag"
|
||||
android:layout_width="70dp"
|
||||
android:layout_height="24dp"
|
||||
android:layout_gravity="top|start"
|
||||
android:background="@drawable/bg_series_original_tag">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_series_original_icon"
|
||||
android:layout_width="14dp"
|
||||
android:layout_height="14dp"
|
||||
android:layout_gravity="start|center_vertical"
|
||||
android:layout_marginStart="8dp"
|
||||
android:contentDescription="@null"
|
||||
android:src="@drawable/ic_series_original" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_series_original_text"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="26dp"
|
||||
android:layout_marginTop="2dp"
|
||||
android:fontFamily="@font/phosphate_solid"
|
||||
android:text="Only"
|
||||
android:textColor="@color/white"
|
||||
android:textSize="16sp"
|
||||
tools:ignore="HardcodedText" />
|
||||
</FrameLayout>
|
||||
</FrameLayout>
|
||||
</kr.co.vividnext.sodalive.v2.creator.channel.ui.CreatorChannelHomeSeriesCardView>
|
||||
@@ -30,7 +30,7 @@
|
||||
<TextView
|
||||
android:id="@+id/tv_feed_community_creator"
|
||||
style="@style/Typography.Body5"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_width="85dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:ellipsize="end"
|
||||
android:includeFontPadding="false"
|
||||
@@ -41,7 +41,7 @@
|
||||
<TextView
|
||||
android:id="@+id/tv_feed_community_created_at"
|
||||
style="@style/Typography.Body6"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_width="85dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="2dp"
|
||||
android:ellipsize="end"
|
||||
@@ -57,35 +57,26 @@
|
||||
style="@style/Typography.Body3"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="@dimen/spacing_14"
|
||||
android:includeFontPadding="false"
|
||||
android:textColor="@color/white"
|
||||
tools:text="크리에이터가 커뮤니티에 올린 글이 보이는 부분" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_feed_community_keyword"
|
||||
style="@style/Typography.Body3"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="@dimen/spacing_4"
|
||||
android:layout_marginTop="@dimen/spacing_16"
|
||||
android:ellipsize="end"
|
||||
android:includeFontPadding="false"
|
||||
android:maxLines="1"
|
||||
android:textColor="@color/soda_400"
|
||||
tools:text="#키워드 #키워드 #키워드" />
|
||||
android:maxLines="5"
|
||||
android:textColor="@color/white"
|
||||
tools:text="크리에이터가 커뮤니티에 올린 글이 보이는 부분" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/fl_feed_community_image_container"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="0dp"
|
||||
android:layout_height="236dp"
|
||||
android:layout_marginTop="@dimen/spacing_14"
|
||||
android:background="@drawable/bg_feed_community_image"
|
||||
android:visibility="gone">
|
||||
android:visibility="gone"
|
||||
tools:visibility="visible">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_feed_community_image"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:background="@drawable/bg_feed_community_image"
|
||||
android:contentDescription="@string/a11y_feed_content_image"
|
||||
android:scaleType="centerCrop"
|
||||
tools:src="@drawable/ic_launcher_background" />
|
||||
@@ -94,10 +85,11 @@
|
||||
android:id="@+id/ll_feed_community_paid_overlay"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:background="@color/color_99525252"
|
||||
android:background="@color/color_26909090"
|
||||
android:gravity="center"
|
||||
android:orientation="vertical"
|
||||
android:visibility="gone">
|
||||
android:visibility="gone"
|
||||
tools:visibility="visible">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="24dp"
|
||||
@@ -105,24 +97,37 @@
|
||||
android:contentDescription="@null"
|
||||
android:src="@drawable/ic_new_community_lock" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_feed_community_price"
|
||||
style="@style/Typography.Body3"
|
||||
<LinearLayout
|
||||
android:layout_width="70dp"
|
||||
android:layout_height="36dp"
|
||||
android:layout_marginTop="@dimen/spacing_4"
|
||||
android:background="@drawable/bg_round_corner_999_white"
|
||||
android:background="@drawable/bg_creator_channel_community_price"
|
||||
android:gravity="center"
|
||||
android:includeFontPadding="false"
|
||||
android:textColor="@color/black"
|
||||
tools:text="30" />
|
||||
android:orientation="horizontal">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="18dp"
|
||||
android:layout_height="18dp"
|
||||
android:contentDescription="@null"
|
||||
android:src="@drawable/ic_bar_cash" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_feed_community_price"
|
||||
style="@style/Typography.Body3"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_6"
|
||||
android:includeFontPadding="false"
|
||||
android:textColor="@color/black"
|
||||
tools:text="30" />
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
</FrameLayout>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="24dp"
|
||||
android:layout_marginTop="@dimen/spacing_14"
|
||||
android:layout_marginTop="@dimen/spacing_16"
|
||||
android:gravity="center_vertical"
|
||||
android:orientation="horizontal">
|
||||
|
||||
@@ -139,7 +144,7 @@
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_4"
|
||||
android:includeFontPadding="false"
|
||||
android:textColor="@color/gray_500"
|
||||
android:textColor="@color/gray_400"
|
||||
tools:text="5" />
|
||||
|
||||
<ImageView
|
||||
@@ -156,7 +161,7 @@
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="@dimen/spacing_4"
|
||||
android:includeFontPadding="false"
|
||||
android:textColor="@color/gray_500"
|
||||
android:textColor="@color/gray_400"
|
||||
tools:text="6" />
|
||||
</LinearLayout>
|
||||
</kr.co.vividnext.sodalive.v2.widget.feed.FeedCommunityView>
|
||||
|
||||
@@ -297,6 +297,8 @@
|
||||
<string name="creator_channel_series_summary">%1$d episodes · %2$s</string>
|
||||
<string name="creator_channel_community_summary">%1$s · Likes %2$d · Comments %3$d</string>
|
||||
<string name="creator_channel_fantalk_summary">%1$s · Total %2$d</string>
|
||||
<string name="creator_channel_fantalk_empty_title">Be the first\nto cheer them on!</string>
|
||||
<string name="creator_channel_fantalk_support_action">Leave support</string>
|
||||
<string name="creator_channel_activity_summary">Live %1$d · %2$d hours · %3$d contributors · Audio %4$d · Series %5$d</string>
|
||||
<string name="creator_channel_activity_debut">Debut</string>
|
||||
<string name="creator_channel_activity_debut_format">%1$s (%2$s)</string>
|
||||
|
||||
@@ -297,6 +297,8 @@
|
||||
<string name="creator_channel_series_summary">%1$d件 · %2$s</string>
|
||||
<string name="creator_channel_community_summary">%1$s · いいね %2$d · コメント %3$d</string>
|
||||
<string name="creator_channel_fantalk_summary">%1$s · 全体 %2$d</string>
|
||||
<string name="creator_channel_fantalk_empty_title">最初の応援を\n待っています!</string>
|
||||
<string name="creator_channel_fantalk_support_action">応援を残す</string>
|
||||
<string name="creator_channel_activity_summary">ライブ %1$d回 · 累計 %2$d時間 · 参加者 %3$d人 · オーディオ %4$d件 · シリーズ %5$d件</string>
|
||||
<string name="creator_channel_activity_debut">デビュー</string>
|
||||
<string name="creator_channel_activity_debut_format">%1$s(%2$s)</string>
|
||||
|
||||
@@ -60,6 +60,7 @@
|
||||
<color name="color_ccd85e37">#CCD85E37</color>
|
||||
<color name="color_cc333333">#CC333333</color>
|
||||
<color name="color_33ffffff">#33FFFFFF</color>
|
||||
<color name="color_4dffffff">#4DFFFFFF</color>
|
||||
<color name="color_303030">#303030</color>
|
||||
<color name="color_555555">#555555</color>
|
||||
<color name="color_3e1b93">#3E1B93</color>
|
||||
|
||||
@@ -296,6 +296,8 @@
|
||||
<string name="creator_channel_series_summary">%1$d개 · %2$s</string>
|
||||
<string name="creator_channel_community_summary">%1$s · 좋아요 %2$d · 댓글 %3$d</string>
|
||||
<string name="creator_channel_fantalk_summary">%1$s · 전체 %2$d</string>
|
||||
<string name="creator_channel_fantalk_empty_title">당신의 첫 응원을\n기다리고 있어요!</string>
|
||||
<string name="creator_channel_fantalk_support_action">응원 남기기</string>
|
||||
<string name="creator_channel_activity_summary">라이브 %1$d회 · 누적 %2$d시간 · 참여자 %3$d명 · 오디오 %4$d개 · 시리즈 %5$d개</string>
|
||||
<string name="creator_channel_activity_debut">데뷔</string>
|
||||
<string name="creator_channel_activity_debut_format">%1$s(%2$s)</string>
|
||||
|
||||
Reference in New Issue
Block a user