ゲームの成果を検出するにはどうすればよいですか?


10

私は誤ってこれをstackoverflowに投稿し、そのサイトの提案に基づいてここに投稿しました...

これは非常に高レベルの概念的な質問です。ソフトウェアアプリケーションで、「アップロード」、「共有」、「コメント」など、4つの異なるアクションがあるとします。

そして、私は次のようなユーザーに達成バッジを与えたいです:

  • 新人-最初の5つのファイルをアップロードする
  • Junkieをアップロードする-1日に20個のファイルをアップロードする
  • ナイトクローラー-午前0時以降にファイルをアップロード
  • Share-a-holic-10種類のファイルを共有する
  • すべてが好き-20種類のファイルが好き

あなたはアイデアを得ます。ユーザーが特定のアチーブメントを達成したかどうかをチェックして、達成のためのロジックをコードにコンパイルする必要がないかどうかを確認する最良の方法は何ですか?そして..-コンパイル後に新しい実績を追加する機能を保持します(xmlまたはdb)-実績は特定のアクション、回数、および追加の基準(時刻など)を追跡する必要があります-検出はほぼリアルタイムであるため、ユーザーに通知されます実績が完了するとほぼ瞬時に

私の最大の質問は、達成されているこれらの成果をどのように検出するかです。私は:

1)すべてのアクションの後で、...(ほとんどリアルタイム)かどうかを確認します。2)別のプログラムに、一連のルールに照らして常にDBをチェックさせますか?(最も簡単)

私が見逃している別のパラダイムはありますか?多くのゲーム(iOSのjetpackなど)では、ロックを解除した瞬間にロックを解除した実績が通知されるので、間違いなくあると思います。非常に印象的でした。

ありがとうございました


アチーブメントシステムを設計または作成し、ゲームでの使用方法を知りたいですか?
Harrison Brock 2013年

回答:


6

あなたが一般的に行うことは、「達成」システムを持っていることです。発生したアクションは、アチーブメントシステムを呼び出して、「このことはただ起こっただけだ」と言います。

その場合、達成システムは通常、一連のルールであり、通常は単純な組み合わせロジックとさまざまな「イベント」のカウンターで構成されます。ルールとカウンターの助けを借りて、何が起こったのか、そしてどんな成果を与えるのかは、ワークアウトの成果システムの責任です。

これを行う理由は2つあります。

  • コードベース全体に状態ロジックを分散したくない場合。

  • 実績によっては、まったく異なるシステム/時間などで発生する可能性のある「もの」の組み合わせが必要になることがあり、このためのロジックをコードベースの周りに分散すると、不要な複雑さが大量に発生します。

過去に私が行った方法は、スクリプト可能なルールシステムを使用することです(スクリプト可能は非常に緩い用語であり、通常はデータ駆動型コンパレータの一種です)。したがって、次のようなものを言うことができます。

  • 「ユーザーが何かを押した」とき、「押された」変数が「インクリメント」されます。

次に、別のルールがあります

  • 「押された」変数が「何らかの値」よりも「大きい」場合、成果を「大げさ」に配ります。

多分

  • 「ユーザーがボスを殺す」と、「手渡し」の成果「だいぶ」が発生します。

アチーブメントシステムには、アチーブメントが既に配布されている状態を維持する役割もあるので、重複することはありません。


0

これをうまく処理する方法は、仕様パターンかもしれません。あなたは、一連の仕様のいずれかに一致するユーザーを定期的にユーザーに問い合わせるアチーブメントマネージャーを用意します。したがって、実績クラスには、名前、ロゴ、ポイントスコアなどが通常どおり含まれ、その実績を獲得したユーザーを説明する仕様も含まれます。たとえば、C#では、「Share-a-holic」の成果は次のようになります。

AchievementType ShareAHolic = new AchievementType
{
    Name = "Share-a-holic",
    Description = "Shared 10 files",
    Score = 25,
    Specification = (user => user.SharedFiles.Distinct().Count() > 10)
};

AchievementManager.AddAchievementType(ShareAHolic);

そして、適切な時点で、アチーブメントマネージャは次のようなことを実行できます。

foreach (AchievementType achievement in AchievementTypes)
{
    var users = DB.Users.Where(achievement.Specification && !(user.Achievements.Contains(achievement)));
    foreach (User u in shareaholics)
    {
        AchievementManager.Award(u, achievement);
    }
}

実績を.Award()すぐに検出できる場合は、適切な時点で実績マネージャのメソッドを直接呼び出すこともできます。特定のユーザーに対してこれらのチェックを実行するメソッドを追加して、重要なイベントの後にチェックをトリガーして、ユーザーがすぐに実績を取得できるようにすることもできます。


アチーブメントのパーティション分割はすぐに重要になります。AchTypeには、可能であれば、無関係なアチーブメントを回避するためにDB.Users.Where()を支援できる「sope」プロパティが必要です。したがって、ファイル共有実績がPvPでのみ授与される場合は、PvPのみを検索してください。略奪のような一般的なものはグローバルに実行可能であり、そのようなスコープを持っていないでしょう。
hpavc 2016年
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.