Skip to content

Commit b59d7f0

Browse files
authored
Merge pull request #552 from sopt-makers/feat/#551-soptamp-special
[Feat] #551 - 솝탬프 특별 미션 기능 구현
2 parents 4cee7eb + 220590e commit b59d7f0

File tree

13 files changed

+215
-68
lines changed

13 files changed

+215
-68
lines changed

SOPT-iOS/Projects/Core/Sources/Enum/StarViewLevel.swift

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,4 +12,5 @@ public enum StarViewLevel: Int {
1212
case levelOne = 1
1313
case levelTwo = 2
1414
case levelThree = 3
15+
case levelTen = 10
1516
}

SOPT-iOS/Projects/Core/Sources/Literals/StringLiterals.swift

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,8 @@ public struct I18N {
103103

104104
public struct MissionList {
105105
public static let noMission = "아직 완료한 미션이 없습니다!"
106+
public static let multipleTen = "x 10"
107+
public static let specialMission = "특별미션"
106108
}
107109

108110
public struct RankingList {
Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
//
2+
// STLevelTenStarView.swift
3+
// StampFeature
4+
//
5+
// Created by Jae Hyun Lee on 4/23/25.
6+
// Copyright © 2025 SOPT-iOS. All rights reserved.
7+
//
8+
9+
import UIKit
10+
11+
import Core
12+
import DSKit
13+
14+
import SnapKit
15+
import Then
16+
17+
final class STLevelTenStarView: UIView {
18+
19+
// MARK: - UI Components
20+
21+
private let starImageView = UIImageView().then {
22+
$0.image = DSKitAsset.Assets.icStar.image.withRenderingMode(.alwaysTemplate)
23+
$0.tintColor = DSKitAsset.Colors.orange300.color
24+
}
25+
26+
private let starMultipleTenLabel = UILabel().then {
27+
$0.text = I18N.MissionList.multipleTen
28+
$0.font = DSKitFontFamily.Suit.semiBold.font(size: 14)
29+
$0.textColor = DSKitAsset.Colors.white100.color
30+
}
31+
32+
private let dividerView = UIView().then {
33+
$0.backgroundColor = DSKitAsset.Colors.gray600.color
34+
}
35+
36+
private let specialMissionLabel = UILabel().then {
37+
$0.text = I18N.MissionList.specialMission
38+
$0.font = DSKitFontFamily.Suit.semiBold.font(size: 14)
39+
$0.textColor = DSKitAsset.Colors.orange300.color
40+
}
41+
42+
private let stackView = UIStackView().then {
43+
$0.axis = .horizontal
44+
$0.alignment = .center
45+
}
46+
47+
// MARK: - View Life Cycle
48+
49+
override init(frame: CGRect) {
50+
super.init(frame: .zero)
51+
self.setStackView()
52+
self.setLayout()
53+
}
54+
55+
required init?(coder: NSCoder) {
56+
fatalError("init(coder:) has not been implemented")
57+
}
58+
59+
deinit {
60+
self.stackView.removeAllSubViews()
61+
}
62+
}
63+
64+
// MARK: - UI & Layout
65+
66+
extension STLevelTenStarView {
67+
private func setStackView() {
68+
stackView.addArrangedSubviews(
69+
starImageView,
70+
starMultipleTenLabel,
71+
dividerView,
72+
specialMissionLabel
73+
)
74+
}
75+
76+
private func setLayout() {
77+
self.addSubview(stackView)
78+
79+
stackView.snp.makeConstraints { make in
80+
make.edges.equalToSuperview()
81+
}
82+
83+
stackView.setCustomSpacing(2, after: starImageView)
84+
stackView.setCustomSpacing(7, after: starMultipleTenLabel)
85+
stackView.setCustomSpacing(7, after: dividerView)
86+
87+
starImageView.snp.makeConstraints { make in
88+
make.size.equalTo(15)
89+
}
90+
91+
dividerView.snp.makeConstraints { make in
92+
make.width.equalTo(1)
93+
make.height.equalTo(7)
94+
}
95+
}
96+
}

SOPT-iOS/Projects/Features/StampFeature/Sources/Components/STStarView.swift

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,8 +57,9 @@ extension STStarView {
5757

5858
private func setLayout() {
5959
self.addSubviews(starStackView)
60+
6061
starStackView.snp.makeConstraints { make in
61-
make.center.equalToSuperview()
62+
make.edges.equalToSuperview()
6263
}
6364
}
6465

@@ -72,6 +73,7 @@ extension STStarView {
7273
}
7374
imageView.contentMode = .scaleToFill
7475
imageView.image = DSKitAsset.Assets.icStar.image.withRenderingMode(.alwaysTemplate)
76+
7577
starStackView.addArrangedSubviews(imageView)
7678
starImageArray.append(imageView)
7779

@@ -95,6 +97,8 @@ extension STStarView {
9597
self.starImageArray[starNumber-1].tintColor = DSKitAsset.Colors.soptampPurple300.color
9698
} else if level == .levelThree {
9799
self.starImageArray[starNumber-1].tintColor = DSKitAsset.Colors.soptampMint300.color
100+
} else if level == .levelTen {
101+
self.starImageArray[starNumber-1].tintColor = DSKitAsset.Colors.orange300.color
98102
} else {
99103
self.starImageArray[starNumber-1].tintColor = starDefaultColor
100104
}

SOPT-iOS/Projects/Features/StampFeature/Sources/ListDetailScene/VC/ListDetailVC.swift

Lines changed: 1 addition & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -29,50 +29,6 @@ public enum TextViewState {
2929
case completed
3030
}
3131

32-
extension StarViewLevel {
33-
var buttonTitleColor: UIColor {
34-
switch self {
35-
case .levelOne, .levelTwo:
36-
return DSKitAsset.Colors.soptampWhite.color
37-
case .levelThree:
38-
return DSKitAsset.Colors.soptampGray700.color
39-
}
40-
}
41-
42-
var pointColor: UIColor {
43-
switch self {
44-
case .levelOne:
45-
return DSKitAsset.Colors.soptampPink300.color
46-
case .levelTwo:
47-
return DSKitAsset.Colors.soptampPurple300.color
48-
case .levelThree:
49-
return DSKitAsset.Colors.soptampMint300.color
50-
}
51-
}
52-
53-
var disableColor: UIColor {
54-
switch self {
55-
case .levelOne:
56-
return DSKitAsset.Colors.soptampPink200.color
57-
case .levelTwo:
58-
return DSKitAsset.Colors.soptampPurple200.color
59-
case .levelThree:
60-
return DSKitAsset.Colors.soptampMint200.color
61-
}
62-
}
63-
64-
var bgColor: UIColor {
65-
switch self {
66-
case .levelOne:
67-
return DSKitAsset.Colors.soptampPink100.color
68-
case .levelTwo:
69-
return DSKitAsset.Colors.soptampPurple100.color
70-
case .levelThree:
71-
return DSKitAsset.Colors.soptampMint100.color
72-
}
73-
}
74-
}
75-
7632
public class ListDetailVC: UIViewController, ListDetailViewControllable {
7733

7834
// MARK: - Properties
@@ -177,6 +133,7 @@ extension ListDetailVC {
177133

178134
private func bindViewModels() {
179135
let rightButtonTapped = naviBar.rightButtonTapped
136+
.throttle(for: 1, scheduler: DispatchQueue.main, latest: false)
180137
.withUnretained(self)
181138
.map { owner, _ in
182139
owner.sceneType

SOPT-iOS/Projects/Features/StampFeature/Sources/ListDetailScene/View/MissionView.swift

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,9 @@ final class MissionView: UIView {
1818

1919
// MARK: - UI Component
2020

21-
private let starView = STStarView(starScale: 14, spacing: 10, level: .levelOne)
21+
private lazy var defaultStarView = STStarView(starScale: 14, spacing: 10, level: .levelOne)
22+
private lazy var levelTenStarView = STLevelTenStarView()
23+
2224
private let missionLabel = UILabel().then {
2325
$0.textAlignment = .center
2426
$0.numberOfLines = 2
@@ -32,13 +34,13 @@ final class MissionView: UIView {
3234
super.init(frame: frame)
3335

3436
self.setUI()
35-
self.setLayout()
3637
}
3738

3839
public convenience init(level: StarViewLevel, mission: String) {
3940
self.init()
4041
self.setMissionLabelText(mission)
41-
starView.changeStarLevel(level: level)
42+
self.setLayout(level: level)
43+
defaultStarView.changeStarLevel(level: level)
4244
}
4345

4446
required init?(coder: NSCoder) {
@@ -53,13 +55,14 @@ final class MissionView: UIView {
5355
self.missionLabel.setTypoStyle(.SoptampFont.subtitle1)
5456
}
5557

56-
private func setLayout() {
58+
private func setLayout(level: StarViewLevel) {
59+
let starView = level == .levelTen ? levelTenStarView : defaultStarView
60+
5761
self.addSubviews([starView, missionLabel])
5862

5963
starView.snp.makeConstraints { make in
6064
make.centerX.equalToSuperview()
6165
make.top.equalToSuperview().inset(12)
62-
make.height.equalTo(14)
6366
}
6467

6568
missionLabel.snp.makeConstraints { make in

SOPT-iOS/Projects/Features/StampFeature/Sources/ListDetailScene/ViewModel/ListDetailViewModel.swift

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -160,6 +160,7 @@ extension ListDetailViewModel {
160160
}.store(in: self.cancelBag)
161161

162162
input.deleteButtonTapped
163+
.removeDuplicates()
163164
.withUnretained(self)
164165
.sink { owner, _ in
165166
owner.useCase.deleteStamp(stampId: owner.stampId)

SOPT-iOS/Projects/Features/StampFeature/Sources/MissionCompletedScene/VC/MissionCompletedVC.swift

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,8 @@ extension StarViewLevel {
2727
return "purplestamp"
2828
case .levelThree:
2929
return "greenstamp"
30+
case .levelTen:
31+
return "orangeStamp"
3032
}
3133
}
3234
}

SOPT-iOS/Projects/Features/StampFeature/Sources/MissionListScene/Cells/MissionListCVC.swift

Lines changed: 32 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -22,14 +22,15 @@ enum MissionListCellType {
2222
case levelOne(completed: Bool)
2323
case levelTwo(completed: Bool)
2424
case levelThree(completed: Bool)
25+
case levelTen(completed: Bool)
2526

2627
var isCompleted: Bool {
2728
switch self {
28-
case .levelOne(let completed):
29-
return completed
30-
case .levelTwo(let completed):
31-
return completed
32-
case .levelThree(let completed):
29+
case
30+
let .levelOne(completed),
31+
let .levelTwo(completed),
32+
let .levelThree(completed),
33+
let .levelTen(completed):
3334
return completed
3435
}
3536
}
@@ -42,6 +43,8 @@ enum MissionListCellType {
4243
return .levelTwo
4344
case .levelThree:
4445
return .levelThree
46+
case .levelTen:
47+
return .levelTen
4548
}
4649
}
4750
}
@@ -53,44 +56,52 @@ extension MissionListCellType {
5356
var stampTop: CGFloat {
5457
switch self {
5558
case .levelOne:
56-
return 47.adjustedH
59+
return 47
5760
case .levelTwo:
58-
return 40.adjustedH
61+
return 40
5962
case .levelThree:
60-
return 26.adjustedH
63+
return 26
64+
case .levelTen:
65+
return 36
6166
}
6267
}
6368

6469
var stampWidth: CGFloat {
6570
switch self {
6671
case .levelOne:
67-
return 135.adjusted
72+
return 135
6873
case .levelTwo:
69-
return 125.adjusted
74+
return 125
7075
case .levelThree:
71-
return 135.adjusted
76+
return 104
77+
case .levelTen:
78+
return 124
7279
}
7380
}
7481

7582
var stampHeight: CGFloat {
7683
switch self {
7784
case .levelOne:
78-
return 81.adjusted
85+
return 81
7986
case .levelTwo:
80-
return 90.adjusted
87+
return 90
8188
case .levelThree:
82-
return 104.adjusted
89+
return 104
90+
case .levelTen:
91+
return 87
8392
}
8493
}
8594

8695
var stampLabelSpacing: CGFloat {
8796
switch self {
8897
case .levelOne:
89-
return 16.adjustedH
98+
return 16
9099
case .levelTwo:
91-
return 13.adjustedH
100+
return 13
92101
case .levelThree:
93-
return 12.adjustedH
102+
return 12
103+
case .levelTen:
104+
return 19
94105
}
95106
}
96107
}
@@ -100,6 +111,8 @@ extension MissionListModel {
100111
switch self.level {
101112
case 1: return .levelOne(completed: self.isCompleted)
102113
case 2: return .levelTwo(completed: self.isCompleted)
114+
case 3: return .levelThree(completed: self.isCompleted)
115+
case 10: return .levelTen(completed: self.isCompleted)
103116
default: return .levelThree(completed: self.isCompleted)
104117
}
105118
}
@@ -196,6 +209,8 @@ extension MissionListCVC {
196209
stampImageView.image = DSKitAsset.Assets.levelTwoStamp.image
197210
case .levelThree:
198211
stampImageView.image = DSKitAsset.Assets.levelThreeStamp.image
212+
case .levelTen:
213+
stampImageView.image = DSKitAsset.Assets.levelTenStamp.image
199214
}
200215
}
201216

@@ -217,7 +232,6 @@ extension MissionListCVC {
217232
starView.snp.makeConstraints { make in
218233
make.top.equalToSuperview().inset(70.adjustedH)
219234
make.centerX.equalToSuperview()
220-
make.height.equalTo(15.adjustedH)
221235
}
222236

223237
purposeLabel.snp.makeConstraints { make in
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
{
2+
"images" : [
3+
{
4+
"filename" : "levelTenStamp.svg",
5+
"idiom" : "universal"
6+
}
7+
],
8+
"info" : {
9+
"author" : "xcode",
10+
"version" : 1
11+
}
12+
}

0 commit comments

Comments
 (0)