我跟着this tutorial在我的app的启动时添加了一个加载屏幕,同时数据加载了AsyncTask的doInBackground()函数。
我的应用还具有应用内结算优惠升级功能,我想在启动时查询广告资源以检查此情况。但是IabHelper
函数已经异步。
如何将IabHelper
检查集成到doInBackground()中,以便仅在所有内容成功完成后才加载主活动?
我的结算代码如下:
private void checkForPremiumPurchase()
{
billingHelper = new IabHelper(this, Constants.BASE_64_KEY);
//Start setup. This is asynchronous and the specified listener will be called once setup completes.
billingHelper.startSetup(new IabHelper.OnIabSetupFinishedListener() {
public void onIabSetupFinished(IabResult result) {
if(result.isSuccess()) {
billingHelper.queryInventoryAsync(mGotInventoryListener);
}
}
});
}
//Listener that's called when we finish querying the items and subscriptions we own
IabHelper.QueryInventoryFinishedListener mGotInventoryListener = new IabHelper.QueryInventoryFinishedListener()
{
@Override
public void onQueryInventoryFinished(IabResult result, Inventory inventory) {
if(result.isSuccess()) {
isPremium = inventory.hasPurchase(Constants.SKU_PREMIUM);
Log.d(Constants.TAG, "App is " + (isPremium ? "PREMIUM" : "NOT PREMIUM"));
}
}
};
答案 0 :(得分:3)
AsyncTask
非常有用,可以帮助您将长时间运行的作业放到后台线程上,并为您提供一个很好的清理机制,用于在后台任务运行之前,期间和之后更新UI ...所有没有直接搞乱线程。
然而,其他一些Android API设置为允许您在主(UI)线程上发起调用,然后在幕后,他们将在后台线程上完成工作(他们甚至可以使用AsyncTask
,虽然你不一定关心。)
在这种情况下,IabHelper
methods you're using are asynchronous,它们将允许您从主线程启动它们,而不会阻止UI。
因此,无需在您用于其他工作的同一AsyncTask#doInBackground()
方法中运行它们,只需将工作从主线程中删除。
我看到两个选项:
理想情况下,如果您需要在启动时加载一些数据(并且正在使用AsyncTask
),您可以同时启动应用内结算请求。
您描述了主要活动,因此我假设您的应用以某种启动活动开头(?)。在该启动活动中,您可以使用:
public void onCreate(Bundle savedInstanceState) {
new MyLoadingAsyncTask().execute();
checkForPremiumPurchase();
}
然后在IAB检查完成时启动主要活动:
public void onQueryInventoryFinished(IabResult result, Inventory inventory) {
isPremium = false;
if(result.isSuccess()) {
isPremium = inventory.hasPurchase(Constants.SKU_PREMIUM);
Log.d(Constants.TAG, "App is " + (isPremium ? "PREMIUM" : "NOT PREMIUM"));
}
Intent i = new Intent(self, MainActivity.class);
i.putExtra("IsPremium", isPremium);
startActivity(i);
}
这假设网络IAB事务将花费比应用程序正常“加载”过程更长的时间。 (如果该假设无效,则发表评论,我将处理该案例)
如果您的应用设计中有其他内容需要您“完成加载”而然后会启动IAB请求,那么您可以在checkForPremiumPurchase()
完成后致电AsyncTask
它的工作:
protected void onPostExecute(Long result) {
checkForPremiumPurchase();
}
加载完成后,在主线程上调用 AsyncTask#onPostExecute()
,并且可以安全地在主线程上调用checkForPremiumPurchase()
。
一般情况下,我建议您不要推迟启动应用以检查优质升级。理想情况下,您会找到一种聪明的方法来保存此状态(购买的溢价)一次,然后避免将来的检查。您的用户会很感激。
但是,我不知道你的应用程序的免费/溢价之间的区别是什么,以及这种差异是否会立即出现......所以,这可能是你无法避免的。