【AkashicEngine完全に理解した】環境構築からニコニコにゲームを投稿するまで

今年の10月末にニコ生の実験放送に自作ゲームを投稿できるようになった そうで、今回はそれについてまとめてみた記事です
この記事を読み終えた頃には、「AkashicEngine完全に理解した」って言えるようになります、たぶん

※本記事は グレンジ Advent Calendar 2018 22日目の記事です

AkashicEngineとは

[このページ] (https://dwango.github.io/articles/akashic/) を見ればわかりますが、自分なりにまとめると
iOSでもAndroidでもブラウザでも同様に快適に動き、多数の視聴者が同時にランキング対戦できる2Dゲームをjavascriptで簡単に作れるゲームエンジンです
おまけにツールも作れるらしいです

実際にどんなゲームがあるか気になった方は「つりっくま」で検索してみてください
実験放送で体感9割は遊ばれてる覇権ゲーです

環境構築~サンプル実行まで

node.js のインストール

ここからインストール(推奨版でOK)
homebrew で入れる場合は下記の記事を参考
【2018年版】macのhomebrewでnodebrew入れてからnode.jsを入れるまで

AkashieEngine のインストール

ターミナル(コマンドプロンプト) に以下のコマンドを入力

npm install -g @akashic/akashic-sandbox     
npm install -g @akashic/akashic-cli  

これこれ をインストールしてます

ここで npm ERR! Error: EACCES: permission denied, ~~ みたいなエラーが出た方は下記の記事を参考(自分がなりました)
npmでpermission deniedになった時の対処法[mac]

プロジェクトの作成

プロジェクトを作成したいフォルダに移動し、以下のコマンドを入力

akashic init

すると、以下のように解像度とFPSの初期設定を聞かれるので、それぞれ入力してEnter

prompt: width:  (320) 640
prompt: height:  (320) 360
prompt: fps:  (30)

解像度はニコ生の解像度と同じ 16:9 が推奨されています
入力すると、現在のディレクトリ下に必要なファイルが生成されます

サンプル実行

akashic initを行ったディレクトリで、

akashic-sandbox

と入力します
これでゲーム用のローカルサーバが起動しているので、http://localhost:3000/にアクセスすると、サンプルが実行されます

sample.gif

各ファイル・フォルダについて

ファイル・フォルダ名 説明
audio サウンドファイルを格納するフォルダ
image 画像ファイルを格納するフォルダ
script スクリプトファイルを格納するフォルダ
script/main.js ゲームのエントリポイント。最初は赤い四角が右に流れるだけのサンプルコードが書かれてる
.elintrc.json ESLint (JSの性的検証ツール) の設定ファイル。気になる方は「 ESLint 最初の一歩
game.json 解像度やFPS、各種アセットの情報等、さまざまな情報を記載するjson。詳細は「 game.jsonの仕様
package.json npmのモジュールに関数する情報。気になる方は「 package.jsonの中身を理解する
README.md マークダウンで書かれたreadme

audio , image , text フォルダ内には、必要なフォルダがgitで無視されないようにするために .gitkeep ファイルが入ってます
詳細については次のページの最下部に記載されています(少し情報が古い)
akashic-cli利用ガイド

ゲームの構成

akashic_constructure.png
ゲーム内に複数のシーンが存在し、シーンにエンティティ(シーン上に描画されるオブジェクト)を配置してゲームを構成します
エンティティは親子関係を持つことができ、動的に生成、破棄することができます
以下、サンプルコードにコメントを追加したものです

エンティティ

エンティティとは、シーン上で描画されるオブジェクトのことで、以下のようなものがあります

コンストラクタ名 機能
FilledRect 単色で塗りつぶした矩形を描画する
Sprite 画像を描画する
FrameSprite 画像を分割してそれらの一つを描画する。自動的にアニメーションさせることができる
Label 単一行テキストを描画する
SystemLabel システムフォントでテキストを描画する
E 複数のエンティティをまとめる
Pane 複数のエンティティをまとめ、領域でクリッピングする

シーンにエンティティを配置するには、次の2つのステップが必要です

  1. new 演算子でエンティティオブジェクトを作る
  2. シーンの append() メソッドでエンティティオブジェクトをシーンに追加する

※「 コンテンツ作成の基本 」より引用

ここでは全てのエンティティやそのプロパティについては説明しないので、気になったら上の表中の各"コンストラクタ名"をクリックしてください(公式リファレンスに飛びます)

エンティティができることの一部を、手っ取り早くスクリプトで説明します

実行すると以下のようになります sample2.gif

アセット

アセットの登録

akashic initを行ったディレクトリで、

akashic scan asset

のコマンドを実行するとアセットが game.json に自動で登録されます 登録されるのは以下のファイルです

  • script フォルダ下の .js , .json
  • image フォルダ下の .jpg , .png
  • audio フォルダ下の .aac , .ogg
  • text フォルダ下のテキストとして読み込むファイル

アセットの利用

画像・オーディオ・テキストアセットはシーン作成時に、assetIds プロパティにシーン内で利用するアセットIDを指定します

akashic scan asset で登録したアセットの assetId は基本的に拡張子なしのファイル名です
game.json の以下の箇所に記載されてます
1010.PNG

アセットを参照するときは、scene.assets["hoge"]といった感じで、scene.assets から assetsId をキーとして取得します

画像表示

画像表示はエンティティの Sprite を利用します

これだけでOKです
Spriteについての詳細は「 Sprite | @akashic/akashic-engine

オーディオ

ゲーム内で音を鳴らすには音ひとつごとに .ogg.aacのファイルが必要です
(様々な実行環境に対応するためらしい)
再生処理は一行だけです

オーディオアセットはデフォルトではループしない音として登録されます
ループさせる場合は game.json を以下のように変更します
0000.PNG BGMは音のループで実現させます

テキスト

テキストは以下のようにしてテキストデータを取得できます

文字列の表示

文字列の表示方法は、次の二種類があります

  • DynamycFontSystemLabel エンティティを利用して表示
  • BitmapFontLabel エンティティを利用して表示

ここでは後者の方法を説明します

前者は "サンセリフ体(ゴシック)", "セリフ体(明朝体)", "等幅フォント" の3種類が使えますが、安っぽい見た目になってしまうので説明は省略します。
気になる方は 「 色々な描画

アセットの準備

ビットマップフォントの表示には "フォント(jpg/png)" とそれに対応した "グリフ(json)" のアセットが必要です
ここではAkashicEngineの [サンプルデモの素材] (https://akashic-games.github.io/asset/material.html)からダウンロードしたものを使います

展開したファイルの font16_1.pngimage フォルダに、glyph_area_16.jsontext フォルダに移します
ファイルの中身を見るとわかると思いますが、
フォント画像 = "同じ大きさのフォントを並べた画像"、グリフ = "文字に対応したテクスチャ座標(左上)が記述されているjson"
といった感じです

アセットをフォルダに移したら akashic scan asset でアセットを登録します

ビットマップフォントの描画処理

スクリプトで説明します

これで以下のように文字列が表示されます 11112.PNG

入力イベント

"触れた", "移動した", "離した"といった入力を取得するイベント(ポイントイベント)は以下の二種類があります

  • エンティティに触れる入力
  • シーン上での入力

それぞれスクリプトで説明していきます

エンティティに触れる入力

シーン上での入力

evで扱えるプロパティはエンティティに触れる入力と同じです

ランキングモード対応

game.jsonenvironment に以下のように追記することで、ランキングモードのゲームとして扱われます 111111.PNG

ランキングモード対応のゲームは以下の条件を満たす必要があります

  • 一人プレイ
  • 一定時間でのスコアを競うゲーム
  • 0 ~ 99999 点のスコアを特定の変数に代入する

"特定の変数" とは g.game.vars.gameState.score のことで、ここに代入した値がスコアとしてランキングに利用されます
また、変数 g.game.vars.gameState.playThreshold にプレイ閾値を代入することで、そのスコア以下のプレイヤーを未プレイとみなし、ランキングから除外できます

ランキングモード時の残り時間はゲーム開始直後にサーバから通知される "セッションパラメータ" から受け取ります
以下のようにして受け取ることができます

これだけでランキング対応が完了です
ランキングに関しての詳細は「 ニコニコ新市場対応コンテンツ作成ガイド

ニコニコ新市場に投稿

ニコニコ新市場対応コンテンツの投稿方法」に全部書いてありますが、抜粋して簡略に説明します

1. game.jsonのあるディレクトリで、次のコマンドを実行

akashic export  html --output <zipFileName> --atsumaru

注意点

  • zipファイルの展開後のサイズが 10MB 以下でないと申請が通らない
  • script, text下のアセットの文字コードUTF-8 にしないと文字化けする恐れがある

2. 投稿ページ でゲームを登録 ※ニコニコのログインが必要

注意点

  • ここで指定した「ゲーム名」「アイコン画像」「紹介文」はニコニコ新市場にも反映される
  • 「アイコン」のサイズは 160x160 以上、320x320 以下 (正方形推奨)
  • 「ゲーム表示サイズ」はゲームの解像度と同じ値の指定を推奨
  • 「公開」にしないとニコニコ新市場に申請できない

3. 内容保存後、マイページで投稿するゲーム中の「その他 > ニコニコ新市場に登録申請」を選択
4. 「ニコニコ新市場へ登録申請」というダイアログが表示されるので、「申請」ボタンを押す
5. 投稿対象のゲームに「ニコニコ新市場に申請済み」と表示されたら完了

おわりに

ここまで読んだ方は「AkashicEngine完全に理解した」とこの記事をシェアしつつ、つぶやいてOKです

実験放送対応の自作ゲームはまだ少ないので、暇つぶしにでも作ってみてはいかがでしょうか