이 페이지에서

인앱 구매 데모

앱 내 상품 구매 기능을 보여주는 완성된 모바일 애플리케이션입니다.

참고: Qt Purchasing모듈은 Qt 6.0에서 제거된 모듈 중 하나였으며, 해당 코드는 이제 Qt를 사용하여 일반적인 마켓플레이스와 연동하는 방법을 안내하기 위한 예제로 이 예제에 포함되어 있습니다.

이 데모는 무엇인가요?

문자 키보드와 숨겨진 단어를 나타내는 대시가 있는 행맨 게임

이 데모는 고전적인 단어 맞추기 게임인 행맨(Hangman)을 기반으로 한 모바일 게임 애플리케이션으로, 데모 내부의 스토어를 통해 모음을 구매할 수 있습니다. 게임에서는 추측해야 할 단어의 글자를 나타내는 대시(-)가 일렬로 표시됩니다. 주어진 단어에 포함된 올바른 글자를 맞히면, 해당 글자가 단어의 해당 대시 한 개 또는 여러 개 위에 표시됩니다. 단어의 모든 글자를 모두 맞히거나, 언제든지 단어 전체를 정확히 맞히면 게임이 끝나고 승리하게 됩니다. 추측이 틀리면 매달린 막대 인형의 한 부분이 그려집니다. 인형이 완성되면 더 이상 추측할 기회가 없어지며 패배하게 됩니다.

이 데모는 Android 및 iOS 플랫폼용 Qt 애플리케이션 내에서 인앱 상품을 제공하는 방법을 보여줍니다. 데모에서 인앱 구매 기능을 테스트하려면 먼저 외부 스토어에 애플리케이션과 해당 상품을 등록해야 합니다. 등록 방법에 대한 안내는 Google Play 및 App Store의 각 가이드를 참조하십시오.

타사 앱 스토어

앱 내에서 상품을 조회하거나 구매하려면, 해당 상품을 대상 스토어에 미리 등록해야 합니다. 상품을 조회하고 구매하는 코드를 단순화하기 위해 각 스토어의 상품에 동일한 식별자를 사용하는 것을 권장합니다.

데모 작동 방식

이 데모는 인앱 상품에 대한 정보에 접근하고 해당 상품의 구매를 요청하기 위해 QML 타입을 등록하는 QML 애플리케이션입니다. 이러한 타입들은 대상 플랫폼의 외부 스토어에 등록됩니다.

인앱 구매 기능을 애플리케이션에 추가하려면 먼저 Store 객체를 추가해야 합니다. 데모에서는 애플리케이션 시작 시 로드되는 MainView 컴포넌트에서 Store 객체를 생성합니다.

Store {
    id: iapStore
}

이 데모는 사용 가능한 인앱 상품을 구매할 수 있는 스토어를 표시하는 컴포넌트를 정의합니다. 이러한 상품은 먼저 위에서 MainView에서 생성한 Store 객체에 등록되어야 합니다. 사용 가능한 상품은 두 가지이며, 첫 번째는 소모성 상품입니다.

Product {
    id: product100Vowels
    store: iapStore
    type: Product.Consumable
    identifier: "qt.io.demo.hangman.100vowels"

    onPurchaseSucceeded: {
        console.log(identifier + " purchase successful");
        //Add 100 Vowels
        applicationData.vowelsAvailable += 100;
        transaction.finalize();
        pageStack.pop();
    }

    onPurchaseFailed: {
        console.log(identifier + " purchase failed");
        console.log("reason: "
                    + transaction.failureReason === Transaction.CanceledByUser ? "Canceled" : transaction.errorString);
        transaction.finalize();
    }
}

이 소모성 상품은 게임에서 단어를 추측할 때 사용할 수 있는 모음 100개를 추가로 제공합니다. 구매가 성공적으로 완료되면, 애플리케이션 상태를 업데이트하여 모음 100개가 추가되도록 합니다. 그런 다음 트랜잭션 객체에 finalize()를 호출하여 플랫폼 스토어에 소모성 상품이 제공되었음을 확인합니다.

두 번째 상품은 향후 모음을 영구적으로 잠금 해제해 주는 비소모성 유형입니다. 구매 시 애플리케이션 상태를 업데이트하는 것 외에도, 최종 사용자가 사용하는 다른 기기에서 이 구매 내역을 복원할 수 있는 방법을 반드시 제공해야 합니다. 이 경우 onPurchaseRestored에 대한 신호 핸들러를 생성합니다.

Product {
    id: productUnlockVowels
    type: Product.Unlockable
    store: iapStore
    identifier: "qt.io.demo.hangman.unlockvowels"

    onPurchaseSucceeded: {
        console.log(identifier + " purchase successful");
        applicationData.vowelsUnlocked = true;
        transaction.finalize();
        pageStack.pop();
    }

    onPurchaseFailed: {
        console.log(identifier + " purchase failed");
        console.log("reason: "
                    + transaction.failureReason === Transaction.CanceledByUser ? "Canceled" : transaction.errorString);
        transaction.finalize();
    }

    onPurchaseRestored: {
        console.log(identifier + " purchase restored");
        applicationData.vowelsUnlocked = true;
        console.log("timestamp: " + transaction.timestamp);
        transaction.finalize();
        pageStack.pop();
    }
}

모음 구매 옵션과 가격이 포함된 행맨 스토어

제품 등록 외에도, 이 데모는 등록된 제품을 실제로 구매할 수 있는 인터페이스를 제공합니다. 데모에서는 구매 인터랙션을 표시하고 처리하기 위해 ` StoreItem `라는 사용자 정의 컴포넌트를 정의합니다.

Product {
    id: productUnlockVowels
    type: Product.Unlockable
    store: iapStore
    identifier: "qt.io.demo.hangman.unlockvowels"

    onPurchaseSucceeded: {
        console.log(identifier + " purchase successful");
        applicationData.vowelsUnlocked = true;
        transaction.finalize();
        pageStack.pop();
    }

    onPurchaseFailed: {
        console.log(identifier + " purchase failed");
        console.log("reason: "
                    + transaction.failureReason === Transaction.CanceledByUser ? "Canceled" : transaction.errorString);
        transaction.finalize();
    }

    onPurchaseRestored: {
        console.log(identifier + " purchase restored");
        applicationData.vowelsUnlocked = true;
        console.log("timestamp: " + transaction.timestamp);
        transaction.finalize();
        pageStack.pop();
    }
}

StoreItem 컴포넌트는 플랫폼 스토어에서 조회한 상품 데이터를 표시하며, 사용자가 클릭하면 해당 상품의 purchase() 메서드를 호출합니다.

Text {
    id: titleText
    text: product.title
    font.bold: true
    anchors.right: priceText.left
    anchors.rightMargin: topLevel.globalMargin
    anchors.top: parent.top
    anchors.topMargin: topLevel.globalMargin
    anchors.left: parent.left
    anchors.leftMargin: topLevel.globalMargin
}

Text {
    id: descriptionText
    text: product.description
    anchors.right: priceText.left
    anchors.rightMargin: topLevel.globalMargin
    anchors.left: parent.left
    anchors.leftMargin: topLevel.globalMargin
    anchors.top: titleText.bottom
    anchors.topMargin: topLevel.globalMargin / 2
    wrapMode: Text.WordWrap
}

Text {
    id: priceText
    text: product.price
    anchors.right: parent.right
    anchors.rightMargin: topLevel.globalMargin
    anchors.verticalCenter: parent.verticalCenter
}

MouseArea {
    anchors.fill: parent
    onClicked: {
        pendingRect.visible = true;
        spinBox.visible = true;
        statusText.text = "Purchasing...";
        storeItem.state = "PURCHASING";
        product.purchase();
    }
    onPressed: {
        storeItem.state = "PRESSED";
    }
    onReleased: {
        storeItem.state = "NORMAL";
    }
}

Android와 iOS는 기본 클래스를 사용합니다. 기본 클래스를 기반으로 Android 및 iOS용 파생 클래스가 있습니다:

인앱 구매

인앱 결제는 애플리케이션으로 수익을 창출하는 방법입니다. 이러한 결제는 애플리케이션 내부에서 이루어지며, 콘텐츠 잠금 해제부터 가상 아이템 구매에 이르기까지 다양한 항목을 포함할 수 있습니다. 이 데모는 인앱 결제를 위한 시스템 API를 사용하므로, 사용자에게 더 친숙한 결제 프로세스를 제공하며, 플랫폼에 이미 저장된 정보(예: 신용카드 정보)를 활용하여 결제 절차를 간소화할 수 있습니다.

라이선스 및 출처 표기

Android에 데모를 배포하는 것과 관련하여 자세한 내용은 Android GNU C++ 런타임 라이선싱을 참조하십시오.

예제 프로젝트 @ code.qt.io

© 2026 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.