iOS IAP教程

1. 创建应用

首先进入iTunes Connect然后按下 Manage Your Applications


接下来按下Add New Applicationbutton创建应用

2. 在应用中创建IAP


创建应用之后,在Manage Your Applications中点应用的图示,进入应用

就会看到上图画面点击Manage In App Purchases就能够进入IAP的管理画面

在这边要注意左边的Bundle ID,在Xcode项目中,info.plist中的设定需与此Bundle同样

(此Bundle ID会在创建应用时填入)

此为IAP的管理画面,仅仅要按下Create Newbutton就可创建IAP

在本图中我已经创建好三个IAP

而当中要注意的是Product ID,仅仅要用Product ID就能够请求IAP的相关讯息及交易

Consumable

消耗品,每次下载都需付费

Non-Consumable

一次性付费,通经常使用在升级pro版或是移除广告等

Auto-Renewable Subscriptions

自己主动更新订阅

Free Subscription

免费订阅

Non-Renewing Subscription

自己主动更新订阅

3. 怎样创建沙盒測试用户

进入iTunes Connect,点击Manage Users

在这个画面中点下Test User

按下Add New User就能够了Email Address就是登入沙盒測试的username

password的部份在Add New User时可自行创建

4.代码

/**  CBiOSStoreManager.h*  CloudBox Cross-Platform Framework Project**  Created by Cloud on 2012/10/30.*  Copyright 2011 Cloud Hsu. All rights reserved.**/#import <UIKit/UIKit.h> 
#import <StoreKit/StoreKit.h>@interface CBiOSStoreManager : NSObject<SKProductsRequestDelegate,SKPaymentTransactionObserver>
{NSString* _buyProductIDTag;
}+ (CBiOSStoreManager*) sharedInstance;- (void) buy:(NSString*)buyProductIDTag;
- (bool) CanMakePay;
- (void) initialStore;
- (void) releaseStore;
- (void) requestProductData:(NSString*)buyProductIDTag;
- (void) provideContent:(NSString *)product;
- (void) recordTransaction:(NSString *)product;- (void) requestProUpgradeProductData:(NSString*)buyProductIDTag;
- (void) paymentQueue:(SKPaymentQueue *)queue updatedTransactions:(NSArray *)transactions;
- (void) purchasedTransaction: (SKPaymentTransaction *)transaction;
- (void) completeTransaction: (SKPaymentTransaction *)transaction;
- (void) failedTransaction: (SKPaymentTransaction *)transaction;
- (void) paymentQueueRestoreCompletedTransactionsFinished: (SKPaymentTransaction *)transaction;
- (void) paymentQueue:(SKPaymentQueue *) paymentQueue restoreCompletedTransactionsFailedWithError:(NSError *)error;
- (void) restoreTransaction: (SKPaymentTransaction *)transaction;@end

/**  CBiOSStoreManager.mm*  CloudBox Cross-Platform Framework Project**  Created by Cloud on 2012/10/30.*  Copyright 2011 Cloud Hsu. All rights reserved.**/#import "CBiOSStoreManager.h"@implementation CBiOSStoreManagerstatic CBiOSStoreManager* _sharedInstance = nil;+(CBiOSStoreManager*)sharedInstance
{@synchronized([CBiOSStoreManager class]){if (!_sharedInstance)[[self alloc] init];return _sharedInstance;}return nil;
}+(id)alloc
{@synchronized([CBiOSStoreManager class]){NSAssert(_sharedInstance == nil, @"Attempted to allocate a second instance of a singleton.\n");_sharedInstance = [super alloc];return _sharedInstance;}return nil;
}-(id)init {self = [super init];if (self != nil) {// initialize stuff here}return self;
}-(void)initialStore
{[[SKPaymentQueue defaultQueue] addTransactionObserver:self];
}
-(void)releaseStore
{[[SKPaymentQueue defaultQueue] removeTransactionObserver:self];
}-(void)buy:(NSString*)buyProductIDTag
{[self requestProductData:buyProductIDTag];
}-(bool)CanMakePay
{return [SKPaymentQueue canMakePayments];
}   -(void)requestProductData:(NSString*)buyProductIDTag
{NSLog(@"---------Request product information------------\n");_buyProductIDTag = [buyProductIDTag retain];NSArray *product = [[NSArray alloc] initWithObjects:buyProductIDTag,nil];NSSet *nsset = [NSSet setWithArray:product];SKProductsRequest *request=[[SKProductsRequest alloc] initWithProductIdentifiers: nsset];request.delegate=self;[request start];[product release];
}- (void)productsRequest:(SKProductsRequest *)request didReceiveResponse:(SKProductsResponse *)response{   NSLog(@"-----------Getting product information--------------\n");NSArray *myProduct = response.products;NSLog(@"Product ID:%@\n",response.invalidProductIdentifiers);NSLog(@"Product count: %d\n", [myProduct count]);// populate UIfor(SKProduct *product in myProduct){NSLog(@"Detail product info\n");NSLog(@"SKProduct description: %@\n", [product description]);NSLog(@"Product localized title: %@\n" , product.localizedTitle);NSLog(@"Product localized descitption: %@\n" , product.localizedDescription);NSLog(@"Product price: %@\n" , product.price);NSLog(@"Product identifier: %@\n" , product.productIdentifier);}SKPayment *payment = nil;payment = [SKPayment paymentWithProduct:[response.products objectAtIndex:0]];NSLog(@"---------Request payment------------\n");[[SKPaymentQueue defaultQueue] addPayment:payment];[request autorelease];    }
- (void)requestProUpgradeProductData:(NSString*)buyProductIDTag
{NSLog(@"------Request to upgrade product data---------\n");NSSet *productIdentifiers = [NSSet setWithObject:buyProductIDTag];SKProductsRequest* productsRequest = [[SKProductsRequest alloc] initWithProductIdentifiers:productIdentifiers];productsRequest.delegate = self;[productsRequest start];    }- (void)request:(SKRequest *)request didFailWithError:(NSError *)error
{NSLog(@"-------Show fail message----------\n");UIAlertView *alerView =  [[UIAlertView alloc] initWithTitle:NSLocalizedString(@"Alert",NULL) message:[error localizedDescription]delegate:nil cancelButtonTitle:NSLocalizedString(@"Close",nil) otherButtonTitles:nil];[alerView show];[alerView release];
}   -(void) requestDidFinish:(SKRequest *)request
{NSLog(@"----------Request finished--------------\n");}   -(void) purchasedTransaction: (SKPaymentTransaction *)transaction
{NSLog(@"-----Purchased Transaction----\n");NSArray *transactions =[[NSArray alloc] initWithObjects:transaction, nil];[self paymentQueue:[SKPaymentQueue defaultQueue] updatedTransactions:transactions];[transactions release];
}    - (void)paymentQueue:(SKPaymentQueue *)queue updatedTransactions:(NSArray *)transactions
{NSLog(@"-----Payment result--------\n");for (SKPaymentTransaction *transaction in transactions){switch (transaction.transactionState){case SKPaymentTransactionStatePurchased:[self completeTransaction:transaction];NSLog(@"-----Transaction purchased--------\n");UIAlertView *alerView =  [[UIAlertView alloc] initWithTitle:@"Congratulation"message:@"Transaction suceed!"delegate:nil cancelButtonTitle:NSLocalizedString(@"Close",nil) otherButtonTitles:nil];   [alerView show];[alerView release];break;case SKPaymentTransactionStateFailed:[self failedTransaction:transaction];NSLog(@"-----Transaction Failed--------\n");UIAlertView *alerView2 =  [[UIAlertView alloc] initWithTitle:@"Failed"message:@"Sorry, your transcation failed, try again."delegate:nil cancelButtonTitle:NSLocalizedString(@"Close",nil) otherButtonTitles:nil];   [alerView2 show];[alerView2 release];break;case SKPaymentTransactionStateRestored:[self restoreTransaction:transaction];NSLog(@"----- Already buy this product--------\n");case SKPaymentTransactionStatePurchasing:NSLog(@"-----Transcation puchasing--------\n");break;default:break;}}
}- (void) completeTransaction: (SKPaymentTransaction *)transaction   
{NSLog(@"-----completeTransaction--------\n");// Your application should implement these two methods.NSString *product = transaction.payment.productIdentifier;if ([product length] > 0) {   NSArray *tt = [product componentsSeparatedByString:@"."];NSString *bookid = [tt lastObject];if ([bookid length] > 0) {[self recordTransaction:bookid];[self provideContent:bookid];}}   // Remove the transaction from the payment queue.   [[SKPaymentQueue defaultQueue] finishTransaction: transaction];   }   -(void)recordTransaction:(NSString *)product
{NSLog(@"-----Record transcation--------\n");// Todo: Maybe you want to save transaction result into plist.
}   -(void)provideContent:(NSString *)product
{NSLog(@"-----Download product content--------\n");
}   - (void) failedTransaction: (SKPaymentTransaction *)transaction
{NSLog(@"Failed\n");if (transaction.error.code != SKErrorPaymentCancelled){}[[SKPaymentQueue defaultQueue] finishTransaction: transaction];
}
-(void) paymentQueueRestoreCompletedTransactionsFinished: (SKPaymentTransaction *)transaction
{   }- (void) restoreTransaction: (SKPaymentTransaction *)transaction
{NSLog(@"-----Restore transaction--------\n");
}-(void) paymentQueue:(SKPaymentQueue *) paymentQueue restoreCompletedTransactionsFailedWithError:(NSError *)error
{NSLog(@"-------Payment Queue----\n");
}#pragma mark connection delegate
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data
{NSLog(@"%@\n",  [[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding] autorelease]);
}
- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{   }   - (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response
{switch([(NSHTTPURLResponse *)response statusCode]) {case 200:case 206:break;case 304:break;case 400:break;case 404:break;case 416:break;case 403:break;case 401:case 500:break;default:break;}
}   - (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error
{NSLog(@"test\n");
}   -(void)dealloc
{[super dealloc];
}@end


[[SKPaymentQueue defaultQueue] addTransactionObserver:self];
因为交易是永久有效的,建议addTransactionObserver这个于应用启动后即可监听,而不要在用户想买东西时才监听

- (void)paymentQueue:(SKPaymentQueue *)queue updatedTransactions:(NSArray *)transactions
交易结果会于此处显示

苹果准备沙盒測试环境需一段时间,若是创建IAP后能够取得资讯,却无法交易成功,要稍待一下

另外若是模拟器能够购买,但真机购买却失败的话,做Hard Reset就能够了,一直按住Home键跟电源键就能够做Hard Reset

按住后会出现关机画面,不要理会它,继续等,直到等到白苹果出现后,就能够放开等重开机完成后再測试

5. IAP运作流程图

6.范例下载

下载连结

转载于:https://www.cnblogs.com/hrhguanli/p/4052130.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/420523.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

mybatis plus 新增,修改

simple curd1. mybatis-plus2. 以用户表为例&#xff0c;德莫1. mybatis-plus mybatis的升级版&#xff0c;curd的奇淫技巧。 MyBatis-Plus&#xff08;简称 MP&#xff09;是一个 MyBatis 的增强工具&#xff0c;在 MyBatis 的基础上只做增强不做改变&#xff0c;为简化开发、…

Linux中fork的秘密

linux中fork&#xff08;&#xff09;函数详解 一、fork入门知识 一个进程&#xff0c;包括代码、数据和分配给进程的资源。fork&#xff08;&#xff09;函数通过系统调用创建一个与原来进程几乎完全相同的进程&#xff0c;也就是两个进程可以做完全相同的事&#xff0c;但如果…

mybatis-plus 使用乐观锁修改

title乐观锁与悲观锁解决方案code测试乐观锁与悲观锁 乐观锁&#xff1a;十分乐观&#xff0c;总是认为不会出现问题&#xff0c;无论干什么&#xff0c;都不会去上锁。如果出现了问题&#xff0c;就再次更新值测试。 悲观锁&#xff1a;十分悲观&#xff0c;认为总是出现问题…

EasyUI 在aspx页面显示高度不正常解决办法

<body class"easyui-layout"><form id"form1" runat"server"><table id"dg" class"easyui-datagrid"></table></form> </body> </html>这样写的时候&#xff0c;datagrid显示就不…

WPF中的动画——(四)缓动函数

缓动函数可以通过一系列公式模拟一些物理效果&#xff0c;如实地弹跳或其行为如同在弹簧上一样。它们一般应用在From/To/By动画上&#xff0c;可以使得其动画更加平滑。 var widthAnimation new DoubleAnimation() { From 0, To 320, Duration Tim…

mybatis-plus 查询,删除

title查询 单值&#xff0c;多个主键&#xff0c;条件分页查询物理删除&#xff0c;逻辑删除mybatis-plus 新增&#xff0c;修改查询 单值&#xff0c;多个主键&#xff0c;条件 Testvoid queryOne() {// 查询单个userUser user userMapper.selectById(1);System.out.println(…

C#获取txt记事本内容,防止乱码情况

StreamReader sr new StreamReader("E:\人名.txt", Encoding.GetEncoding("GB2312"));string readText sr.ReadToEnd(); 转载于:https://www.cnblogs.com/blog4xy/p/4059363.html

mybatis高级查询,批量新增

reviewsql脚本实体类sql watch outmappermapper test之前的比较分散&#xff0c;自己用。。。sql脚本 -- auto-generated definition create table stu_info (stu_id int auto_incrementprimary key,stu_name varchar(255) null,stu_age int(255) null,stu_gende…

Java对存储过程的调用方法

本文将介绍Java怎样实现对存数过程的调用方法&#xff0c;作者用了几个样例进行了具体的说明&#xff0c;简单明了&#xff0c;很适合刚開始学习的人。 一、Java怎样实现对存储过程的调用&#xff1a; A&#xff1a;不带输出參数的 create procedure getsum n int 0<--此处…

mybatis-plus 代码生成器

生成entity -> mapper-> service ->controller所有的接口&#xff0c;实现&#xff0c;一键完成。 1. 轮子 <dependency><groupId>mysql</groupId><artifactId>mysql-connector-java</artifactId><scope>runtime</scope>…

电脑报错找不到msvcr100.dll,无法继续执行代码如何修复

在电脑使用过程中&#xff0c;我们经常会遇到一些错误提示&#xff0c;其中之一就是MSVCR100.dll丢失。那么&#xff0c;MSVCR100.dll到底是什么&#xff1f;它的作用是什么&#xff1f;为什么会丢失呢&#xff1f;本文将详细介绍MSVCR100.dll的定义、作用以及丢失的原因&#…

windows下面虚拟主机

1. wondows xp apmserv 5.2.6 端口8088 2.httpd.config文件 1. ServerRoot      "D:/APMServ/APMServ5.2.6/Apache" Listen        8088 ServerName     127.0.0.1:8088 DocumentRoot   "D:/APMServ/APMServ5.2.6/www/" (原文未变)…

QueryWrapper查询

QueryWrapper, mybatisplus 中封装了大量的查询方法。用于高级查询。传入表的列和查询的值&#xff0c;就能反射对应的sql. 简化了查询。 更多api&#xff0c;查询使用&#xff0c;看&#xff1a; https://baomidou.com/guide/wrapper.html package cn.bitqian;import cn.bit…

Smooks转换设计

Smooks转换设计 背景 不同的合作银行对应的外部接口是不一样的,我们需要把外部这些变化不定的接口格式,转换为我们银保通系统可以识别的内部接口.Smooks可以很好的解决这一问题.并且,当合作银行的接口随着业务的变化而发生变化时,smooks只需要通过变更转换模板,就可以实现对变化…