662 lines
30 KiB
Swift
662 lines
30 KiB
Swift
//
|
|
// SwapControllerInvestment.swift
|
|
// Wallet
|
|
//
|
|
// Created by Saveliy Stavitsky on 3/25/21.
|
|
// Copyright © 2021 AM. All rights reserved.
|
|
//
|
|
|
|
import UIKit
|
|
|
|
// swiftlint:disable:next type_body_length
|
|
final class SwapControllerInvestment: UIViewController {
|
|
|
|
let service = Swap.Service.Investment()
|
|
|
|
@IBOutlet private weak var scrollView: UIScrollView!
|
|
|
|
@IBOutlet private weak var tokenGiveView: CommonViewCard!
|
|
@IBOutlet private weak var tokenGetView: CommonViewCard!
|
|
|
|
@IBOutlet private weak var conversionRateStackView: UIStackView!
|
|
@IBOutlet private weak var forwardConversionRate: UILabel!
|
|
@IBOutlet private weak var backwardConversionRate: UILabel!
|
|
@IBOutlet private weak var poolSize: UILabel!
|
|
@IBOutlet private weak var poolLiquidity: UILabel!
|
|
@IBOutlet private weak var newPoolWarning: UIView!
|
|
|
|
@IBOutlet private weak var addRemoveLiquidityStackView: UIStackView!
|
|
@IBOutlet private weak var liquidityView: CommonViewCard!
|
|
@IBOutlet private weak var segCtrl: UISegmentedControl!
|
|
|
|
@IBOutlet private weak var conversionFieldsStackView: UIStackView!
|
|
@IBOutlet private weak var amount1TextField: CommonTextField!
|
|
@IBOutlet private weak var amount2TextField: CommonTextField!
|
|
|
|
@IBOutlet private weak var minimumTextField: CommonTextField!
|
|
@IBOutlet private weak var countStackView: UIStackView!
|
|
|
|
@IBOutlet private weak var createPoolStackView: UIStackView!
|
|
|
|
@IBOutlet private weak var removeYouGetStackView: UIStackView!
|
|
@IBOutlet private weak var removeYouGetToken1: UILabel!
|
|
@IBOutlet private weak var removeYouGetToken2: UILabel!
|
|
@IBOutlet private weak var removeYouGetToken1TextField: CommonTextField!
|
|
@IBOutlet private weak var removeYouGetToken2TextField: CommonTextField!
|
|
|
|
@IBOutlet private weak var newPooolFieldsStackView: UIStackView!
|
|
@IBOutlet private weak var newAmount1TextField: CommonTextField!
|
|
@IBOutlet private weak var newAmount2TextField: CommonTextField!
|
|
|
|
@IBOutlet private weak var newExchangeRateStackView: UIStackView!
|
|
@IBOutlet private weak var newExchangeRate: UILabel!
|
|
@IBOutlet private weak var newBackwardExchangeRate: UILabel!
|
|
|
|
@IBOutlet var swapButton: CommonButtonAction!
|
|
|
|
var startAction: SwapActionType = .add
|
|
|
|
override func viewDidLoad() {
|
|
super.viewDidLoad()
|
|
|
|
title = L10n.Swap.Investment.title
|
|
navigationItem.leftBarButtonItem = .pop(self)
|
|
tabBarItem.title = L10n.Swap.Main.TabBar.title
|
|
|
|
tokenGiveView.action = .cards(collection: nil)
|
|
tokenGetView.action = .cards(collection: nil)
|
|
liquidityView.isEnabled = false
|
|
|
|
segCtrl.setTitle(L10n.Swap.Investment.PoolToken.addTitle, forSegmentAt: 0)
|
|
segCtrl.setTitle(L10n.Swap.Investment.PoolToken.removeTitle, forSegmentAt: 1)
|
|
segCtrl.setTitleTextAttributes([.foregroundColor: UIColor.white], for: .selected)
|
|
|
|
removeYouGetToken1.isHidden = true
|
|
removeYouGetToken2.isHidden = true
|
|
for textField in [amount1TextField, amount2TextField, minimumTextField, newAmount1TextField, newAmount2TextField, removeYouGetToken1TextField, removeYouGetToken2TextField] {
|
|
textField?.delegate = self
|
|
textField?.keyboardType = .decimalPad
|
|
}
|
|
minimumTextField.precision = 0
|
|
|
|
swapButton.isHidden = true
|
|
|
|
service.didUpdate = { [weak self] in
|
|
self?.setupTokensViews()
|
|
}
|
|
|
|
observers.append(contentsOf: [
|
|
Notification.subscribe(name: .didUpdateBalances) { [weak self] _ in
|
|
guard let self = self else { return }
|
|
self.service.tokenGive = self.service.swappableBalances.first(where: {$0.symbol == self.service.tokenGive?.symbol})
|
|
self.service.tokenGet = self.service.swappableBalances.first(where: {$0.symbol == self.service.tokenGet?.symbol})
|
|
self.setupTokensViews()
|
|
}
|
|
])
|
|
|
|
self.selectActionType(type: self.startAction)
|
|
}
|
|
|
|
var observers: [AnyObject] = []
|
|
deinit { observers.forEach({ Notification.unsubscribe(observer: $0) }) }
|
|
|
|
override func viewWillAppear(_ animated: Bool) {
|
|
super.viewWillAppear(animated)
|
|
Accounts().isLocked = true
|
|
service.fetch {
|
|
Alert.error($0)
|
|
}
|
|
|
|
if self.service.tokenGive != nil &&
|
|
self.service.tokenGet != nil {
|
|
self.setupTokensViews()
|
|
}
|
|
}
|
|
|
|
override func viewWillDisappear(_ animated: Bool) {
|
|
super.viewWillDisappear(animated)
|
|
Accounts().isLocked = false
|
|
}
|
|
|
|
var selectedReturnAmountIndex: Int? {
|
|
didSet {
|
|
if selectedReturnAmountIndex != nil {
|
|
minimumTextField.resignFirstResponder()
|
|
removeYouGetToken1TextField.resignFirstResponder()
|
|
removeYouGetToken2TextField.resignFirstResponder()
|
|
}
|
|
}
|
|
}
|
|
func setupCountStackView() {
|
|
countStackView.arrangedSubviews.forEach({ $0.removeFromSuperview() })
|
|
countStackView.addArrangedSubview(
|
|
.button(style: selectedReturnAmountIndex != 0 ? .secondary : .primary,
|
|
title: "10%", size: .small, action: { [weak self] in
|
|
self?.selectedReturnAmountIndex = 0
|
|
if let amount = self?.service.yourPoolSupply?.amount {
|
|
self?.service.update(minimum: (amount * 0.1).toReadebleString(precisionMax: 0))
|
|
}
|
|
self?.setupTokensViews()
|
|
})
|
|
)
|
|
countStackView.addArrangedSubview(
|
|
.button(style: selectedReturnAmountIndex != 1 ? .secondary : .primary,
|
|
title: "25%", size: .small, action: { [weak self] in
|
|
self?.selectedReturnAmountIndex = 1
|
|
if let amount = self?.service.yourPoolSupply?.amount {
|
|
self?.service.update(minimum: (amount * 0.25).toReadebleString(precisionMax: 0))
|
|
}
|
|
self?.setupTokensViews()
|
|
})
|
|
)
|
|
countStackView.addArrangedSubview(
|
|
.button(style: selectedReturnAmountIndex != 2 ? .secondary : .primary,
|
|
title: "50%", size: .small, action: { [weak self] in
|
|
self?.selectedReturnAmountIndex = 2
|
|
if let amount = self?.service.yourPoolSupply?.amount {
|
|
self?.service.update(minimum: (amount * 0.5).toReadebleString(precisionMax: 0))
|
|
}
|
|
self?.setupTokensViews()
|
|
})
|
|
)
|
|
countStackView.addArrangedSubview(
|
|
.button(style: selectedReturnAmountIndex != 3 ? .secondary : .primary,
|
|
title: "100%", size: .small, action: { [weak self] in
|
|
self?.selectedReturnAmountIndex = 3
|
|
if let amount = self?.service.yourPoolSupply?.amount {
|
|
self?.service.update(minimum: (amount * 1.0).toReadebleString(precisionMax: 0))
|
|
}
|
|
self?.setupTokensViews()
|
|
})
|
|
)
|
|
}
|
|
|
|
// swiftlint:disable:next function_body_length
|
|
func setupTokensViews() {
|
|
self.tokenGiveView.action = self.setupTokenCard(isGet: false)
|
|
|
|
self.tokenGetView.action = self.setupTokenCard(isGet: true)
|
|
|
|
conversionRateStackView.isHidden = service.tokenGive == nil || service.tokenGet == nil || service.pool == nil
|
|
addRemoveLiquidityStackView.isHidden = service.tokenGive == nil || service.tokenGet == nil || service.pool == nil
|
|
newPoolWarning.isHidden = service.tokenGive == nil || service.tokenGet == nil || service.pool != nil
|
|
createPoolStackView.isHidden = service.tokenGive == nil || service.tokenGet == nil || service.pool != nil
|
|
newExchangeRateStackView.isHidden = service.tokenGive == nil || service.tokenGet == nil || service.pool != nil
|
|
conversionFieldsStackView.isHidden = segCtrl.selectedSegmentIndex == 1
|
|
minimumTextField.isHidden = segCtrl.selectedSegmentIndex == 0
|
|
removeYouGetStackView.isHidden = segCtrl.selectedSegmentIndex == 0
|
|
swapButton.isHidden = true
|
|
countStackView.superview?.isHidden = true
|
|
|
|
guard let tokenGive = service.tokenGive,
|
|
let tokenGet = service.tokenGet else {
|
|
return
|
|
}
|
|
|
|
removeYouGetToken1TextField.lzPlaceholder = tokenGive.symbol
|
|
removeYouGetToken1TextField.lzTitle = tokenGive.symbol
|
|
removeYouGetToken2TextField.lzPlaceholder = tokenGet.symbol
|
|
removeYouGetToken2TextField.lzTitle = tokenGet.symbol
|
|
|
|
setupCountStackView()
|
|
|
|
let giveImg = UIImageView(image: UIImage.from(token: tokenGive))
|
|
giveImg.addHeightWidthConstraints(height: 24, width: 24)
|
|
newAmount1TextField.accessoryView = giveImg
|
|
newAmount1TextField.value = service.newAmountSend
|
|
newAmount1TextField.error = service.newAmountSendError
|
|
|
|
let getImg = UIImageView(image: UIImage.from(token: tokenGet))
|
|
getImg.addHeightWidthConstraints(height: 24, width: 24)
|
|
newAmount2TextField.accessoryView = getImg
|
|
newAmount2TextField.value = service.newAmountReceive
|
|
newAmount2TextField.error = service.newAmountReceiveError
|
|
|
|
swapButton.isHidden = false
|
|
|
|
if let newAmountSend = service.newAmountSend.toOptionalDecimal(),
|
|
let newAmountReceive = service.newAmountReceive.toOptionalDecimal() {
|
|
newExchangeRateStackView.isHidden = false
|
|
newExchangeRate.lzText = "\(Decimal(1).toString(precision: tokenGive)) = \((newAmountReceive / newAmountSend).toString(precision: tokenGet))"
|
|
newBackwardExchangeRate.lzText = "\(Decimal(1).toString(precision: tokenGet)) = \((newAmountSend / newAmountReceive).toString(precision: tokenGive))"
|
|
} else {
|
|
newExchangeRateStackView.isHidden = true
|
|
}
|
|
|
|
guard let pool = service.pool else {
|
|
swapButton.lzTitle = L10n.Swap.Investment.AddPool.buttonTitle
|
|
swapButton.isEnabled = !createPoolStackView.isHidden
|
|
&& !newAmount1TextField.value.isEmpty
|
|
&& !newAmount2TextField.value.isEmpty
|
|
&& service.newAmountSend.toDecimal() > 0
|
|
&& service.newAmountReceive.toDecimal() > 0
|
|
&& service.newAmountSendError == nil
|
|
&& service.newAmountReceiveError == nil
|
|
return
|
|
}
|
|
|
|
forwardConversionRate.lzText = "\(Decimal(1).toString(precision: tokenGive)) ≈ \(pool.forwardExchangeRate.toString(precision: tokenGet))"
|
|
backwardConversionRate.lzText = "\(Decimal(1).toString(precision: tokenGet)) ≈ \(pool.backwardExchangeRate.toString(precision: tokenGive))"
|
|
|
|
poolSize.lzText = "\(pool.token1?.amount.toString(precision: tokenGive) ?? "") / \(pool.token2?.amount.toString(precision: tokenGet) ?? "")"
|
|
|
|
if let supplyTokens = service.poolSupply {
|
|
poolLiquidity.lzText = "\(supplyTokens.amount.toString(precision: supplyTokens))"
|
|
}
|
|
|
|
liquidityView.action = .select(
|
|
icon: UIImage(),
|
|
kind: .cards,
|
|
title: L10n.Common.Card.Token.title,
|
|
empty: .cardsTokensEmpty(),
|
|
collection: (service.yourPoolSupply != nil ? [service.yourPoolSupply!] : [])
|
|
.map({ $0.toMenu() }),
|
|
selected: service.yourPoolSupply?.toMenu(),
|
|
completion: { _ in }
|
|
)
|
|
|
|
let giveImage = UIImageView(image: UIImage.from(token: tokenGive))
|
|
giveImage.addHeightWidthConstraints(height: 24, width: 24)
|
|
amount1TextField.accessoryView = giveImage
|
|
amount1TextField.value = service.amountSend
|
|
amount1TextField.error = service.amountSendError
|
|
|
|
let getImage = UIImageView(image: UIImage.from(token: tokenGet))
|
|
getImage.addHeightWidthConstraints(height: 24, width: 24)
|
|
amount2TextField.accessoryView = getImage
|
|
amount2TextField.value = service.amountReceive
|
|
amount2TextField.error = service.amountReceiveError
|
|
|
|
let lImage = UIImageView(image: Asset.tokenSwap.image)
|
|
lImage.addHeightWidthConstraints(height: 24, width: 24)
|
|
minimumTextField.accessoryView = lImage
|
|
minimumTextField.value = service.amountMinimum
|
|
minimumTextField.error = service.amountMinimumError
|
|
|
|
if let minAmount = service.amountMinimum.toOptionalDecimal(),
|
|
let poolSupply = service.poolSupply?.amount,
|
|
let token1 = pool.token1,
|
|
let token2 = pool.token2,
|
|
segCtrl.selectedSegmentIndex == 1 {
|
|
// removeYouGetStackView.isHidden = false
|
|
DispatchQueue.main.asyncAfter(deadline: .now() + 0.3, execute: {
|
|
let bottomOffset = CGPoint(x: 0, y: self.scrollView.contentSize.height - self.scrollView.bounds.height + self.scrollView.contentInset.bottom)
|
|
self.scrollView.setContentOffset(bottomOffset, animated: true)
|
|
})
|
|
removeYouGetToken1.lzText = "≈ \((token1.amount * minAmount / poolSupply).toString(precision: token1))"
|
|
removeYouGetToken2.lzText = "≈ \((token2.amount * minAmount / poolSupply).toString(precision: token2))"
|
|
|
|
if !removeYouGetToken1TextField.isFirstResponder {
|
|
var amount = token1.amount * minAmount / poolSupply
|
|
if token1.isCash { amount = amount.receive(precision: token1.precision) }
|
|
if amount <= 0 { amount = 0 }
|
|
removeYouGetToken1TextField.value = "≈\(amount.toReadebleString(precisionMax: token1.precision))"
|
|
|
|
if minAmount == 0 {
|
|
removeYouGetToken1TextField.value = "≈\(Decimal(0).toReadebleString(precisionMax: token1.precision))"
|
|
}
|
|
}
|
|
|
|
if !removeYouGetToken2TextField.isFirstResponder {
|
|
var amount = token2.amount * minAmount / poolSupply
|
|
if token2.isCash { amount = amount.receive(precision: token2.precision) }
|
|
if amount <= 0 { amount = 0 }
|
|
removeYouGetToken2TextField.value = "≈\(amount.toReadebleString(precisionMax: token2.precision))"
|
|
|
|
if minAmount == 0 {
|
|
removeYouGetToken2TextField.value = "≈\(Decimal(0).toReadebleString(precisionMax: token2.precision))"
|
|
}
|
|
}
|
|
} else {
|
|
// removeYouGetStackView.isHidden = true
|
|
removeYouGetToken1TextField.value = "≈"
|
|
removeYouGetToken2TextField.value = "≈"
|
|
}
|
|
|
|
if service.pool == nil {
|
|
swapButton.lzTitle = L10n.Swap.Investment.AddPool.buttonTitle
|
|
swapButton.isEnabled = !createPoolStackView.isHidden
|
|
&& !newAmount1TextField.value.isEmpty
|
|
&& !newAmount2TextField.value.isEmpty
|
|
&& service.newAmountSend.toDecimal() > 0
|
|
&& service.newAmountReceive.toDecimal() > 0
|
|
&& service.newAmountSendError == nil
|
|
&& service.newAmountReceiveError == nil
|
|
} else if !conversionFieldsStackView.isHidden {
|
|
swapButton.lzTitle = L10n.Swap.Investment.PoolToken.addButtonTitle
|
|
swapButton.isEnabled = !conversionFieldsStackView.isHidden
|
|
&& !amount1TextField.value.isEmpty
|
|
&& !amount2TextField.value.isEmpty
|
|
&& service.amountSend.toDecimal() > 0
|
|
&& service.amountReceive.toDecimal() > 0
|
|
&& service.amountSendError == nil
|
|
&& service.amountReceiveError == nil
|
|
} else if !minimumTextField.isHidden {
|
|
swapButton.lzTitle = L10n.Swap.Investment.PoolToken.removeButtonTitle
|
|
countStackView.superview?.isHidden = false
|
|
swapButton.isEnabled = !minimumTextField.isHidden
|
|
&& !minimumTextField.value.isEmpty
|
|
&& service.amountMinimumError == nil
|
|
&& service.amountMinimum.toDecimal() > 0
|
|
}
|
|
}
|
|
|
|
private func setupTokenCard(isGet: Bool) -> CommonMenuAction {
|
|
let excludedToken = isGet ? self.service.tokenGive : self.service.tokenGet
|
|
return .cards(tokens: self.service.swappableBalances.filter({$0 != excludedToken}), selected: isGet ? self.service.tokenGet : self.service.tokenGive, { [weak self] in
|
|
guard let self else { return }
|
|
isGet ? (self.service.tokenGet = self.service.swappableBalances.object(menu: $0)) : (self.service.tokenGive = self.service.swappableBalances.object(menu: $0))
|
|
self.amount1TextField.precision = self.service.swappableBalances.object(menu: $0)?.precision
|
|
self.newAmount1TextField.precision = self.service.swappableBalances.object(menu: $0)?.precision
|
|
self.setupTokensViews()
|
|
})
|
|
}
|
|
|
|
@IBAction private func onChange(_: AnyObject?) {
|
|
self.setupTokensViews()
|
|
}
|
|
|
|
@IBAction func swapPressed(_ sender: Any) {
|
|
view.endEditing(true)
|
|
|
|
guard let tokenGive = service.tokenGive,
|
|
let tokenGet = service.tokenGet else {
|
|
return
|
|
}
|
|
|
|
if service.pool == nil {
|
|
let views: [UIView] = [
|
|
.label(
|
|
text: L10n.Swap.Investment.CreateConfirmation.description
|
|
.attributed(style: .regular, size: 14, color: Asset.textCoal.color),
|
|
numberOfLines: 0
|
|
),
|
|
.field(
|
|
title: L10n.Swap.Investment.CreateConfirmation.give,
|
|
text: service.newAmountSend.toDecimal().toString(max: tokenGive)
|
|
+ "\n" + service.newAmountReceive.toDecimal().toString(max: tokenGet)
|
|
)
|
|
]
|
|
Popup.show(title: L10n.Common.Title.confirmation, views: views, submit: L10n.Common.Button.confirm, in: self) { ctrl in
|
|
AccountViewAuthorize.showGetPrivateKey(in: self) {
|
|
Loader.show(in: ctrl)
|
|
|
|
self.service.submitCreate(privateKey: $0) { (trxId, lqtoken, error) in
|
|
ctrl.dismiss(animated: true)
|
|
Alert.notify(error)
|
|
|
|
let views: [UIView] =
|
|
[
|
|
.field(
|
|
title: L10n.Swap.Investment.Success.debited,
|
|
text: (self.service.newAmountSend.toOptionalDecimal()?.toString(max: tokenGive) ?? "")
|
|
+ "\n" + (self.service.newAmountReceive.toOptionalDecimal()?.toString(max: tokenGet) ?? "")
|
|
),
|
|
.field(
|
|
title: L10n.Swap.Investment.Success.liquidityGet,
|
|
text: lqtoken
|
|
)
|
|
]
|
|
|
|
trxId.flatMap { self.showCompletion(transactionId: $0, views: views) }
|
|
}
|
|
}
|
|
}
|
|
} else if segCtrl.selectedSegmentIndex == 0 && service.pool != nil {
|
|
let views: [UIView] = [
|
|
.label(
|
|
text: L10n.Swap.Investment.AddConfirmation.description
|
|
.attributed(style: .regular, size: 14, color: Asset.textCoal.color),
|
|
numberOfLines: 0
|
|
),
|
|
.field(
|
|
title: L10n.Swap.Investment.AddConfirmation.give,
|
|
text: service.amountSend.toDecimal().toString(max: tokenGive)
|
|
+ "\n" + service.amountReceive.toDecimal().toString(max: tokenGet)
|
|
)
|
|
]
|
|
|
|
Popup.show(title: L10n.Common.Title.confirmation,
|
|
views: views,
|
|
submit: L10n.Common.Button.confirm,
|
|
in: self) { ctrl in
|
|
|
|
AccountViewAuthorize.showGetPrivateKey(in: self) {
|
|
Loader.show(in: ctrl)
|
|
|
|
let amountSend = self.service.amountSend.toOptionalDecimal()?.toString(max: tokenGive)
|
|
let amountReceive = self.service.amountReceive.toOptionalDecimal()?.toString(max: tokenGet)
|
|
|
|
self.service.submitAdd(privateKey: $0) { (trxId, lqtoken, error) in
|
|
|
|
ctrl.dismiss(animated: true)
|
|
|
|
Alert.notify(error)
|
|
|
|
let views: [UIView] =
|
|
[
|
|
.field(
|
|
title: L10n.Swap.Investment.Success.debited,
|
|
text: (amountSend ?? "") + "\n" + (amountReceive ?? "")
|
|
),
|
|
.field(
|
|
title: L10n.Swap.Investment.Success.liquidityGet,
|
|
text: lqtoken
|
|
)
|
|
]
|
|
|
|
trxId.flatMap { self.showCompletion(transactionId: $0, views: views) }
|
|
}
|
|
}
|
|
}
|
|
} else if segCtrl.selectedSegmentIndex == 1 && service.pool != nil {
|
|
var views: [UIView] = [
|
|
.label(
|
|
text: L10n.Swap.Investment.RemoveConfirmation.description
|
|
.attributed(style: .regular, size: 14, color: Asset.textCoal.color),
|
|
numberOfLines: 0
|
|
)
|
|
]
|
|
|
|
if let poolSupply = service.poolSupply {
|
|
views.append(
|
|
.field(
|
|
title: L10n.Swap.Investment.RemoveConfirmation.give,
|
|
text: service.amountMinimum.toDecimal().toString(max: poolSupply)
|
|
)
|
|
)
|
|
}
|
|
|
|
if let minAmount = service.amountMinimum.toOptionalDecimal(),
|
|
let poolSupply = service.poolSupply?.amount,
|
|
let token1 = service.pool?.token1,
|
|
let token2 = service.pool?.token2 {
|
|
views.append(
|
|
.field(
|
|
title: L10n.Swap.Investment.RemoveConfirmation.get,
|
|
text: ("\(self.removeYouGetToken1TextField.value) \(token1.symbol)"
|
|
+ "\n" + "\(self.removeYouGetToken2TextField.value) \(token2.symbol)")
|
|
.replacingOccurrences(of: "≈", with: "≈ ")
|
|
)
|
|
)
|
|
}
|
|
|
|
Popup.show(title: L10n.Common.Title.confirmation, views: views, submit: L10n.Common.Button.confirm, in: self) { ctrl in
|
|
AccountViewAuthorize.showGetPrivateKey(in: self) {
|
|
Loader.show(in: ctrl)
|
|
self.service.submitRemove(privateKey: $0) { (id, error) in
|
|
// Loader.hide(in: ctrl)
|
|
ctrl.dismiss(animated: true)
|
|
Alert.notify(error)
|
|
|
|
var views: [UIView] =
|
|
[
|
|
.field(
|
|
title: L10n.Swap.Investment.Success.return,
|
|
text: (self.service.amountMinimum.toOptionalDecimal()?.toString(max: self.service.poolSupply) ?? "")
|
|
)
|
|
]
|
|
|
|
if let minAmount = self.service.amountMinimum.toOptionalDecimal(),
|
|
let poolSupply = self.service.poolSupply?.amount,
|
|
let token1 = self.service.pool?.token1,
|
|
let token2 = self.service.pool?.token2 {
|
|
views.append(
|
|
.field(
|
|
title: L10n.Swap.Investment.Success.got,
|
|
text: ("\(self.removeYouGetToken1TextField.value) \(token1.symbol)"
|
|
+ "\n" + "\(self.removeYouGetToken2TextField.value) \(token2.symbol)")
|
|
.replacingOccurrences(of: "≈", with: "")
|
|
)
|
|
)
|
|
}
|
|
|
|
id.flatMap { self.showCompletion(transactionId: $0, views: views) }
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
private func showCompletion(transactionId: String, views: [UIView]) {
|
|
let views = views +
|
|
[
|
|
.field(
|
|
title: L10n.Swap.Investment.Success.Transaction.id,
|
|
text: transactionId,
|
|
rightButtonAvailbale: true,
|
|
rightButtonImage: Asset.commonCopy.image,
|
|
rightButtonAction: {
|
|
Alert.copy(transactionId)
|
|
}
|
|
)
|
|
]
|
|
|
|
Popup.show(title: L10n.Swap.Main.Success.title,
|
|
views: views,
|
|
submit: L10n.Common.Button.checkOnBloksIO,
|
|
submitStyle: .outline,
|
|
cancel: L10n.Common.Button.done,
|
|
in: self) { ctrl in
|
|
guard let checkTransactionUrl = URL(transactionId: transactionId) else { return }
|
|
|
|
UIApplication.shared.open(checkTransactionUrl, options: [:], completionHandler: nil)
|
|
}
|
|
|
|
self.clear()
|
|
}
|
|
|
|
private func clear() {
|
|
selectedReturnAmountIndex = nil
|
|
service.update(send: "")
|
|
service.update(receive: "")
|
|
service.update(newReceive: "")
|
|
service.update(newSend: "")
|
|
service.update(minimum: "")
|
|
}
|
|
|
|
func selectActionType(type: SwapActionType) {
|
|
switch type {
|
|
case .add:
|
|
self.segCtrl.selectedSegmentIndex = 0
|
|
case .withdraw:
|
|
self.segCtrl.selectedSegmentIndex = 1
|
|
}
|
|
|
|
setupTokensViews()
|
|
}
|
|
}
|
|
|
|
extension SwapControllerInvestment: CommonTextFieldDelegate {
|
|
|
|
func textField(_ textField: CommonTextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
|
|
let newString = (textField.value as NSString).replacingCharacters(in: range, with: string)
|
|
switch textField {
|
|
case removeYouGetToken1TextField:
|
|
if newString.contains("≈") && !newString.starts(with: "≈") {
|
|
return false
|
|
}
|
|
if let precision = service.pool?.token1?.precision,
|
|
newString.replacingOccurrences(of: "≈", with: "").precision > precision {
|
|
return false
|
|
}
|
|
case removeYouGetToken2TextField:
|
|
if newString.contains("≈") && !newString.starts(with: "≈") {
|
|
return false
|
|
}
|
|
if let precision = service.pool?.token2?.precision,
|
|
newString.replacingOccurrences(of: "≈", with: "").precision > precision {
|
|
return false
|
|
}
|
|
default:
|
|
break
|
|
}
|
|
return true
|
|
}
|
|
|
|
func textFieldDidChange(_ textField: CommonTextField) {
|
|
switch textField {
|
|
case amount1TextField:
|
|
textField.value = textField.value.replacingOccurrences(of: ",", with: ".")
|
|
let newPosition = textField.textField.endOfDocument
|
|
textField.textField.selectedTextRange = textField.textField.textRange(from: newPosition, to: newPosition)
|
|
service.update(send: textField.value)
|
|
case amount2TextField:
|
|
textField.value = textField.value.replacingOccurrences(of: ",", with: ".")
|
|
let newPosition = textField.textField.endOfDocument
|
|
textField.textField.selectedTextRange = textField.textField.textRange(from: newPosition, to: newPosition)
|
|
service.update(receive: textField.value)
|
|
case minimumTextField:
|
|
selectedReturnAmountIndex = nil
|
|
let newPosition = textField.textField.endOfDocument
|
|
textField.textField.selectedTextRange = textField.textField.textRange(from: newPosition, to: newPosition)
|
|
service.update(minimum: textField.value)
|
|
case newAmount1TextField:
|
|
textField.value = textField.value.replacingOccurrences(of: ",", with: ".")
|
|
let newPosition = textField.textField.endOfDocument
|
|
textField.textField.selectedTextRange = textField.textField.textRange(from: newPosition, to: newPosition)
|
|
service.update(newSend: textField.value)
|
|
case newAmount2TextField:
|
|
textField.value = textField.value.replacingOccurrences(of: ",", with: ".")
|
|
let newPosition = textField.textField.endOfDocument
|
|
textField.textField.selectedTextRange = textField.textField.textRange(from: newPosition, to: newPosition)
|
|
service.update(newReceive: textField.value)
|
|
case removeYouGetToken1TextField:
|
|
selectedReturnAmountIndex = nil
|
|
textField.value = textField.value.replacingOccurrences(of: ",", with: ".")
|
|
let newPosition = textField.textField.endOfDocument
|
|
textField.textField.selectedTextRange = textField.textField.textRange(from: newPosition, to: newPosition)
|
|
if !textField.value.starts(with: "≈") { textField.value = "≈\(textField.value)" }
|
|
if let poolSupply = service.poolSupply?.amount,
|
|
let token1 = service.pool?.token1,
|
|
let token2 = service.pool?.token2 {
|
|
|
|
let minimum = textField.value.replacingOccurrences(of: "≈", with: "").toDecimal() * poolSupply / token1.amount
|
|
service.update(minimum: "\(minimum.roundUp(to: 0).toReadebleString(precisionMax: 0))")
|
|
}
|
|
case removeYouGetToken2TextField:
|
|
selectedReturnAmountIndex = nil
|
|
textField.value = textField.value.replacingOccurrences(of: ",", with: ".")
|
|
let newPosition = textField.textField.endOfDocument
|
|
textField.textField.selectedTextRange = textField.textField.textRange(from: newPosition, to: newPosition)
|
|
if !textField.value.starts(with: "≈") { textField.value = "≈\(textField.value)" }
|
|
if let poolSupply = service.poolSupply?.amount,
|
|
let token1 = service.pool?.token1,
|
|
let token2 = service.pool?.token2 {
|
|
|
|
let minimum = textField.value.replacingOccurrences(of: "≈", with: "").toDecimal() * poolSupply / token2.amount
|
|
service.update(minimum: "\(minimum.roundUp(to: 0).toReadebleString(precisionMax: 0))")
|
|
}
|
|
default:
|
|
break
|
|
}
|
|
}
|
|
}
|
|
|
|
extension SwapControllerInvestment {
|
|
enum SwapActionType {
|
|
case add
|
|
case withdraw
|
|
}
|
|
}
|