Showing
5 changed files
with
233 additions
and
1 deletions
... | @@ -7,6 +7,7 @@ | ... | @@ -7,6 +7,7 @@ |
7 | objects = { | 7 | objects = { |
8 | 8 | ||
9 | /* Begin PBXBuildFile section */ | 9 | /* Begin PBXBuildFile section */ |
10 | + 1E4C4CFB2DE6014500279AAD /* CopyableLabel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1E4C4CFA2DE6014500279AAD /* CopyableLabel.swift */; }; | ||
10 | 1E64E1832DE48E0600543217 /* MyRewardsOfferCollectionViewCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = 1E64E1822DE48E0600543217 /* MyRewardsOfferCollectionViewCell.xib */; }; | 11 | 1E64E1832DE48E0600543217 /* MyRewardsOfferCollectionViewCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = 1E64E1822DE48E0600543217 /* MyRewardsOfferCollectionViewCell.xib */; }; |
11 | 1E64E1842DE48E0600543217 /* MyRewardsOfferCollectionViewCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1E64E1812DE48E0600543217 /* MyRewardsOfferCollectionViewCell.swift */; }; | 12 | 1E64E1842DE48E0600543217 /* MyRewardsOfferCollectionViewCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1E64E1812DE48E0600543217 /* MyRewardsOfferCollectionViewCell.swift */; }; |
12 | 1E917CD62DDF64B2002221D8 /* MyRewardsViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = 1E917CD52DDF64B2002221D8 /* MyRewardsViewController.xib */; }; | 13 | 1E917CD62DDF64B2002221D8 /* MyRewardsViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = 1E917CD52DDF64B2002221D8 /* MyRewardsViewController.xib */; }; |
... | @@ -150,6 +151,7 @@ | ... | @@ -150,6 +151,7 @@ |
150 | 151 | ||
151 | /* Begin PBXFileReference section */ | 152 | /* Begin PBXFileReference section */ |
152 | 1E108A9728A3FA9B0008B8E7 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; }; | 153 | 1E108A9728A3FA9B0008B8E7 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; }; |
154 | + 1E4C4CFA2DE6014500279AAD /* CopyableLabel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CopyableLabel.swift; sourceTree = "<group>"; }; | ||
153 | 1E64E1812DE48E0600543217 /* MyRewardsOfferCollectionViewCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MyRewardsOfferCollectionViewCell.swift; sourceTree = "<group>"; }; | 155 | 1E64E1812DE48E0600543217 /* MyRewardsOfferCollectionViewCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MyRewardsOfferCollectionViewCell.swift; sourceTree = "<group>"; }; |
154 | 1E64E1822DE48E0600543217 /* MyRewardsOfferCollectionViewCell.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = MyRewardsOfferCollectionViewCell.xib; sourceTree = "<group>"; }; | 156 | 1E64E1822DE48E0600543217 /* MyRewardsOfferCollectionViewCell.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = MyRewardsOfferCollectionViewCell.xib; sourceTree = "<group>"; }; |
155 | 1E917CD42DDF64B2002221D8 /* MyRewardsViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MyRewardsViewController.swift; sourceTree = "<group>"; }; | 157 | 1E917CD42DDF64B2002221D8 /* MyRewardsViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MyRewardsViewController.swift; sourceTree = "<group>"; }; |
... | @@ -462,6 +464,7 @@ | ... | @@ -462,6 +464,7 @@ |
462 | E6A77850282933340045BBA8 /* SwiftWarplyFramework */ = { | 464 | E6A77850282933340045BBA8 /* SwiftWarplyFramework */ = { |
463 | isa = PBXGroup; | 465 | isa = PBXGroup; |
464 | children = ( | 466 | children = ( |
467 | + 1E4C4CFA2DE6014500279AAD /* CopyableLabel.swift */, | ||
465 | 1E108A9728A3FA9B0008B8E7 /* Info.plist */, | 468 | 1E108A9728A3FA9B0008B8E7 /* Info.plist */, |
466 | 1EA8E5B42DDF315600CD3418 /* screens */, | 469 | 1EA8E5B42DDF315600CD3418 /* screens */, |
467 | 1EA8E5BC2DDF34FB00CD3418 /* cells */, | 470 | 1EA8E5BC2DDF34FB00CD3418 /* cells */, |
... | @@ -926,6 +929,7 @@ | ... | @@ -926,6 +929,7 @@ |
926 | 1E917CD72DDF64B2002221D8 /* MyRewardsViewController.swift in Sources */, | 929 | 1E917CD72DDF64B2002221D8 /* MyRewardsViewController.swift in Sources */, |
927 | E6A77915282933E60045BBA8 /* WLUtils.m in Sources */, | 930 | E6A77915282933E60045BBA8 /* WLUtils.m in Sources */, |
928 | 1E917CDC2DDF68C7002221D8 /* CouponViewController.swift in Sources */, | 931 | 1E917CDC2DDF68C7002221D8 /* CouponViewController.swift in Sources */, |
932 | + 1E4C4CFB2DE6014500279AAD /* CopyableLabel.swift in Sources */, | ||
929 | E6A77947282933E70045BBA8 /* FMDatabaseQueue.m in Sources */, | 933 | E6A77947282933E70045BBA8 /* FMDatabaseQueue.m in Sources */, |
930 | E6A77922282933E60045BBA8 /* NSData+SSToolkitAdditions.m in Sources */, | 934 | E6A77922282933E60045BBA8 /* NSData+SSToolkitAdditions.m in Sources */, |
931 | E6A7794A282933E70045BBA8 /* FMDatabaseAdditions.m in Sources */, | 935 | E6A7794A282933E70045BBA8 /* FMDatabaseAdditions.m in Sources */, | ... | ... |
No preview for this file type
1 | +// | ||
2 | +// CopyableLabel.swift | ||
3 | +// SwiftWarplyFramework | ||
4 | +// | ||
5 | +// Created by Manos Chorianopoulos on 26/10/22. | ||
6 | +// | ||
7 | + | ||
8 | +import Foundation | ||
9 | +import UIKit | ||
10 | + | ||
11 | +class CopyableLabel: UILabel { | ||
12 | + | ||
13 | + override init(frame: CGRect) { | ||
14 | + super.init(frame: frame) | ||
15 | + sharedInit() | ||
16 | + } | ||
17 | + | ||
18 | + required init(coder aDecoder: NSCoder) { | ||
19 | + super.init(coder: aDecoder)! | ||
20 | + sharedInit() | ||
21 | + } | ||
22 | + | ||
23 | + func sharedInit() { | ||
24 | + isUserInteractionEnabled = true | ||
25 | + addGestureRecognizer(UILongPressGestureRecognizer(target: self, action: #selector(showMenu(sender:)))) | ||
26 | + } | ||
27 | + | ||
28 | + @objc | ||
29 | + func showMenu(sender: AnyObject?) { | ||
30 | + becomeFirstResponder() | ||
31 | + let menu = UIMenuController.shared | ||
32 | + if !menu.isMenuVisible { | ||
33 | + menu.setTargetRect(bounds, in: self) | ||
34 | + menu.setMenuVisible(true, animated: true) | ||
35 | + } | ||
36 | + } | ||
37 | + | ||
38 | + override var canBecomeFirstResponder: Bool { | ||
39 | + return true | ||
40 | + } | ||
41 | + | ||
42 | + override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool { | ||
43 | + if action == #selector(UIResponderStandardEditActions.copy(_:)) { | ||
44 | + return true | ||
45 | + } | ||
46 | + return false | ||
47 | + } | ||
48 | + | ||
49 | + override func copy(_ sender: Any?) { | ||
50 | + let board = UIPasteboard.general | ||
51 | + if var textToCopy = text { | ||
52 | + if (textToCopy.contains(", ")) { | ||
53 | + textToCopy = textToCopy.replacingOccurrences(of: ", ", with: "") | ||
54 | + } | ||
55 | + print(textToCopy) | ||
56 | + board.string = textToCopy | ||
57 | + } | ||
58 | + | ||
59 | +// board.string = text | ||
60 | + let menu = UIMenuController.shared | ||
61 | + menu.setMenuVisible(false, animated: true) | ||
62 | + } | ||
63 | + | ||
64 | +} |
... | @@ -8,13 +8,125 @@ | ... | @@ -8,13 +8,125 @@ |
8 | import UIKit | 8 | import UIKit |
9 | 9 | ||
10 | @objc public class CouponViewController: UIViewController { | 10 | @objc public class CouponViewController: UIViewController { |
11 | + @IBOutlet weak var couponImage: UIImageView! | ||
12 | + | ||
13 | + @IBOutlet weak var infoView: UIView! | ||
14 | + @IBOutlet weak var infoImage: UIImageView! | ||
15 | + @IBOutlet weak var infoLabel: UILabel! | ||
16 | + | ||
17 | + @IBOutlet weak var favoriteImage: UIImageView! | ||
18 | + @IBOutlet weak var shareImage: UIImageView! | ||
19 | + | ||
20 | + @IBOutlet weak var titleLabel: UILabel! | ||
21 | + @IBOutlet weak var subtitleLabel: UILabel! | ||
22 | + @IBOutlet weak var expirationLabel: UILabel! | ||
23 | + @IBOutlet weak var detailsLabel: UILabel! | ||
24 | + | ||
25 | + // MARK: - IBOutlets for Coupon Code Section | ||
26 | + @IBOutlet weak var couponCodeContainerView: UIView! | ||
27 | + @IBOutlet weak var couponCodeHeaderView: UIView! | ||
28 | + @IBOutlet weak var couponCodeContentView: UIView! | ||
29 | + | ||
30 | + // Header elements | ||
31 | + @IBOutlet weak var couponCodeTitleLabel: UILabel! | ||
32 | + @IBOutlet weak var couponCodeArrowImage: UIImageView! | ||
33 | + @IBOutlet weak var couponCodeButton: UIButton! | ||
34 | + | ||
35 | + // Content elements (initially hidden) | ||
36 | + @IBOutlet weak var couponCodeValueLabel: CopyableLabel! | ||
37 | + @IBOutlet weak var copyButtonImage: UIImageView! | ||
38 | + @IBOutlet weak var copyButton: UIButton! | ||
39 | + | ||
40 | + // Constraints for animation | ||
41 | + @IBOutlet weak var couponCodeContentHeightConstraint: NSLayoutConstraint! | ||
42 | + | ||
43 | + // MARK: - IBOutlets for Coupon Code Section | ||
44 | + @IBOutlet weak var couponQRContainerView: UIView! | ||
45 | + @IBOutlet weak var couponQRHeaderView: UIView! | ||
46 | + @IBOutlet weak var couponQRContentView: UIView! | ||
47 | + | ||
48 | + // Header elements | ||
49 | + @IBOutlet weak var couponQRTitleLabel: UILabel! | ||
50 | + @IBOutlet weak var couponQRArrowImage: UIImageView! | ||
51 | + @IBOutlet weak var couponQRButton: UIButton! | ||
52 | + | ||
53 | + // Content elements (initially hidden) | ||
54 | + @IBOutlet weak var couponQRImage: UIImageView! | ||
55 | + | ||
56 | + // Constraints for animation | ||
57 | + @IBOutlet weak var couponQRContentHeightConstraint: NSLayoutConstraint! | ||
58 | + | ||
59 | + @IBOutlet weak var termsButton: UIButton! | ||
60 | + @IBOutlet weak var termsLabel: UILabel! | ||
61 | + @IBOutlet weak var termsLabelHeight: NSLayoutConstraint! | ||
62 | + | ||
63 | + @IBOutlet weak var mapButton: UIButton! | ||
64 | + | ||
65 | + @IBOutlet weak var websiteButton: UIButton! | ||
66 | + | ||
11 | var coupon: OfferModel? | 67 | var coupon: OfferModel? |
68 | + private var isDetailsExpanded = false | ||
69 | + private var isCouponCodeExpanded = false | ||
70 | + private var isCouponBarcodeExpanded = false | ||
71 | + private var isTermsExpanded = false | ||
12 | 72 | ||
13 | public override func viewDidLoad() { | 73 | public override func viewDidLoad() { |
14 | super.viewDidLoad() | 74 | super.viewDidLoad() |
15 | 75 | ||
16 | // Show navigation bar for this screen (with back button) | 76 | // Show navigation bar for this screen (with back button) |
17 | self.navigationController?.setNavigationBarHidden(false, animated: false) | 77 | self.navigationController?.setNavigationBarHidden(false, animated: false) |
78 | + setBackButton() | ||
79 | + setNavigationTitle("Προσφορά") | ||
80 | + | ||
81 | + infoView.backgroundColor = UIColor(rgb: 0xFFFFFF) | ||
82 | + infoView.layer.cornerRadius = 10.0 | ||
83 | + infoView.layer.borderWidth = 1.0 | ||
84 | + infoView.layer.borderColor = UIColor(red: 0.01, green: 0.05, blue: 0.11, alpha: 0.19).cgColor | ||
85 | + | ||
86 | + infoImage.image = UIImage(named: "info", in: MyEmptyClass.resourceBundle(), compatibleWith: nil) | ||
87 | + shareImage.image = UIImage(named: "share", in: MyEmptyClass.resourceBundle(), compatibleWith: nil) | ||
88 | + couponCodeArrowImage.image = UIImage(named: "arrow_down", in: MyEmptyClass.resourceBundle(), compatibleWith: nil) | ||
89 | + copyButtonImage.image = UIImage(named: "copy", in: MyEmptyClass.resourceBundle(), compatibleWith: nil) | ||
90 | + couponQRArrowImage.image = UIImage(named: "arrow_down", in: MyEmptyClass.resourceBundle(), compatibleWith: nil) | ||
91 | + couponQRImage.image = UIImage(named: "barcode", in: MyEmptyClass.resourceBundle(), compatibleWith: nil) | ||
92 | + | ||
93 | + infoLabel.font = UIFont(name: "PingLCG-Regular", size: 13) | ||
94 | + infoLabel.textColor = UIColor(rgb: 0x020E1C) | ||
95 | + infoLabel.text = "Περισσότερα" | ||
96 | + | ||
97 | + setupExpandableDetails() | ||
98 | + | ||
99 | + couponCodeContainerView.backgroundColor = UIColor(rgb: 0xFFFFFF) | ||
100 | + couponCodeContainerView.layer.cornerRadius = 8.0 | ||
101 | + | ||
102 | + couponQRContainerView.backgroundColor = UIColor(rgb: 0xFFFFFF) | ||
103 | + couponQRContainerView.layer.cornerRadius = 8.0 | ||
104 | + | ||
105 | + termsButton.titleLabel?.font = UIFont(name: "PingLCG-Bold", size: 16) | ||
106 | +// termsButton.imageView?.layer.transform = CATransform3DMakeScale(1.5, 1.5, 1.5) | ||
107 | + termsButton.setTitle("Όροι Χρήσης", for: .normal) | ||
108 | + termsButton.setTitleColor(UIColor(rgb: 0x020E1C), for: .normal) | ||
109 | + termsButton.setImage(UIImage(named: "arrow_down.png", in: MyEmptyClass.resourceBundle(), compatibleWith: nil), for: .normal) | ||
110 | + termsButton.semanticContentAttribute = .forceRightToLeft | ||
111 | + termsButton.tintColor = UIColor(red: 0.00, green: 0.00, blue: 0.00, alpha: 1.00) | ||
112 | + termsButton.imageEdgeInsets = UIEdgeInsets(top: 0, left: 5, bottom: 0, right: 0); | ||
113 | + termsButton.titleEdgeInsets = UIEdgeInsets(top: 0, left: 0, bottom: 0, right: 5); | ||
114 | + termsButton.imageView?.layer.transform = CATransform3DMakeScale(0.8, 0.8, 0.8) | ||
115 | + | ||
116 | + termsLabelHeight.constant = 0 | ||
117 | + | ||
118 | + mapButton.titleLabel?.font = UIFont(name: "PingLCG-Bold", size: 16) | ||
119 | + mapButton.setTitle("Όροι Χρήσης", for: .normal) | ||
120 | + mapButton.setTitleColor(UIColor(rgb: 0xFFFFFF), for: .normal) | ||
121 | + mapButton.layer.cornerRadius = 4.0 | ||
122 | + | ||
123 | + websiteButton.titleLabel?.font = UIFont(name: "PingLCG-Bold", size: 16) | ||
124 | + websiteButton.setTitle("Όροι Χρήσης", for: .normal) | ||
125 | + websiteButton.setTitleColor(UIColor(rgb: 0x000F1E), for: .normal) | ||
126 | + websiteButton.backgroundColor = .clear | ||
127 | + websiteButton.layer.borderWidth = 1 | ||
128 | + websiteButton.layer.borderColor = UIColor(rgb: 0x000F1E).cgColor | ||
129 | + websiteButton.layer.cornerRadius = 4.0 | ||
18 | 130 | ||
19 | // Configure the view with offer data | 131 | // Configure the view with offer data |
20 | if let offer = coupon { | 132 | if let offer = coupon { |
... | @@ -23,7 +135,59 @@ import UIKit | ... | @@ -23,7 +135,59 @@ import UIKit |
23 | } | 135 | } |
24 | 136 | ||
25 | private func setupUI(with coupon: OfferModel) { | 137 | private func setupUI(with coupon: OfferModel) { |
26 | - // Set up the UI based on the offer data | 138 | + couponImage.image = UIImage(named: coupon.bannerImage, in: MyEmptyClass.resourceBundle(), compatibleWith: nil) |
139 | + favoriteImage.image = UIImage(named: coupon.isFavorite ? "favorite2_filled" : "favorite2_empty", in: MyEmptyClass.resourceBundle(), compatibleWith: nil) | ||
140 | + | ||
141 | + titleLabel.font = UIFont(name: "PingLCG-Bold", size: 24) | ||
142 | + titleLabel.textColor = UIColor(rgb: 0xF2709D) | ||
143 | + titleLabel.text = coupon.title | ||
144 | + | ||
145 | + subtitleLabel.font = UIFont(name: "PingLCG-Regular", size: 18) | ||
146 | + subtitleLabel.textColor = UIColor(rgb: 0x020E1C) | ||
147 | + subtitleLabel.text = coupon.description | ||
148 | + | ||
149 | + expirationLabel.font = UIFont(name: "PingLCG-Regular", size: 18) | ||
150 | + expirationLabel.textColor = UIColor(rgb: 0x020E1C) | ||
151 | +// expirationLabel.text = ("Η προσφορά ισχύει " + coupon.expirationDate) | ||
152 | + expirationLabel.text = "Η προσφορά ισχύει έως 30-09-2025" | ||
153 | + | ||
154 | + couponCodeTitleLabel.font = UIFont(name: "PingLCG-Regular", size: 16) | ||
155 | + couponCodeTitleLabel.textColor = UIColor(rgb: 0x000F1E) | ||
156 | + couponCodeTitleLabel.text = "Κωδικός Κουπονιού" | ||
157 | + | ||
158 | + couponCodeTitleLabel.font = UIFont(name: "PingLCG-Bold", size: 24) | ||
159 | + couponCodeTitleLabel.textColor = UIColor(rgb: 0x000F1E) | ||
160 | + couponCodeTitleLabel.text = "coupons_ab" | ||
161 | + | ||
162 | + couponCodeTitleLabel.font = UIFont(name: "PingLCG-Regular", size: 16) | ||
163 | + couponCodeTitleLabel.textColor = UIColor(rgb: 0x000F1E) | ||
164 | + couponCodeTitleLabel.text = "QR Κουπονιού" | ||
165 | + | ||
166 | + termsLabel.font = UIFont(name: "PingLCG-Regular", size: 16) | ||
167 | + termsLabel.textColor = UIColor(rgb: 0x020E1C) | ||
168 | + termsLabel.text = "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Maecenas sed ex euismod, feugiat justo eu, faucibus urna. Nulla sodales euismod arcu volutpat finibus. Etiam id urna at justo facilisis tempor. Morbi dignissim erat vitae magna sodales dignissim ac in mauris. Mauris tempor convallis tortor, interdum hendrerit turpis eleifend at. Praesent." | ||
27 | } | 169 | } |
28 | 170 | ||
171 | + private func setupExpandableDetails() { | ||
172 | + let fullText = "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Maecenas sed ex euismod, feugiat justo eu, faucibus urna. Nulla sodales euismod arcu volutpat finibus. Etiam id urna at justo facilisis tempor. Morbi dignissim erat vitae magna sodales dignissim ac in mauris. Mauris tempor convallis tortor, interdum hendrerit turpis eleifend at. Praesent." | ||
173 | + | ||
174 | + detailsLabel.text = fullText | ||
175 | + detailsLabel.numberOfLines = 3 | ||
176 | + detailsLabel.font = UIFont(name: "PingLCG-Regular", size: 18) | ||
177 | + detailsLabel.textColor = UIColor(rgb: 0x020E1C) | ||
178 | + | ||
179 | + // Add tap gesture | ||
180 | + let tapGesture = UITapGestureRecognizer(target: self, action: #selector(toggleDetailsExpansion)) | ||
181 | + detailsLabel.isUserInteractionEnabled = true | ||
182 | + detailsLabel.addGestureRecognizer(tapGesture) | ||
183 | + } | ||
184 | + | ||
185 | + @objc private func toggleDetailsExpansion() { | ||
186 | + isDetailsExpanded.toggle() | ||
187 | + | ||
188 | + UIView.animate(withDuration: 0.3) { | ||
189 | + self.detailsLabel.numberOfLines = self.isDetailsExpanded ? 0 : 3 | ||
190 | + self.view.layoutIfNeeded() | ||
191 | + } | ||
192 | + } | ||
29 | } | 193 | } | ... | ... |
This diff is collapsed. Click to expand it.
-
Please register or login to post a comment