mcpField
G
game-distribution-js-sdk

game-distribution-js-sdk

github.com/hungify開発016 回インストール1 週間前に更新
リポジトリ

game-distribution-js-sdk について

ブラウザーゲームに GameDistribution の広告とライフサイクルイベントを組み込むための JavaScript SDK スキルです。初期化や広告処理、ポーズと音声の制御を扱い、プレイヤーやソーシャル機能は対象外です。

主な機能

  1. 01SDK 初期化と準備完了イベント
  2. 02インタースティシャル、リワード、バナー広告
  3. 03広告処理の Promise 対応
  4. 04一時停止・再開イベント処理
  5. 05ブラウザーの表示状態への対応

活用シーン

  1. 01ブラウザーゲームへの広告追加
  2. 02広告完了後の報酬付与
  3. 03広告中のゲームと音声の一時停止

インストール

コマンドをコピーしてターミナルで実行します。

$npx skills add https://github.com/hungify/playables-skills --skill game-distribution-js-sdk

インストール後、Claude Code で/game-distribution-js-sdkを入力して読み込まれたか確認します。

詳細

GameDistribution JavaScript SDK

概要

GameDistribution は、グローバルな window.GD_OPTIONS オブジェクトで設定する単一のブラウザー SDK(window.gdsdk)を提供します。SDK が読み込まれると、単一の onEvent コールバックを通じてライフサイクルイベントを発行し、広告をプリロードおよび表示するための Promise を返すメソッドを公開します。ネイティブ SDK は、次の機能をサポートしています。

  • gameId と単一の onEvent コールバックによる初期化
  • インタースティシャル広告(gdsdk.showAd())
  • リワード広告(gdsdk.preloadAd('rewarded') + gdsdk.showAd('rewarded'))
  • ディスプレイバナー(gdsdk.showAd('display', { containerId }))
  • SDK_GAME_PAUSE / SDK_GAME_START イベントによるライフサイクルの一時停止/再開シグナル

プレイヤー認証、ストレージ、決済、リーダーボード、ソーシャル API はありません。このプラットフォームでは、外部リンクへの移動も避けてください。

インストール

window.GD_OPTIONS を定義した後、ページに SDK スクリプトを追加します。スクリプト URL は固定です。

const SDK_URL = 'https://html5.api.gamedistribution.com/main.min.js';

function loadScript(src) {
    return new Promise((resolve, reject) => {
        const script = document.createElement('script');
        script.src = src;
        script.onload = resolve;
        script.onerror = reject;
        document.head.appendChild(script);
    });
}

SDK_READY イベントが発生すると、SDK は window.gdsdk として公開されます。

初期化

GameDistribution は、SDK スクリプトを追加する前に window.GD_OPTIONS を割り当てて設定します。必須フィールドは gameId のみです。これは GameDistribution のゲーム GUID です。すべてのライフサイクルイベントと広告イベントは、単一の onEvent(event) コールバックを通じて届きます。

const options = {
    gameId: 'YOUR_GAME_ID'
};

let platformSdk = null;
let isInitialized = false;
let currentAdvertisementIsRewarded = false;

const listeners = {
    interstitialStateChanged: [],
    rewardedStateChanged: [],
    bannerStateChanged: [],
    pauseStateChanged: [],
    audioStateChanged: []
};

function emit(name, payload) {
    listeners[name].forEach((cb) => cb(payload));
}

function initialize() {
    return new Promise((resolve, reject) => {
        if (isInitialized) {
            resolve();
            return;
        }

        if (typeof options.gameId !== 'string') {
            reject(new Error('Game params are not found'));
            return;
        }

        window.GD_OPTIONS = {
            gameId: options.gameId,
            onEvent(event) {
                switch (event.name) {
                    case 'SDK_READY':
                        platformSdk = window.gdsdk;
                        isInitialized = true;

                        // Optional: show an interstitial immediately once the SDK is ready
                        showInterstitial();
                        resolve();
                        break;
                    case 'SDK_GAME_START':
                        // Ad finished — game should resume
                        if (currentAdvertisementIsRewarded) {
                            emit('rewardedStateChanged', 'closed');
                            // Preload the next rewarded ad right away
                            platformSdk.preloadAd('rewarded');
                        } else {
                            emit('interstitialStateChanged', 'closed');
                        }
                        emit('pauseStateChanged', false);
                        emit('audioStateChanged', true);
                        break;
                    case 'SDK_GAME_PAUSE':
                        // Ad started — game should pause
                        if (currentAdvertisementIsRewarded) {
                            emit('rewardedStateChanged', 'opened');
                        } else {
                            emit('interstitialStateChanged', 'opened');
                        }
                        emit('pauseStateChanged', true);
                        emit('audioStateChanged', false);
                        break;
                    case 'SDK_REWARDED_WATCH_COMPLETE':
                        // Reward must be granted here
                        emit('rewardedStateChanged', 'rewarded');
                        break;
                    case 'SDK_GDPR_TRACKING':
                    case 'SDK_GDPR_TARGETING':
                    default:
                        break;
                }
            }
        };

        loadScript(SDK_URL).catch(reject);
    });
}

SDK が onEvent を通じて発行する主なイベント名は次のとおりです。

  • SDK_READY — SDK の準備が完了し、window.gdsdk を利用できます。
  • SDK_GAME_PAUSE — 広告が開始されます。ゲームプレイを一時停止し、音声をミュートします。
  • SDK_GAME_START — 広告が終了した(または表示されなかった)ため、ゲームプレイを再開し、ミュートを解除します。
  • SDK_REWARDED_WATCH_COMPLETE — ユーザーがリワード広告を最後まで視聴しました。報酬を付与してください。
  • SDK_GDPR_TRACKING、SDK_GDPR_TARGETING — GDPR 同意シグナル(通常、対応は不要です)。

広告

GameDistribution は、インタースティシャル広告、リワード広告、ディスプレイバナー広告をサポートしています。gdsdk のすべての広告メソッドは Promise を返し、広告を配信できない場合は reject します。

インタースティシャル広告とリワード広告のどちらが進行中かを記録しておく必要があります。これにより、共通の SDK_GAME_PAUSE / SDK_GAME_START イベントを適切な状態に振り分けられます。

インタースティシャル広告
function showInterstitial() {
    currentAdvertisementIsRewarded = false;

    if (!platformSdk) {
        emit('interstitialStateChanged', 'failed');
        return;
    }

    platformSdk.showAd().catch(() => {
        emit('interstitialStateChanged', 'failed');
    });
}

GameDistribution は SDK レベルではインタースティシャル広告の最小間隔を設けていません。ゲームロジックで必要になったときにいつでも showAd() を呼び出してください。

リワード広告

リワード広告は、表示する前にプリロードする必要があります。リワード広告が終了するたびに(SDK_GAME_START)、次の広告をプリロードしてください。

function preloadRewarded() {
    if (platformSdk) {
        platformSdk.preloadAd('rewarded');
    }
}

function showRewarded() {
    currentAdvertisementIsRewarded = true;

    if (!platformSdk) {
        emit('rewardedStateChanged', 'failed');
        return;
    }

    platformSdk.showAd('rewarded').catch(() => {
        emit('rewardedStateChanged', 'failed');
    });
}
バナー

ディスプレイバナーは、gdsdk.showAd('display', { containerId }) に渡す ID の DOM コンテナーに描画されます。以下の例では、固定 ID 'banner-container' を使用しています。

const BANNER_CONTAINER_ID = 'banner-container';

function createBannerContainer(position) {
    const container = document.createElement('div');
    container.id = BANNER_CONTAINER_ID;
    container.style.position = 'fixed';
    container.style.left = '0';
    container.style.right = '0';
    container.style.zIndex = '9999';

    if (position === 'top') {
        container.style.top = '0';
    } else {
        container.style.bottom = '0';
    }

    document.body.appendChild(container);
    return container;
}

function showBanner(position) {
    let container = document.getElementById(BANNER_CONTAINER_ID);
    if (!container) {
        container = createBannerContainer(position);
    }

    container.style.display = 'block';

    platformSdk
        .showAd('display', { containerId: BANNER_CONTAINER_ID })
        .then(() => {
            emit('bannerStateChanged', 'shown');
        })
        .catch(() => {
            emit('bannerStateChanged', 'failed');
            container.style.display = 'none';
        });
}

function hideBanner() {
    const container = document.getElementById(BANNER_CONTAINER_ID);
    if (container) {
        container.style.display = 'none';
    }

    emit('bannerStateChanged', 'hidden');
}

position には 'top' または 'bottom' を指定できます。バナーを非表示にしてもコンテナーの表示状態が切り替わるだけで、広告枠は破棄されません。

ライフサイクル/音声/一時停止

GameDistribution は、すべての広告の前後で発生する SDK_GAME_PAUSE と SDK_GAME_START イベントを通じて、ゲームの一時停止/再開を制御します。個別の表示状態 API や音声 API はありません。これらのイベントから両方の状態を判断します。

  • SDK_GAME_PAUSE の発生時:ゲームプレイを一時停止し、音声をミュートするか音量を下げます。
  • SDK_GAME_START の発生時:ゲームプレイを再開し、音声を元に戻します。広告が配信されなかった場合、このイベントは SDK_READY の後にも一度発生します。

GameDistribution 自体はタブ切り替えイベントを通知しないため、タブ切り替えへの対応には標準のブラウザー表示状態イベントを組み合わせてください。

document.addEventListener('visibilitychange', () => {
    const isHidden = document.visibilityState === 'hidden';
    emit('pauseStateChanged', isHidden);
    emit('audioStateChanged', !isHidden);
});

window.addEventListener('blur', () => {
    emit('pauseStateChanged', true);
    emit('audioStateChanged', false);
});

window.addEventListener('focus', () => {
    emit('pauseStateChanged', false);
    emit('audioStateChanged', true);
});

ストレージ

GameDistribution はプラットフォームのストレージ API を提供していません。プレイヤーの進行状況を保存するには、window.localStorage を直接使用してください。

コメント