import SwiftUI struct MainHomeFollowingRankingNewsCard: View { private let imageUrl: String? private let title: String private let rank: Int private let action: () -> Void init( creatorRanking: FollowingCreatorRankingNewsResponse, onTapCreator: @escaping (Int) -> Void = { _ in } ) { self.imageUrl = creatorRanking.profileImageUrl self.title = creatorRanking.nickname self.rank = creatorRanking.rank self.action = { onTapCreator(creatorRanking.creatorId) } } init( contentRanking: FollowingContentRankingNewsResponse, onTapContent: @escaping (Int) -> Void = { _ in } ) { self.imageUrl = contentRanking.contentImageUrl self.title = contentRanking.title self.rank = contentRanking.rank self.action = { onTapContent(contentRanking.contentId) } } var body: some View { Button(action: action) { HStack(alignment: .center, spacing: SodaSpacing.s14) { RankingThumbnailView(imageUrl: imageUrl, rank: rank) rankingMessage .appFont(size: 16, weight: .medium) .lineSpacing(0) .multilineTextAlignment(.leading) .frame(maxWidth: .infinity, alignment: .leading) } .padding(SodaSpacing.s14) .background(Color.gray900) .clipShape(RoundedRectangle(cornerRadius: SodaRadius.r14, style: .continuous)) } .buttonStyle(.plain) } private var rankingMessage: Text { Text(I18n.HomeFollowing.rankingMessagePrefix(title)) .foregroundColor(.white) + Text(I18n.HomeFollowing.rankingRankText(rank)) .foregroundColor(Color.soda400) + Text(I18n.HomeFollowing.rankingMessageSuffix) .foregroundColor(.white) } } private struct RankingThumbnailView: View { let imageUrl: String? let rank: Int var body: some View { ZStack(alignment: .bottomTrailing) { DownsampledKFImage(url: imageUrl.flatMap(URL.init(string:)), size: CGSize(width: 80, height: 80)) .clipShape(RoundedRectangle(cornerRadius: SodaRadius.r14, style: .continuous)) LinearGradient( colors: [Color.black.opacity(0), Color.black.opacity(0.5)], startPoint: .top, endPoint: .bottom ) .clipShape(RoundedRectangle(cornerRadius: SodaRadius.r14, style: .continuous)) Text("\(rank)") .appFont(size: 40, weight: .regular, family: .pattaya) .foregroundStyle( LinearGradient( colors: [.white, Color(hex: "EEEEEE")], startPoint: .top, endPoint: .bottom ) ) .shadow(color: Color.black.opacity(0.48), radius: 2) .offset(x: 0, y: 24) } .frame(width: 80, height: 80) } } struct MainHomeFollowingRankingNewsCard_Previews: PreviewProvider { private static let previewImageUrl = "https://picsum.photos/500/500" static var previews: some View { VStack(spacing: SodaSpacing.s12) { MainHomeFollowingRankingNewsCard( creatorRanking: FollowingCreatorRankingNewsResponse( rank: 2, creatorId: 1, nickname: "크리", profileImageUrl: previewImageUrl ) ) MainHomeFollowingRankingNewsCard( contentRanking: FollowingContentRankingNewsResponse( rank: 4, contentId: 10, contentImageUrl: previewImageUrl, title: "콘텐츠 제목" ) ) } .padding(SodaSpacing.s14) .background(Color.black) .previewLayout(.sizeThatFits) } }