1. 內購——應用內購買
我所說的內購——也可以說是應用內購買
大家都知道通過蘋果應用程序商店有三種主要賺錢的方式:
1.直接收費(與國內大部分用戶的消費習慣相悖,如果要收費,直接收高的,別收6塊錢)
2.廣告(降低用戶體驗 應用程序名稱帶Lite可以添加廣告)
3.內購
至於設計哪些賣錢?產品經理需要認真考慮和調研的。記錄用戶行為是可以幫助產品經理確認哪些收費!
所以要做好游戲,一定要研究心理,要研究哲學,哈哈。
2.內購的類別有哪幾種呢?
在游戲中我們經常用到的主要由分兩種:
非消耗品(Nonconsumable)買了就有,頭銜,功能
指的是在游戲中一次性購買並擁有永久訪問權的物品或服務。非消耗品物品可以被用戶再次下載,並且能夠在用戶的所有設備上使用
消耗品(Consumable),買了就用,用了就沒
專為支持可消耗的物品或服務設計的,消耗品購買不可被再次下載,根據其特點,消耗品不能在用戶的設備之間跨設備使用,除非自定義服務在用戶的賬號之間共享這些信息
3.添加內購功能
3.1在iTunes Connect中給自己的應用添加消耗品定義
3.2在iTunes Connect中給自己的應用添加 定義的商品
3.3要使用內購,需要導入StoreKit框架
定義好的商品
#define kIAPBomb @"airplay.10bombs"
#define kIAPBullet @"airplay.laserBullet"
1. 實例化請求時,必須指定有效的identifiers集合,之所以如此處理,主要是為了確保提交的內購商品真的通過了蘋果的審批,處於可用狀態!
2. 要想獲取到准確的可用產品集合,需要通過代理方法實現
- (void)productsRequest:(SKProductsRequest *)request didReceiveResponse:(SKProductsResponse *)response
3. 越獄用戶無法測試內購,但是可以購買
1 @interface ITViewController () <SKProductsRequestDelegate, SKPaymentTransactionObserver> 2 { 3 // 產品字典 4 NSMutableDictionary *_productDict; 5 }
1 - (void)viewDidLoad 2 { 3 [super viewDidLoad]; 4 5 [self requestProducts]; 6 7 // 設置購買隊列的監聽器 8 [[SKPaymentQueue defaultQueue] addTransactionObserver:self]; 9 }
3.4.詢問蘋果的服務器能夠銷售哪些商品
#pragma mark 詢問蘋果的服務器能夠銷售哪些商品 - (void)requestProducts { // 能夠銷售的商品 NSSet *set = [[NSSet alloc] initWithObjects:kIAPBomb, kIAPBullet, nil]; // "異步"詢問蘋果能否銷售 SKProductsRequest *request = [[SKProductsRequest alloc] initWithProductIdentifiers:set]; request.delegate = self; // 啟動請求 [request start]; }
3.5.獲取詢問結果,成功采取操作把商品加入可售商品字典里
- (void)productsRequest:(SKProductsRequest *)request didReceiveResponse:(SKProductsResponse *)response { if (_productDict == nil) { _productDict = [NSMutableDictionary dictionaryWithCapacity:response.products.count]; } for (SKProduct *product in response.products) { // 激活了對應的銷售操作按鈕,相當於商店的商品上架允許銷售 NSLog(@"%@", product.productIdentifier); if ([product.productIdentifier isEqualToString:kIAPBullet]) { _bulletButton.enabled = YES; } if ([product.productIdentifier isEqualToString:kIAPBomb]) { _bombButton.enabled = YES; } // 填充商品字典 [_productDict setObject:product forKey:product.productIdentifier]; } }
3.6.用戶決定購買商品
1 #pragma mark - 用戶決定購買商品 2 - (void)buyProduct:(SKProduct *)product 3 { 4 // 要購買產品(店員給用戶開了個小票) 5 SKPayment *payment = [SKPayment paymentWithProduct:product]; 6 7 // // 設置購買隊列的監聽器 8 // [[SKPaymentQueue defaultQueue] addTransactionObserver:self]; 9 10 // 去收銀台排隊,准備購買(異步網絡) 11 [[SKPaymentQueue defaultQueue] addPayment:payment]; 12 }
1 - (IBAction)purchaseProducts 2 { 3 [self buyProduct:_productDict[kIAPBullet]]; 4 } 5 6 - (IBAction)purchaseBomb:(id)sender 7 { 8 [self buyProduct:_productDict[kIAPBomb]]; 9 }
3.7.判斷購買狀態是否成功
#pragma mark - SKPaymentTransaction Observer #pragma mark 購買隊列狀態變化 - (void)paymentQueue:(SKPaymentQueue *)queue updatedTransactions:(NSArray *)transactions { // 調試 for (SKPaymentTransaction *transaction in transactions) { NSLog(@"隊列狀態變化 %@", transaction); // 如果小票狀態是購買完成 if (SKPaymentTransactionStatePurchased == transaction.transactionState) { NSLog(@"購買完成 %@", transaction.payment.productIdentifier); // 更新界面或者數據,把用戶購買得商品交給用戶 // ... // 驗證購買憑據 [self verifyPruchase]; // 將交易從交易隊列中刪除 [[SKPaymentQueue defaultQueue] finishTransaction:transaction]; } else if (SKPaymentTransactionStateRestored == transaction.transactionState) { NSLog(@"恢復成功 %@", transaction.payment.productIdentifier); // 更新界面或者數據,把用戶購買得商品交給用戶 // ... // 將交易從交易隊列中刪除 [[SKPaymentQueue defaultQueue] finishTransaction:transaction]; } } }
3.8.給用戶提供恢復功能(因為在不同設備上永久性商品可能會出現需要恢復購買的情況)
#pragma mark - 恢復商品 - (void)restorePurchase { // 恢復已經完成的所有交易.(僅限永久有效商品) [[SKPaymentQueue defaultQueue] restoreCompletedTransactions]; }
3.9.驗證購買(防止第三方插件漏洞)iOS7新特性
提示:雖然蘋果在iOS7提升了購買憑據的安全性,但是處於金錢考慮,購買完成后,一定要做憑據的驗證工作。
1 #pragma mark 驗證購買憑據 2 - (void)verifyPruchase 3 { 4 // 驗證憑據,獲取到蘋果返回的交易憑據 5 // appStoreReceiptURL iOS7.0增加的,購買交易完成后,會將憑據存放在該地址 6 NSURL *receiptURL = [[NSBundle mainBundle] appStoreReceiptURL]; 7 // 從沙盒中獲取到購買憑據 8 NSData *receiptData = [NSData dataWithContentsOfURL:receiptURL]; 9 10 // 發送網絡POST請求,對購買憑據進行驗證 11 NSURL *url = [NSURL URLWithString:ITMS_SANDBOX_VERIFY_RECEIPT_URL]; 12 // 國內訪問蘋果服務器比較慢,timeoutInterval需要長一點 13 NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:10.0f]; 14 15 request.HTTPMethod = @"POST"; 16 17 // 在網絡中傳輸數據,大多情況下是傳輸的字符串而不是二進制數據 18 // 傳輸的是BASE64編碼的字符串 19 /** 20 BASE64 常用的編碼方案,通常用於數據傳輸,以及加密算法的基礎算法,傳輸過程中能夠保證數據傳輸的穩定性 21 BASE64是可以編碼和解碼的 22 */ 23 NSString *encodeStr = [receiptData base64EncodedStringWithOptions:NSDataBase64EncodingEndLineWithLineFeed]; 24 25 NSString *payload = [NSString stringWithFormat:@"{\"receipt-data\" : \"%@\"}", encodeStr]; 26 NSData *payloadData = [payload dataUsingEncoding:NSUTF8StringEncoding]; 27 28 request.HTTPBody = payloadData; 29 30 // 提交驗證請求,並獲得官方的驗證JSON結果 31 NSData *result = [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil]; 32 33 // 官方驗證結果為空 34 if (result == nil) { 35 NSLog(@"驗證失敗"); 36 } 37 38 NSDictionary *dict = [NSJSONSerialization JSONObjectWithData:result options:NSJSONReadingAllowFragments error:nil]; 39 40 NSLog(@"%@", dict); 41 42 if (dict != nil) { 43 // 比對字典中以下信息基本上可以保證數據安全 44 // bundle_id&application_version&product_id&transaction_id 45 NSLog(@"驗證成功"); 46 } 47 }
3.9.說說整個購買流程結構
1.蘋果APP(商家)——— 2.告訴蘋果Store服務器要賣的商品 ——— 3.蘋果審核完(告訴你是否可以賣)
4.用戶(買商品)——— 5.蘋果APP(商家)——— 6.開發票給(用戶)————
7.用戶(拿着發票去蘋果Store服務器付款)——8.付款成功(用戶在APP里獲得服務商品)
(注意:如果要模擬測試內購,需要用真機才可以測試)
作者: 清澈Saup
出處: http://www.cnblogs.com/qingche/
本文版權歸作者和博客園共有,歡迎轉載,但必須保留此段聲明,且在文章頁面明顯位置給出原文連接。