在应用程序购买方面,我很失落。我发现有关堆栈溢出的非常可靠的帖子很有帮助。 [Stack Post] [1]但是在此之后我仍然遇到问题。如果我以前从未购买过应用程序内购买商品,而我点击了“恢复”按钮,它将以任何方式解锁。任何帮助都会令人惊讶。
class ViewController: UIViewController, SKProductsRequestDelegate, SKPaymentTransactionObserver {
@IBOutlet weak var nonConsumableLabel: UILabel!
let id_sold = "id_sold"
var productID = ""
var productsRequest = SKProductsRequest()
var iapProducts = [SKProduct]()
var nonConsumablePurchaseMade = UserDefaults.standard.bool(forKey: "nonConsumablePurchaseMade")
override func viewDidLoad() {
super.viewDidLoad()
// Check your In-App Purchases
print("NON CONSUMABLE PURCHASE MADE: \(nonConsumablePurchaseMade)")
if nonConsumablePurchaseMade { nonConsumableLabel.text = "Premium version PURCHASED!"
} else { nonConsumableLabel.text = "Premium version LOCKED!"}
// Fetch IAP Products available
fetchAvailableProducts()
}
@IBAction func nonConsumableBtn(_ sender: Any) {
purchaseMyProduct(product: iapProducts[0])
}
@IBAction func printer(_ sender: Any) {
print(iapProducts)
}
// MARK: - RESTORE NON-CONSUMABLE PURCHASE BUTTON
@IBAction func restorePurchaseButt(_ sender: Any) {
SKPaymentQueue.default().add(self)
SKPaymentQueue.default().restoreCompletedTransactions()
}
func paymentQueueRestoreCompletedTransactionsFinished(_ queue: SKPaymentQueue) {
nonConsumablePurchaseMade = true
UserDefaults.standard.set(nonConsumablePurchaseMade, forKey: "nonConsumablePurchaseMade")
let alert = UIAlertController(title: "IAP Tutorial", message: "You've successfully restored your purchase!", preferredStyle: .alert)
alert.addAction(UIAlertAction(title: "Close", style: .cancel, handler: nil))
self.present(alert, animated: true)
func paymentQueueRestoreCompletedTransactionsFinished(_ queue: SKPaymentQueue) {
for transaction in queue.transactions {
let t: SKPaymentTransaction = transaction
let prodID = t.payment.productIdentifier as String
switch prodID {
case "id_sold":
// implement the given in-app purchase as if it were bought
print("Second IAP restored")
default:
print("iap not found")
}
}
}
}
// MARK: - FETCH AVAILABLE IAP PRODUCTS
func fetchAvailableProducts() {
// Put here your IAP Products ID's
let productIdentifiers = NSSet(objects:
id_sold
)
productsRequest = SKProductsRequest(productIdentifiers: productIdentifiers as! Set<String>)
productsRequest.delegate = self
productsRequest.start()
}
// MARK: - REQUEST IAP PRODUCTS
func productsRequest (_ request:SKProductsRequest, didReceive response:SKProductsResponse) {
if (response.products.count > 0) {
iapProducts = response.products
// Get its price from iTunes Connect
let numberFormatter = NumberFormatter()
numberFormatter.formatterBehavior = .behavior10_4
numberFormatter.numberStyle = .currency
// 2nd IAP Product (Non-Consumable) ------------------------------
let secondProd = response.products[0] as SKProduct
// Get its price from iTunes Connect
numberFormatter.locale = secondProd.priceLocale
}
}
// MARK: - MAKE PURCHASE OF A PRODUCT
func canMakePurchases() -> Bool { return SKPaymentQueue.canMakePayments() }
func purchaseMyProduct(product: SKProduct) {
if self.canMakePurchases() {
let payment = SKPayment(product: product)
SKPaymentQueue.default().add(self)
SKPaymentQueue.default().add(payment)
print("PRODUCT TO PURCHASE: \(product.productIdentifier)")
productID = product.productIdentifier
// IAP Purchases dsabled on the Device
} else {
let alert = UIAlertController(title: "IAP Tutorial", message: "You've successfully restored your purchase!", preferredStyle: .alert)
alert.addAction(UIAlertAction(title: "Close", style: .cancel, handler: nil))
self.present(alert, animated: true)
}
}
// MARK:- IAP PAYMENT QUEUE
func paymentQueue(_ queue: SKPaymentQueue, updatedTransactions transactions: [SKPaymentTransaction]) {
for transaction:AnyObject in transactions {
if let trans = transaction as? SKPaymentTransaction {
switch trans.transactionState {
case .purchased:
SKPaymentQueue.default().finishTransaction(transaction as! SKPaymentTransaction)
if productID == id_sold {
// Save your purchase locally (needed only for Non-Consumable IAP)
nonConsumablePurchaseMade = true
UserDefaults.standard.set(nonConsumablePurchaseMade, forKey: "nonConsumablePurchaseMade")
nonConsumableLabel.text = "Premium version PURCHASED!"
let alert = UIAlertController(title: "IAP Tutorial", message: "You've successfully unlocked the Premium version!", preferredStyle: .alert)
alert.addAction(UIAlertAction(title: "Close", style: .cancel, handler: nil))
self.present(alert, animated: true)
}
break
case .failed:
SKPaymentQueue.default().finishTransaction(transaction as! SKPaymentTransaction)
break
case .restored:
SKPaymentQueue.default().finishTransaction(transaction as! SKPaymentTransaction)
break
default: break
}
}
}
}
答案 0 :(得分:0)
你在说
divmod
但是即使没有任何恢复,该方法也会被调用。它的全部意思是恢复交互是 over ,而不是成功。但是您要继续前进,就好像它成功了一样,并向您的用户授予神奇的用户默认密钥。