如何制作消费类应用程序购买安卓游戏项目?

时间:2013-12-26 09:54:47

标签: android in-app-purchase

所以我想在unity3d制作的游戏中制作游戏购买物品。

我正在测试基于新的unity3d版本(4.3.1)和android sdk,in-app-buy API 3.

所以我在开发者控制台上测试了应用内购买项目(托管,非托管),

和eclipse java源码的统一插件就像,

package com.dimension14.unityandroidjartest;

import java.util.List;

import org.json.JSONException;
import org.json.JSONObject;

import android.R.string;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;

import com.example.android.trivialdrivesample.util.IabHelper;
import com.example.android.trivialdrivesample.util.IabHelper.OnConsumeFinishedListener;
import com.example.android.trivialdrivesample.util.IabHelper.OnIabPurchaseFinishedListener;
import com.example.android.trivialdrivesample.util.IabHelper.QueryInventoryFinishedListener;
import com.example.android.trivialdrivesample.util.IabResult;
import com.example.android.trivialdrivesample.util.Inventory;
import com.example.android.trivialdrivesample.util.Purchase;
import com.unity3d.player.UnityPlayer;
import com.unity3d.player.UnityPlayerActivity;

public class MainActivity extends UnityPlayerActivity {

 @Override
 protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState); 
 }

 public void javaTestFunc(String strFromUnity) {
  UnityPlayer.UnitySendMessage("AndroidManager", "SetLog", strFromUnity + "HelloWorld");
 }

 static final int RC_REQUEST = 10001;
private static final String LOG_TAG = null;
 private IabHelper mHelper;

 public void InAppInit_U(String strPublicKey, boolean bDebug) {                                                 
     Log.d(LOG_TAG, "Creating IAB helper." + bDebug);                                                             
     mHelper = new IabHelper(this, strPublicKey);                                                                 

     if(bDebug == true) {                                                                                         
      mHelper.enableDebugLogging(true, "IAB");                                                                   
     }                                                                                                             

     mHelper.startSetup(new IabHelper.OnIabSetupFinishedListener() {                                               

     @Override                                                                                                     
     public void onIabSetupFinished(IabResult result) {                                                           
      // TODO Auto-generated method stub                                                                         
      boolean bInit = result.isSuccess();                                                                         
      Log.d(LOG_TAG, "IAB Init " + bInit + result.getMessage());                                                 

      if(bInit == true) {                                                                                         
       Log.d(LOG_TAG, "Querying inventory.");                                                                   
       //QueryInventoryFinishedListener mGotInventoryListener = null;
       mHelper.queryInventoryAsync(mGotInventoryListener);                                                       
      }                                                                                                           

      UnityPlayer.UnitySendMessage("AndroidManager", "InAppInitResult_J", String.valueOf(bInit));               
     }                                                                                                             
    });                                                                                                             
    }

//Listener that's called when we finish querying the items and subscriptions we own                          
    IabHelper.QueryInventoryFinishedListener mGotInventoryListener = new IabHelper.QueryInventoryFinishedListener() {
      public void onQueryInventoryFinished(IabResult result, Inventory inventory) {                               
          if (result.isFailure()) {                                                                               
              Log.d(LOG_TAG, "Failed to query inventory: " + result);                                             
              SendConsumeResult(null, result);                                                                   
              return;                                                                                             
          }                                                                                                       

          /*                                                                                                     
           * Check for items we own. Notice that for each purchase, we check                                     
           * the developer payload to see if it's correct! See                                                   
           * verifyDeveloperPayload().                                                                           
           */                                                                                                     

          List<String> inappList = inventory.getAllOwnedSkus(IabHelper.ITEM_TYPE_INAPP);                         

          for(String inappSku : inappList) {                                                                     
           Purchase purchase = inventory.getPurchase(inappSku);                                                 
           Log.d(LOG_TAG, "Consumeing ... " + inappSku);                                   

           UnityPlayer.UnitySendMessage("AndroidManager", "InAppBuyItemResult_J", inappSku);

           mHelper.consumeAsync(purchase, mConsumeFinishedListener);

           if(inappSku.equals("itemtest1")){
            //give user access to premium unlock item                   
             UnityPlayer.UnitySendMessage("AndroidManager", "UnlockItem", "");
           }
           if(inappSku.equals("consumeitem1")){
                // consume consumable item
                mHelper.consumeAsync(purchase, mConsumeFinishedListener);
                 UnityPlayer.UnitySendMessage("AndroidManager", "BoughtConsume1", "");
           }
          }                                                                                                       

          Log.d(LOG_TAG, "Query inventory was successful.");                                                     
      }

    };  

    public void InAppBuyItem_U(final String strItemId) {
         runOnUiThread(new Runnable() {

         @Override
         public void run() {
          // TODO Auto-generated method stub

                /* TODO: for security, generate your payload here for verification. See the comments on
                 *        verifyDeveloperPayload() for more info. Since this is a SAMPLE, we just use
                 *        an empty string, but on a production app you should carefully generate this. */
                String payload = "";

                OnIabPurchaseFinishedListener mPurchaseFinishedListener = null;
                mHelper.launchPurchaseFlow(UnityPlayer.currentActivity
                  , strItemId, RC_REQUEST, mPurchaseFinishedListener, payload);

                Log.d(LOG_TAG, "InAppBuyItem_U " + strItemId);
         }
         });
        }

    // Callback for when a purchase is finished
    IabHelper.OnIabPurchaseFinishedListener mPurchaseFinishedListener = new IabHelper.OnIabPurchaseFinishedListener() {
        public void onIabPurchaseFinished(IabResult result, Purchase purchase) {
            Log.d(LOG_TAG, "Purchase finished: " + result + ", purchase: " + purchase);

            if(purchase != null) {
                if(!verifyDeveloperPayload(purchase)) {
                    Log.d(LOG_TAG, "Error purchasing. Authenticity verification failed.");
                }
                if(result.isFailure()){
                    Log.d(LOG_TAG, "Error purchasing : "+result);
                    return;
                }
                else if(purchase.getSku().equals("itemtest1")){
                    //give user access to premium unlock item                   
                     UnityPlayer.UnitySendMessage("AndroidManager", "UnlockItem", "");
                }
                else if(purchase.getSku().equals("consumeitem1")){
                    // consume consumable item
                    mHelper.consumeAsync(purchase, mConsumeFinishedListener);
                     UnityPlayer.UnitySendMessage("AndroidManager", "BoughtConsume1", "");
                }
                Log.d(LOG_TAG, "Purchase is gas. Starting gas consumption.");
                UnityPlayer.UnitySendMessage("AndroidManager", "InAppBuyItemResult2", "result is "+result+" purchase is "+purchase);
                mHelper.consumeAsync(purchase, mConsumeFinishedListener);

            }
            else {         
                UnityPlayer.UnitySendMessage("AndroidManager", "InAppBuyItemResult_J", String.valueOf(result.getResponse()));
            }
        }

        boolean verifyDeveloperPayload( Purchase purchase) {
            String payload = purchase.getDeveloperPayload();
            /*
             *  TODO: verify that the developer payload of the purchase is correct. It will be
                the same one that you sent when initiating the purchase.
             * Using your own server to store and verify developer payloads across app
             * installations is recommended.
             */
            return true;
        } 
    };

    /*
    boolean verifyDeveloperPayload(Purchase p) {
        String payload = p.getDeveloperPayload();
        return true;
    }
      */  
    // Called when consumption is complete
    IabHelper.OnConsumeFinishedListener mConsumeFinishedListener = new IabHelper.OnConsumeFinishedListener() {
        public void onConsumeFinished(Purchase purchase, IabResult result) {
            Log.d(LOG_TAG, "Consumption finished. Purchase: " + purchase + ", result: " + result);
            if (mHelper == null) return;

            if(result.isSuccess()){
                SendConsumeResult(purchase, result);
            }
        } 
    };

    protected void SendConsumeResult(Purchase purchase, IabResult result) {
     JSONObject jsonObj = new JSONObject();

        try {
     jsonObj.put("Result", result.getResponse());
     if(purchase != null) {
           jsonObj.put("OrderId", purchase.getOrderId());
              jsonObj.put("Sku", purchase.getSku());
              jsonObj.put("purchaseData", purchase.getOriginalJson());
              jsonObj.put("signature", purchase.getSignature());
          }
    } catch (JSONException e) {
     // TODO Auto-generated catch block
     e.printStackTrace();
    }

     UnityPlayer.UnitySendMessage("AndroidManager", "InAppConsumeResult_J", jsonObj.toString());
    }



    @Override
    public void onDestroy() {
        super.onDestroy();

        // very important:
        Log.d(LOG_TAG, "Destroying helper.");
        if (mHelper != null) mHelper.dispose();
        mHelper = null;
    }

    public void onActivityResult(int requestCode, int resultCode, Intent data) {
          Log.d(LOG_TAG, "onActivityResult(" + requestCode + "," + resultCode + "," + data);
          if(requestCode == RC_REQUEST) {
              // Pass on the activity result to the helper for handling
              if (!mHelper.handleActivityResult(requestCode, resultCode, data)) {
                  // not handled, so handle it ourselves (here's where you'd
                  // perform any handling of activity results not related to in-app
                  // billing...
                  super.onActivityResult(requestCode, resultCode, data);
              }
              else {
                  Log.d(LOG_TAG, "onActivityResult handled by IABUtil.");
              }
          }
    }   

}   // end of MainActivity

和团结的gui脚本部分。

public class TestGUI : MonoBehaviour
{
    // Update is called once per frame
    void Update ()
    {
        if (Application.platform == RuntimePlatform.Android)
        {

            if (Input.GetKey(KeyCode.Escape))
            {
                Application.Quit();
                return;
            }
        }
    }

    void OnGUI()
    {
        GUI.Label(new Rect(50, 30, 500, 100), AndroidManager.GetInstance().strLog);
        GUI.Label(new Rect(50, 0, 500, 100), AndroidManager.GetInstance().strLog2);
        GUI.Label(new Rect(50, 70, 500, 100), "Unlocked?   "+AndroidManager.GetInstance().myunlockItem.ToString());
        GUI.Label(new Rect(200, 70, 500, 100), "How many get currently?   "+AndroidManager.GetInstance().myconsumeItem.ToString());

        if (GUI.Button (new Rect(0, 100, 100, 100), "TestButton") == true)
        {
            AndroidManager.GetInstance().CallJavaFunc( "javaTestFunc", "UnityJavaJarTest" );
        }

        // In App Billing 
        if (GUI.Button (new Rect(150, 100, 100, 100), "InAppInit") == true)
        {
            bool bDebug = true;
            AndroidManager.GetInstance().InAppInit(bDebug);
        } 
        if (GUI.Button (new Rect(300, 100, 100, 100), "Buy 1-time Item") == true)
        {
            string strItemId = "itemtest1";
            AndroidManager.GetInstance().InAppBuyItem(strItemId);
        }
        if (GUI.Button (new Rect(250, 200, 150, 100), "Buy consume Item") == true)
        {
            string strItemId = "consumeitem1";
            AndroidManager.GetInstance().InAppBuyItem(strItemId);
        } 
    }
}

首先,购买作品除了反映我的购买结果(在解锁物品时改为false,在购买消耗品时改为消耗品变量+10)

但主要问题是,在成功购买物品(谷歌结账窗口正常打开并且像正常流程一样正常工作)之后,如果再次触摸[购买项目]按钮,则不会发生任何事情。 Google结帐窗口应该会打开,但不会发生。所以我不能再购买物品了。

为什么以及如何制作物品可以再次购买?

我对谷歌的支持提出质疑,但是他们说买的物品应该被消费,但正如你在上面的消息来源所看到的那样,

我已经使用过mHelper.consumeAsync代码(purchase,mConsumeFinishedListener); 多次。

有什么问题?感谢。

1 个答案:

答案 0 :(得分:0)

购买成功后,您必须使用一次物品,然后您才能再次购买相同物品。