こんにちはトイロジックのプログラマーNです。業務ではUnityでのモバイルアプリ開発を担当しています。

アプリ開発では無料でアプリをリリースし、アプリ内で有料アイテムを販売したり、アプリ内広告を実装するケースが多いです。本記事ではUnityでのアプリ内課金の実装について紹介しようと思います。

※使用しているバージョンは Unity2021.3.4f1 です。
※In App Purchasing の バージョン4.1.5 時点の内容です。

UnityIAPの設定

Unityでアプリ内課金を実装する方法はいくつかありますが、UnityIAPという機能を使うのがおすすめです。UnityIAPをプロジェクトに適用するにはService機能を有効化し、Packageのインストールする必要があります。どちらもUnityのエディタ上から設定が可能です。

UnityエディタからServiceウィンドウを開き、In-App PurchasingをONにします。有効にすると、アプリの対象年齢など設定が求められるので、忘れずに設定します。

Serviceウィンドウから設定を有効にできたら、IAPのPackageをインストールします。PackageはPackageManagerからインストール可能です。Packageのバージョンによっては正常に動作しないこともあるので、利用しているUnityエディタで推奨されているPackageのバージョンを選択します。

これで実装の前準備は完了です。

UnityIAPを実装

Unityでアプリ内課金を実装する方法はいくつかあります。C#でコードを書かずに実装することもできますが、コーディングする場合もそこまで苦労しないです。C#でUnityIAPの機能を利用する場合はUnityEngine.Purchasingに含まれる、IStoreListenerのインターフェースを継承して、IAPのクラスを実装します。

public class IAPManager : IStoreListener
{
    /// <summary>
    /// 商品情報
    /// </summary>
    public class ProductInfo
    {
        public string ID { private set; get; }
        public ProductType Type { private set; get; }

        public ProductInfo(string _id, ProductType _type) => (ID, Type) = (_id, _type);
    }

    private IStoreController m_storeController;
    private IExtensionProvider m_extensionProvider;

    public bool IsInitialized => m_storeController != null && m_extensionProvider != null;

    /// <summary>
    /// 初期化
    /// </summary>
    public void Initialize(ProductInfo[] _products)
    {
        if (!IsInitialized)
        {
            var m_builder = ConfigurationBuilder.Instance(StandardPurchasingModule.Instance());
            foreach (var product in _products)
            {
                m_builder.AddProduct(product.ID, product.Type);
            }
            UnityPurchasing.Initialize(this, m_builder);
        }
    }

    /// <summary>
    /// 初期化 成功
    /// </summary>
    public void OnInitialized(IStoreController _controller, IExtensionProvider _extensions)
    {
        m_storeController = _controller;
        m_extensionProvider = _extensions;
    }

    /// <summary>
    /// 初期化 失敗
    /// </summary>
    public void OnInitializeFailed(InitializationFailureReason _error)
    {
        // 失敗時のエラー処理を実装
    }

    /// <summary>
    /// 購入成功時
    /// </summary>
    public PurchaseProcessingResult ProcessPurchase(PurchaseEventArgs _purchaseEvent)
    {
        // 購入した商品情報は_purchaseEvent.purchasedProductから取得可能
        return PurchaseProcessingResult.Complete;
    }

    /// <summary>
    /// 購入処理 失敗
    /// </summary>
    public void OnPurchaseFailed(Product _product, PurchaseFailureReason _failureReason)
    {
        // 失敗時のエラー処理を実装
    }

    /// <summary>
    /// 商品購入
    /// </summary>
    public void Purchase(string _productId)
    {
        if (IsInitialized)
        {
            m_storeController.InitiatePurchase(_productId);
        }
        else
        {
            // 初期化が完了する前に呼ばれたときのエラー処理を実装
        }
    }
}

IStoreListenerを継承した場合は、OnInitializedOnInitializeFailedOnPurchaseFailedProcessPurchaseを定義する必要があります。

商品情報の登録と商品購入の処理は、自身で実装することになりますが、必要なことはストアに登録してある商品のプロダクトIDと消費タイプを設定するくらいです。ストア商品の登録は、初期化時に行えば問題ないと思います。初期化が正常に行われれば、あとは購入する際に登録したプロダクトIDを渡せば購入処理が走ります。

最低限の実装は上記のコード例で済みますが、ストアによっては購入復元機能も実装する必要が出てきます。サーバーと連携してレシート検証なども行った方がいいです。プラットフォームごとに実装が分かれるケースもあるので、コーディングで実装して拡張できるようにしておいたほうがいいと思います。

最後に

本記事ではUnityでのアプリ内課金の実装手順についてご紹介しました。

モバイルアプリの開発では、アプリ内課金の実装を行う機会が多いです。Unityの機能を利用すればそこまで苦労せずに実現することができます。

この記事がどなたかの参考になれば幸いです。ここまで読んでいただきありがとうございました!

著者紹介 N
2018年トイロジックに中途入社。いくつかのプロジェクトでUnityでのゲーム開発を経験、現在はモバイルアプリの開発業務を担当。

トイロジックでは現在、一緒に働くプログラマーを募集しています。

不明点などもお気軽にお問い合わせくださいフルリモート採用も行っております、ご応募お待ちしております!