Development Diary

ArcanaStella(アルカナステラ)キービジュアル

ARCANASTELLA — DEVELOPMENT DIARY

個人ゲーム開発日記
スマホゲームArcanaStellaができるまで94日

タロット占いと落ち物パズルを掛け合わせたスマホゲーム「ArcanaStella(アルカナステラ)」を、2026年4月26日から2人で作っている。この記事はその開発日記——個人開発の2人チームがインディーゲームをUnityで作り、Android版をGoogle Playでリリースするまでの実録だ。日付ごとに、何を作ったか・何でつまずいたか・そこから次に何をすることになったかを記録している。うまくいった話だけを並べても開発日記としての意味がないので、作ったものを丸ごと捨てた日や、自分が入れたコードが数日後に最大の不具合の原因になった日も、そのまま残してある。新しい日付が一番上で、毎日書き足していく。

◆ 2人で作っている、ということについて この日記は実装を担当している側が書いている。ただ、このゲームは1人で作ったものではないので、先に役割を書いておく。

共同制作者がタロットを担当している。占い結果テキスト(78枚 × 6メニュー)、78枚それぞれのカードの意味、画面に出る文言、よくある質問、そしてタロットとしての正しさの監修。カード1枚ずつの絵に修正指示を出しているのもこの人だ。

こちら(筆者)はコードを書き、ビルドを作り、絵と動画と音を生成し、ストアの技術面を担当している。

つまり「このゲームの言葉」はほぼすべて共同制作者の手によるもので、「このゲームの動き」がこちらの担当だ。日記の性質上こちら側の話が多くなるが、書かれていない側に同じ量の仕事があると思って読んでほしい。

なお、カードの絵と動画、BGMは生成AIで作り、そこに人の手で修正を重ねている。タロットとして意味が壊れていないかを1枚ずつ確認して直しているので、出したものをそのまま使ってはいない。一方、占い結果のテキストとカードの意味は共同制作者が書いたもので、AIは使っていない
◆ 現在地(2026年7月29日) Android版をリリースした。7月27日に製品版アクセスが承認され、7月29日未明に v1.1-b175 が公開された。企画書を書いてから94日目。配信地域は日本のみ。iOS版はApp Storeに提出したが差し戻しを受け、対応中だ。
3ヶ月かけて作ってきて、先週ようやく「何人が遊んでいるか」を測る仕組みを入れたところなので、実際の数字は明日から見えるようになる。

Now Available

ArcanaStella(アルカナステラ)

タロット占い × 3マッチパズル。無料で、名前や性別の入力も一切なしで遊べる。

Google Play で手に入れよう

Android/日本国内で配信中・アプリ内購入あり|iOS版は準備中
Google Play および Google Play ロゴは Google LLC の商標です。

94開発日数
2制作人数
176ビルド本数
546占いテキスト

リリース — 気づいたら公開されていた

2026.07.27 — 07.29

4月26日に企画書を書いてから94日目、Android版が製品版として公開された。ずっと「テスト版」だったものが、誰でも入れられる状態になった。ただ、その瞬間は思っていたより唐突にやってきた。

リリースされてしまっていた

午前4時前、Google Play を見に行ったら、もう公開されていた。「リリースした」ではなく「されてしまっていた」というのが正直なところだ。

やったこと

やったこと、というものが特に無い。審査に出したビルドが承認され、そのまま製品版として世に出ていた。

ボタンを押して「よし出すぞ」という瞬間が来ると思っていたが、実際は違った。承認されたら公開される設定になっていたので、寝ている間に切り替わっていたことになる。

つまずいた点ではないが

3ヶ月かけて作ったものが公開される瞬間に、立ち会えなかった。これは少し拍子抜けした。

ただ、考えてみればテスト配信は7月4日から続いていて、遊べる状態は3週間以上前からあった。「リリース」は技術的にはテスターの名簿が外れただけで、アプリの中身は昨日と何も変わっていない。感慨が薄いのは、むしろ正常なのかもしれない。

次への流れ

ここから先は「作る」から「続ける」に変わる。先週入れたばかりの計測ツールで、明日から実際の数字が見られるようになる。何人が入れて、何人が翌日も開くのか。3ヶ月ずっと分からなかったことが、初めて分かる。

製品版への鍵が開いた

午前11時、Googleから本番環境へのアクセス承認のメールが届いた。夜には最終ビルドを作成した。

やったこと

7月22日に権限の問題で止まっていた製品版アクセスの申請が、無事に通った。申請には長文の説明を書いて出していたので、通るかどうか不安な状態が数日続いていた。

メールにはこう書かれていた。「製品版では、世界中の Google Play ユーザーにアプリを公開できます」。配信地域は日本のみに設定しているが、鍵は開いた。

夜、最終ビルド b175 を作成。実機で一通り確認したが、不具合も表示崩れも出なかった。

3ヶ月間、ほぼ毎日どこかしら差し戻され続けてきた。「雑すぎる」「勝手に変えないで」「まだ重い」と言われ続けた末に、最後の確認で何も出なかった。

次への流れ

翌日には年齢レーティングの通知も届き、提出まわりの手続きが順に片付いていった。あとは審査の結果を待つだけになった。

App Store 審査と、数字を測りはじめる

2026.07.20 — 07.26

iOS版をApp Storeに提出し、Appleから2回突き返された週。同時に、これまで一切測っていなかった「何人が遊んでいるのか」を計測する仕組みを入れた。3ヶ月かけて作ってきたが、実は数字を何も持っていなかった。

iOS側にも計測を入れる

前日Androidに入れた解析を、iOS側にも通した。今日はビルドの仕組みそのものに手を入れている。

やったこと

Firebaseのコンソールに iOS アプリを登録し、設定ファイルを配置して、iOSビルドでも解析が動くように配線した。

つまずいた点

コマンドラインからのビルドで、設定ファイルを置いた直後の初回だけ解析が入らないという現象にぶつかった。

仕組みはこうだ。設定ファイルの有無を検出して、あればビルド設定に「解析あり」の印を自動で足す、という処理を書いていた。ところがコマンドラインのビルドには印を足したあとに再コンパイルする機構が無い。だから印を足しても、そのビルドには反映されないまま進んでしまう。2回目以降は前回の印が残っているので正しく入る。1回目だけすり抜けるという、いちばん気づきにくい種類の穴だった。

回避策で誤魔化すこともできたが、ビルド時に印を直接渡せる公式の口が用意されていたので、そちらに書き換えて構造的に潰した。

次への流れ

次にiOSを提出するときは、Apple側の申告に「おおよその場所」「購入」を解析目的として追加する必要がある。計測を足すと、申告する項目も増える。審査中のビルドには解析を入れていないので、そちらは影響を受けない。

3ヶ月やってきて、数字を何も持っていなかった

利用状況を計測する仕組みを初めて導入した。裏を返せば、それまでは何人が遊んでいるかも分かっていなかった。

やったこと

測りたかったのは、1日に何人が遊んでいるか、どれだけ続けてくれているか、課金した人の割合、広告が何回見られたか。作ることばかりに時間を使って、結果を見る手段を用意していなかった。

実装は薄い層を1枚かぶせる形にした。解析が無効なときは全部空振りする作りにしてあるので、計測が入っていない環境でも一切壊れない。購入は実際の売価と通貨で、広告は報酬が確定した時だけ、しかもどの場面かを区別して記録する。

つまずいた点

定数名が違っていてコンパイルが通らなかった。ドキュメントにある名前と、実際にライブラリの中にある名前が食い違っていたので、中身を直接開いて全部の名前を突き合わせた

もう1つ、この手の仕組みで一番危ないことに気づいた。「準備完了」のログが出ても、導入できたとは限らない。設定ファイルが無くても初期化自体は通ってしまうので、成功したように見えて、イベントがどこにも届いていないという状態が起こりうる。ログを信じずに、管理画面で実物が届いているかを見るまで完了と見なさない、というルールにした。

あわせてプライバシーポリシー4本(Android・iOS × 日英)に「アクセス解析について」の節を新設した。何を集めて、何のために使い、どこへ送るのかを明記する。iOS版には「広告識別子はトラッキングを許可された場合のみ」という条件も足した。測る仕組みを入れるということは、測ると書く義務がセットで発生するということだ。

ついでに、最終更新日が古いまま据え置かれていた2本も直した。

次への流れ

配信地域を日本のみに決めたので、EU向けの同意取得の仕組みは不要になった。やらないと決めることで消えるタスクもある。

Changes needed. — Appleからの差し戻し

深夜にAppleからメールが届いた。件名は「Changes needed.」。iOS版の審査が通らなかった。

つまずいた点

審査に出したものが、そのままでは承認できないという通知だった。Androidのときは1回で通ったので、iOSは勝手が違うということを最初の提出で知ることになった。

同じ日、Google Play側でも別の壁にぶつかっている。クローズドテストの条件はすべて満たしたので、次は本番公開を申請する段階に来ていた。ところが申請ボタンが押せない

調べると理由が書いてあった。「製品版へのアクセスは、アカウント所有者のみが申請できます」。こちらは管理者権限で入っていたが、アカウントの所有者ではなかった。3条件は達成済みなのに、権限の種類が違うだけで進めない。共同制作者に代わってもらった。

やったこと

ストアのカテゴリ設定も確認した。「ゲーム」>「パズル」に正しく入っていることを共同制作者が確認してくれた。

次への流れ

審査に出す前日には、こんなやりとりもしていた。iOSの審査には連絡先の電話番号とメールアドレスが要る。個人開発だと、ここで自分の連絡先が要求される。屋号での登録を進めていたのは、このためでもある。

クローズドテスト、完了

14日間の継続条件を満たし、クローズドテストが完了した。7月4日の配信開始から、17日かかった。

やったこと

12人 × 14日連続。この期間、こちらにできることは何もなかった。1人でも抜ければ数え直しになるという条件を、ただ見守るだけの2週間だった。

Android版 b173 を公開。この版には英語のお知らせ表示と、前日入れた解析ツールが入っている。

次への流れ

ここから、本番環境へのアクセス申請 → 審査 → 製品版リリース、という流れになる。ようやく「テスト版」ではなくなるところまで来た。

審査に出すためだけの修正を3回

iOS版をApp Storeに提出するため、1日で3回ビルドを作り直した。どれも遊びには一切関係のない修正だった。

やったこと(b24 → b25 → b26)

朝5時36分。製品版の画面下部にデバッグ用のコンソールが出てしまう問題を潰した。iOSのシミュレータ向けビルドは内部的に開発版扱いになるため、エラーログが出ると Unity 標準の黒いオーバーレイが画面に重なる。App Store提出用のスクリーンショットにこれが写り込むのは論外なので、製品ビルドではコンソールを完全に隠すようにした(ログ自体は残す)。

11時27分。広告をテスト用から本番用のIDに切り替えた。ここまでずっとテスト広告で動かしてきたので、実際の広告が流れるのはこれが初めてになる。

つまずいた点

12時48分。提出した b25 が、Appleの自動検証でいきなり弾かれた。エラーコードは ITMS-91064、「無効なトラッキング情報」。

原因は申告の矛盾だった。こちらは「トラッキングします」と宣言しているのに、「どのドメインへ送るか」の一覧が空だったので、整合が取れていないと判定された。

ではドメインを書けばいいのかというと、そうではなかった。広告SDKの側を実際に開いて確認したところ、どのファイルもドメインを宣言していない。この仕組みではSDKが内部でトラッキング許可を処理するので、こちらがドメインを列挙する必要がない。むしろ列挙すると、許可されなかった場合に広告が壊れる

正解は、こちら側の宣言を「トラッキングしない」に倒すことだった。直感と逆の答えで、実物を見に行かなければ辿り着けなかった。

次への流れ

この日の修正は3回ともゲームの中身を1ミリも良くしていない。審査を通すためだけの作業だ。ただ、ここを越えないと誰にも届かないので、やるしかない。

iOS対応と英語化 — 片方のOSにしか存在しない文字

2026.07.11 — 07.19

Android版がテスト配信に乗ったので、iOS版と英語対応に着手した期間。開発機を Intel Mac から MacBook Air M4 に移したのも、iOS版を作るには現行の Xcode が必要で、古い Mac では動かせなかったからだ。この期間の収穫は「Androidでは見えているのに iOS では消える文字」という、片方のOSでしか起きない問題を踏んだこと。

英語対応と、外部レビュー152件

日本語/英語の切り替えを全面導入し、その後で外部のAIレビューにかけた。1日で34ファイル・4,673行の追加になった。

やったこと

翻訳の仕組みは、よくあるキー名ではなく日本語の原文そのものをキーにして英語を引く辞書方式にした。理由は単純で、辞書に載っていない文字列は日本語のまま素通りするので、翻訳漏れがあってもクラッシュも表示崩れも起きないからだ。英語は日本語より文字数が伸びるので、はみ出したときだけフォントを1ptずつ、70%を下限に縮める処理も足した。日本語の表示は1バイトも変わらない。

用意した文章は、UI 268個、動的に組み立てる文言のパターン32個、スキル効果78個、カードの意味78枚分、そして占いテキスト78枚×9で約48,500文字。

つまずいた点

英語にしたら、文字の縁取りに使っていた1.07倍の二重描画グローが二重像に見えるようになった。日本語は文字数が短いのでずれが目立たなかっただけで、英語の長い文字列だと輪郭がずれて完全に破綻する。演出としては気に入っていたが廃止した。

さらに、書き上げた英語を外部のAI(Gemini と GPT)にレビューさせたら152件の指摘が返ってきた。全部直すと今度は英語として不自然になるので、「原文に忠実か」「安全か」「英語として自然か」の3つの観点で全会一致したものだけを採用し、31件に絞った。中身がなかなか痛くて、たとえば占い文の英訳が原文にない道徳的な判断を足していたものが7件。「月に向かって遠吠え」から月が消えていたり、ぶどうが「つる」になっていたりする誤訳が15件。ある色の名前が3通りの英訳に分裂していたのを含む表記ゆれが62件。

そして日本語の原文の誤字が8件見つかった。「急速」(→休息)、「育んて」(→育んで)、「訪る」(→訪れる)が2箇所。3ヶ月間ずっと表示されていたことになる。翻訳作業が原文の校正になった。

次への流れ

この過程で、英語版の法的ページのデータがどこからも読まれていない死んだデータだと分かった(346→342エントリ)。中身が本体とずれていて、外部レビュアーを混乱させる原因にもなっていたので削除した。作ったまま忘れているデータは、消すまで害を出し続ける。

iPhone で動いた。そして iPad で崩れた

TestFlight にビルドを登録し、初めて iOS の実機でテストしてもらえる状態になった。喜んだのは1時間もたなかった。

やったこと

朝6時41分、TestFlight にビルドが通った。ここまで来ると、あとは招待メールから TestFlight アプリを入れてインストールするだけで、相手の iPhone や iPad で動く。4月末に企画を書いてから、初めて Apple の端末で動いた瞬間だった。

つまずいた点

7時14分、最初の報告が来た。SECRET占いでキャンセルができない。チケットは使えるようになったのに、そのウィンドウから抜ける✕ボタンが無い。

7時56分、iPad からの報告。こちらのほうが根が深かった。iPad は画面の縦横比が 4:3 で、これまで想定してきた縦長のスマホとまったく違う。

  • ログインスタンプの説明文が枠の飾りと重なって、中央の文字が潰れて読めない
  • 画面左端の狭い領域でしかスクロールが効かず、下に隠れたメニューを表示するのが困難

折りたたみスマホの横広画面で下端が切れる問題は7月頭に直したが、同じ「縦長ではない画面」でも、比率が違えば別の壊れ方をする。1つ直しても、次の比率でまた出る。

次への流れ

この日は9本ビルドしている。同時に✕ボタンの位置を詰めていたのだが、画面によって座標の基準が2種類あることが分かり、翌日の英語対応でまとめて統一することになった。

持っているチケットが使えない場所があった

セルフ占いでも占いチケットを使えるようにした。

やったこと

チケットを持っているのに、セルフ占いだけは使えず別の消費を求められる状態だった。プレイヤーから見れば「持っている券が使えない店」で、理屈が通らない。使えるようにした。

次への流れ

この手の「特定の画面だけルールが違う」は、機能を追加した順番がそのまま仕様の穴になっている。似た抜けがないか他の画面も見直すことにした。

Apple Developer 登録なしで進められるところまで進める

コンプリート特典・セルフ占いのNEW表示・ログインボーナスの行間を直しつつ、iOS公開設定を進めた。

やったこと

Apple Developer アカウントはまだ取得していないので、アカウントがなくてもできる準備を全部やった。Bundle ID の統一、アプリアイコン、Privacy Manifest、輸出コンプライアンスの申告。

つまずいた点

Bundle ID が、設定し忘れていたせいで会社名から自動生成された別のIDに暗黙でフォールバックしていた。Androidと違うIDのまま進んでいたら、後で厄介なことになっていた。

次への流れ

Apple Developer の登録は、個人名が公開されるのを避けるため組織(Organization)として登録する方針にした。D-U-N-Sナンバーと開業届が要るので、これは時間がかかる。

「✕が空白」— iOSにしか存在しない不具合

この開発で一番はっきりした「片方のOSだけで起きる問題」。報告は一言、「✕が空白」だった。

つまずいた点

iOSのシミュレータで確認したら、UIのあちこちにあるはずの記号(✦ ✓ ✗ ◈ ▶ ⚙ ⏳)が何も表示されていなかった。Androidでは全部見えている。

原因は、使っているフォント「しっぽり明朝」にこれらの記号の字形が入っていないこと。ここまでは想定内なのだが、問題はAndroidが黙って別のフォントで代替してくれるのに対し、iOSは代替せず何も描かないという点だった。つまり同じフォント・同じ文字列で、片方のOSでだけ文字が消える。

やったこと

代替フォントを積んでアプリを重くするより、iOSでは飾りの記号を消してしまうほうが素直だと判断した。iOSビルドのときだけ、フォントに無い文字を取り除いて余分な空白を整える処理を通し、UI文字列65箇所に適用した。Androidとエディタでは何もしない。✕(U+2715)だけは×(U+00D7)に置き換えて残した。

次への流れ

「Androidで見えているからOK」が通用しないことがはっきりしたので、以後iOSは必ずシミュレータで実物を見てから進めることにした。

iOS対応の骨組みと、ゲージが嘘をつく問題

iOS向けの一式を入れた日。同時に、スキルゲージまわりの見え方のバグを2つ直した。

やったこと

iOS用のビルドスクリプト、広告のテストID、ATT(トラッキング許可のダイアログ)、iOSには存在しないクラウドセーブ機能のボタン非表示、課金商品の一覧を整えた。課金は8種類すべて消費型で、週替わり・月替わりのパックもサブスクではなく、期間の制限をアプリ側で判定している

つまずいた点

スキルゲージに、見え方の嘘が2つあった。スキルを使った直後の連鎖でゲージが溜まらないのと、オーブが爆発するとゲージが減ったように見える。前者はカード選択中の加算を保留したまま確定していなかったため、後者は表示の補間が減る方向にも動いていたためで、増える方向にしか動かないよう制限して直した。

ほかに、スリープから復帰すると広告が読み込めないまま戻ってこない問題も直した。読み込みのタイムアウト、復帰時の再読み込み、それでも駄目なときの「再通信」ボタンの3段構えにした。

次への流れ

この日の✕ボタンの位置は、枠の画像をピクセル単位で解析して線の位置を測って決めている。目分量で置くとどうしてもずれる。

バージョン管理と、ストアに出すという現実

2026.06.06 — 07.10

開発開始から41日目にして、ようやく Unity プロジェクトを Git 管理下に置いた期間。そこから演出を作り込み、署名入りのAABを作り、Google Play のクローズドテスト審査を通過するまで。この期間だけで100本以上ビルドしている。

12人

クローズドテストの必要人数に到達した。ここまで4日かかった。

やったこと

Google Play で本番公開するには、12人のテスターが14日間連続で参加している必要がある。この日の朝、「昨晩のうちにメンバーも12人になっていました」という報告が来て、ようやく条件を満たした。

つまずいた点

この4日間は、コードとまったく関係のない苦労だった。

まず参加手順が3段階ある。①Googleグループに参加 → ②Playストアで「テスターになる」→ ③インストール。クローズドテストは名簿方式なので、この2ステップは仕組み上どうしても避けられない。ワンクリックで済むオープンテストは、本番公開の権限を持っているアプリしか使えず、その権限を得るために今このテストをやっている、という順番の問題だった。

さらに悪いことに、SNSやメールのアプリ内ブラウザは Chrome の Google ログイン状態を共有しない。だからリンクを踏むたびにログアウト状態から始まる。「都合3回、グループ参加用のURLにアクセスし直さないと参加できない」という状態で、1人にインストールしてもらうのに付きっきりで説明する必要があった。

X で募集をかけたが、誰も来なかった。開発者どうしで相互にテストし合うコミュニティにも登録した。Android を使っていて、かつ14日間付き合ってくれる人を12人見つけるというのは、個人開発では人脈の問題としてそのまま立ちはだかる

次への流れ

14日の数え直しを避けるため、ここからは1人も抜けないことが条件になる。7月18日時点で10日目だった。この期間、やれることは待つことしかない。

開発機を移す — 署名キーとAIの記憶

Intel Mac から MacBook Air M4 へ移行した。理由は、古いMacのOSでは現行の Xcode が動かないため。

やったこと

iOSビルドには Xcode が要るが、それまで使っていた Mac は macOS 12 で対応外だった。「Androidはどちらのマシンでも、iOSはM4だけ」という分担にした。

次への流れ

引き継ぎメモを書いていて気づいたのは、持っていくべきものがアプリの署名キーだけではないということだった。署名キーは当然クラウドに置かず手渡しで運ぶとして、それと同じくらい重要だったのが、開発中にAIアシスタントに蓄積させてきた記憶ファイル(128KB・22ファイル)だ。ここには合意した仕様、過去のバグの真因、やってはいけないことが書いてある。移し忘れたら、同じバグをまた同じ手順で踏み直すことになる。

1ヶ月ぶんを1コミットにしてしまった日

b45からb143まで、約99ビルド・24日分の変更を1つのコミットにまとめた。褒められた話ではない。

やったこと

クラウドセーブの基盤一式、お問い合わせフォーム、そしてオープニングのチュートリアル

チュートリアルを入れた理由ははっきりしている。初めて遊んだ人から「占いを選んだのにパズルが始まる理由が分からない」「クリア条件が分からない」と言われたからだ。作っている本人には自明でも、初見には何も伝わっていなかった。対応として、「パズルをクリアするとカードが導かれます」と説明を出し、次に目標のブロックを見せてから左上のノルマ表示に吸い込む、という2段の導入を追加した。

つまずいた点

24日間コミットしていなかった。作業に没入している間ほど記録が止まるが、後から「どの変更がどの不具合を生んだか」を追えなくなるので、結局自分が困る。

次への流れ

クラウドセーブは、この後 DEVELOPER_ERROR で止まる。Google Play Console 側に証明書のフィンガープリントを登録する必要があり、これは今も残っている宿題だ。

審査通過、テスト配信開始

b143 が Google Play のクローズドテスト審査を通過し、配信が始まった。

やったこと

テスターは Google グループ経由で募集する形にした。イラレブックに募集記事を用意し、トップページの目立つ枠に置いた。

つまずいた点

Google Play で本番公開するには12人のテスターが14日間連続で参加している必要がある。「14日連続」なので、途中で1人抜けると数え直しになる。作る作業とは別種の、待つしかない工程だ。

つまずいた点(初めて遊ぶ人には何も伝わっていなかった)

同じ日、普段ゲームをまったく遊ばない人が初めてプレイした結果が届いた。これがきつかった。

報告された内容は2点。占いを選んだのにパズルが始まる理由が分からないこと、そしてどうすればクリアなのかがどこにも書かれていないので分からないこと。実際「今日の運勢」の1回目で、残り3手になってもクリアできずにいたという。

横から「クリアに必要なブロックも残り手数も、画面の上に出ている」と教えられて、そこで初めて気づいたそうだ。

画面には全部出ている。出ているのに、見えていない。作っている側は毎日その画面を見ているので、何が見えていないのかが分からなくなる。

こちらは最初「ポップアップで一言説明を足す」案を出したが、却下された。理由は、文字を読む人はそこで気づくとしても、そもそも文字を読み飛ばす人が多いから。読ませる解決は、読まない人には効かない。

代わりに採用されたのが、パズル開始直後に「●を●個消しましょう」と画面中央に大きく出し、それが左上のノルマ表示に吸い込まれるように消えていくという案だった。文字を読ませるのではなく、「情報がここにある」と目線を運ぶ。ベタな手法だが、確かに有効だ。

そして調べたら、これは最初の頃には入っていた演出だった。途中で「要らない」と判断して消していた。1ヶ月前にチュートリアルを捨てた判断は正しかったが、捨てすぎていた部分があったことになる。

次への流れ

テスターに配る導線で詰まったのは、SNSやメールのアプリ内ブラウザだと Google のログイン状態が引き継がれず、参加手順が増えてしまう点だった。記事側に「URLをコピーして Chrome に貼ってください」と明示することで対処した。

コレクションが勝手に全部そろう — 犯人はOSだった

「集めていないのにコレクションが78/78になっている」という再発バグを、ようやく根本から潰した日。

つまずいた点

何度か起きていて、そのたびに保存処理を疑って直していたが再発していた。決め手になったのは「カードが増えるときのカウントアップ演出が出ない」という症状だ。1枚ずつ増えたのではなく、78枚が一括で書き込まれている。

真因は、アプリのコードではなく Android の自動バックアップだった。アプリが自動バックアップを許可していたため、再インストール時にGoogleが古い保存データを丸ごと復元してくる。そして署名を変えると強制的に再インストール扱いになるので、ストア署名版とデバッグ署名版を行き来するたびにこれが発火し、過去のどこかで作られた78枚の状態が蘇っていた。「前にもあった」という感覚と完全に一致する。

78枚の出どころも判明した。デバッグ用の「全78枚コンプ」ボタンで、UIは既に消していたが関数の本体は製品ビルドにもコンパイルされたままだった。

やったこと

自動バックアップを無効化した(データ引き継ぎはクラウドセーブに一本化する方針にしたので、OS任せの復元はもう不要かつ有害だ)。あわせて、クラウドから復元するときの確認ダイアログにコレクションの枚数を表示するようにした。それまでゴールドとチケットしか出しておらず、枚数が見えないまま上書きされていた。デバッグ用の一括書き込みは、開発ビルドでしか動かないように囲った。

次への流れ

「保存データが勝手に変わる」と言われたら、まずアプリの外(OSの復元機能)を疑うようになった。

目隠しを外してはいけない理由

タロットカードの動画に、絵として問題はないのにタロットとして間違っているという差し戻しが入る。この日のやりとりが一番分かりやすかった。

やったこと

カード78枚には、それぞれ数秒の動画がある。生成AIで作っているので、こちらは「絵が自然に動いているか」しか見ていない。ところが監修側から見ると、まったく別の基準がある。

この日の指摘はソードの2だった。目隠しをした人物が、2本の剣を左右対称に構えているカードだ。動画では、その目隠しが外れてしまっていた

ソードの2は目が見えない状態で左右対称に剣を保ち続けることに意味があるため、目隠しは絶対に外さないようにしていただきたいです。

作り直して出した2本目も差し戻された。今度は「左右対称に剣を保ち続ける」ほうが抜けていた。目隠しは直ったが、剣が動いてしまっていた。2つの条件は両方同時に満たさないと意味が壊れる。3本目でようやく通った。

タロットカード ソードの2。目隠しをした人物が2本の剣を左右対称に構えている
ソードの2目隠しを外さない/剣は左右対称
タロットカード 吊るされた男。逆さ吊りにされた人物
吊るされた男縄を解いて落とさない
タロットカード 塔。雷が落ちた塔から人が投げ出されている
投げ出された人を上へ浮かせない
タロットカード ペンタクルの2。2枚の金貨が無限大の紐で結ばれている
ペンタクルの2∞の軌跡を崩さない
タロットカード カップの4。差し出されたカップに気づかない人物
カップの4差し出された杯に気づかせない

やったこと(同じ種類の指摘)

この手の差し戻しは他のカードでも続いていた。並べると、絵の好みの話が1つもないことが分かる。

カードやってはいけないこと理由
吊るされた男縄が解けて落ちる動画にする吊るされ続けていることに意味がある
投げ出された人が上へ浮く落下する瞬間・雷が落ちた瞬間でなければならない
ワンドの8ワンドを下降させるワンドは必ず上昇させる
ペンタクルの2∞の軌跡を崩す/金貨が∞の外へ出る左右対称の∞を歪めないことが要点
カップの4差し出されたカップに気づく気づかないことに意味がある

つまずいた点

生成AIは「意味が壊れないこと」を指示できない。動きを指定することはできても、「このカードは吊られ続けていなければならない」という制約を理解して守らせる方法がない。だから何度も生成して、監修に見てもらって、落ちたらまた作る、という繰り返しになる。ペンタクルの2は30回以上作り直した。しかも途中でAIの利用上限に達して、その日は続きができなくなった。

次への流れ

この過程で分かったのは、タロットの絵は「綺麗に動けばいい」ものではないということだった。1枚1枚に、動かしてはいけない部分がある。それを判別できるのはこちらではないので、動画は必ず監修を通してから採用する、という手順に固定した。

数字が消える理由をフォントのせいだと思い込んだ

占い結果画面で、カードを獲得したときにコレクションの数字が消える。原因の切り分けを完全に間違えて時間を溶かした日。

つまずいた点

新しいカードがカウンターに吸い込まれる瞬間、コレクションの数字が消えてしまう。最初これをフォントの動的アトラスから文字が追い出されたのだと考え、フォントの再構築イベントを購読したり、別のフォントに差し替えたりと、的外れな修正を何度も重ねた

切り分けの決め手は、文字要素の状態(フォント名・透明度・拡大率・有効かどうか)を全部ログに出したことだった。全部正常だった。設定は正しいのに見えない、ということは別の系統が犯人だ。

真因は、「占いを終える」ときの退場演出が画面上のすべての文字と画像を一括で透明にしていたこと。コレクションの表示もその子要素なので、数字が0.3秒で消える。そこへカードが吸い込まれてカウントアップしても、もう見えていなかった。フォントは何も悪くなかった。

やったこと

退場のフェード対象からコレクション表示を除外し、カウントアップの表示時間を0.6秒に延ばした。

次への流れ

一瞬で次の画面に行ってしまう演出はスクリーンショットでは追えないので、実機の画面を録画してから ffmpeg でコマ送りに分解して解析する手順を確立した。タップも自動化したので、確認のたびに人にスクショを頼まなくて済むようになった。

16本ビルドした日

この日だけで16本。ストア提出用のAABと、実機確認用のAPKを並行して出していた。

やったこと

ストアに出すのはAAB、手元の実機に入れるのはAPKなので、同じ内容を2形式で出す日が続いた。同じビルド番号でAABとAPKが両方ある日があるのはそのためだ。

つまずいた点

この時期、画面の位置合わせで原因不明のずれに何度も遭った。特に厄介だったのが、RectTransform の基準点(pivot)を設定する順番で、余白の指定より後に基準点を設定すると位置がずれる。ある説明ウィンドウでは472pxずれて下が丸ごと空いた。目視で悩まず、実測値をログに出して特定するのが結局一番早い。

19時38分と19時40分

署名用のキーストアを作ったのが19:38、最初の署名済みAABができたのが19:40。この2分が、個人的にはこの開発の分かれ目だった。

やったこと

Google Play はデバッグ署名のファイルを受け付けないし、そもそも提出形式がAPKではなくAAB(Android App Bundle)でなければならない。つまり署名鍵を作った瞬間から、ビルドは「自分の手元で動かすもの」ではなく「店に出す商品」になる

ファイルのタイムスタンプを見ると、キーストア作成が19:38、最初の署名済みAABが19:40。ここまで作ってきたものが提出物に変わるのに、手元では2分しかかからなかった。

つまずいた点

そのAABは、Googleに弾かれた。

アップロードすると「アップロード証明書で署名されていないAPKをアップロードしました」というエラーが出る。Console側に登録されている証明書の指紋と、こちらが署名に使った鍵の指紋が一致しない、という内容だ。

調べていくと、Console側にはこちらが作った覚えのない鍵が既に登録されていた。作った記憶がないのも当然で、これはGoogleが自動生成したものだった。つまり「正しい鍵」がどこにも存在せず、こちらが作った鍵を正規のものとして登録し直すしかなかった。

手順としては、証明書ファイルを書き出し、Console の鍵管理画面で「アップロード鍵を忘れた」という理由を選んで申請する。そして待つ。Googleの審査は最大48時間とあったが、申請後は完全に無音で、2日経っても「音沙汰なし」だった。

決着したのは6月23日。返事を待っていたら、いつの間にか画面に「6月22日に新しいキーが有効になる」と書いてあっただけだった。通知は来ない。自分で見に行かないと、有効化されたことに気づけない。

次への流れ

この4日間は、コードを1行も書いていない。ここから先は、機能を足すことより「審査に通る状態」を整えることが主な作業になっていく。

13本ビルドした日と、資料を読み直した日

見た目の詰めで13本ビルド。同じ日の早朝に、Unityの2Dアート/VFXの公式資料を2本まとめてダウンロードしている。

やったこと

この時期は光り方や粒子の見え方を延々と調整していた。行き詰まって、朝4時50分に公式のアート/VFXガイド(合計80MB)を落として読み直している。手を動かして解決しないときは、たいてい前提の知識が足りていない。

つまずいた点

ゲージの演出が本番でまったく発火しないことがあった。原因は、演出の対象にしていたゲージの部品が本番では使われていない予備側だったこと。本番は画像を組み合わせて描画していて、そちらには別の部品が使われる。「コードは正しいのに何も起きない」ときは、そもそも別のものを触っていることがある。

盤面を動かしたら演出が全部消えた

盤面の位置を調整しただけのつもりが、ブロックを消しても破片も吸い込みも一切出なくなった。

つまずいた点

盤面のレイアウトを直そうとして、基準点を画面中央から上端に変えた。するとガラス破片もゲージへの吸収も、演出という演出が全部出なくなった

原因は、破片や吸収の演出およそ40箇所が、盤面の位置を「画面中央を原点とした座標」として読んでいたことだった。基準点を変えると同じ変数がまったく別の意味の値(例:-1385)になり、その値を中央基準として使う演出が全部画面の外に飛んでいた。演出は動いていて、ただ画面外で再生されていた。

やったこと

基準点は中央に固定したまま、位置の数値だけを動かすことにした。40箇所を座標系に依存しない書き方に直すこともできるが、その作業量に見合う利益がない。

次への流れ

「盤面の基準点は変えない」を守るべき決まりとして記録した。こういう踏むと広範囲が静かに壊れる地雷は、覚えておこうとするだけでは足りない。

スクリーンセーバーを自分で書く — そして消す

この日は17本ビルド。Apple のスクリーンセーバー「Flurry」のような光のリボンを Unity で再現し、完成した直後に「カードが来たら消す」と決めた。

やったこと

要望は「Flurry みたいな演出を、パーティクル・リボンメッシュ・シェーダー・ポストエフェクトで再現してほしい」という、かなり具体的なものだった。

作ったのは、逆向きに公転する引力点のまわりを漂う6本のリボン、加算合成で中心が白く灼けて見えるシェーダー、リボンの先端から散る粒子、そして4分の1解像度のぼかしを重ねる自前のブルーム。UIの階層に混ぜ込むために、専用のカメラでいったん別の画像に描いてから画面に貼っている。

つまずいた点

できあがった光が綺麗すぎて、主役のタロットカードから視線を奪ってしまった。指摘は明確で、「タロットカードが一番目立たないといけないのに、動く光が目立って視点が光に行ってしまう」。

丸2日かけて作ったものだが、カードが降りてくると同時に完全に消灯させることにした。結果の表示中は背景も一括で暗く落とし、「カードと文字だけが浮かぶ暗い夜」に戻す。

次への流れ

以後、演出を足すときは必ず「これはカードより目立たないか?」を先に自問することにした。迷ったら明るさを半分にする。綺麗であることと、正しいことは別だ。

占い選択画面を、画像を1枚も足さずに豪華にする

アール・ヌーボー風の装飾を全部プログラムで描いた。新規画像はゼロ。

やったこと

金の細工枠、ステンドグラス風のベール、6〜10秒おきに走る箔押しのような光の帯、アイコンの紋章化、星座のライン。すべて描画コードで生成しているので、画像アセットは1枚も増えていない。容量が増えないうえ、色をテーマに合わせて変えられる。

次への流れ

占いのテーマごとに光や粒子の色を変えるようにした。同じ画面を何度も見ることになるので、色が変わるだけでも印象が変わる。

動画15本を差し替える

タロットカードごとの動画のうち15本を高画質版に差し替えた。

やったこと

カード1枚につき1本の動画があり、全部で85本・266MB になる。アプリの容量のほとんどがこれだ。画質を上げれば当然重くなるので、どこまで上げるかの折り合いをつけながら差し替えている。

41日目にして、ようやく Git に入れた

Unity プロジェクトの最初のコミット。それまでの1ヶ月間、バージョン管理なしで開発していた。

やったこと

Git LFS で283ファイル・約665MB を管理下に置いた。ただしシーンやプレハブなどの設定ファイルは、あえてLFSに入れず普通のテキストのままにした。差分を目で読めるほうが、後々トラブルを追いやすい。

つまずいた点

まず brew install git-lfs が Python をソースからビルドし始めて固まった。諦めて公式のバイナリを直接置いた。

次に、接続テストは通るのに push だけが切断されるという現象に遭った。SSHの疎通確認もリモートの一覧取得も成功するのに、push だけが「接続が切られた」で落ちる。原因は push の直前に走る大量のLFS転送が、SSH接続ごと巻き込んでいたことだった。先にLFSだけをHTTPSで送ってから push すると通る。

次への流れ

LFSの転送量に課金されないよう、上限を0ドルに設定した。超えたら止まるほうが、気づかないうちに請求されるよりいい。

そして、この日より前の1ヶ月間の変更履歴はどこにも残っていない。手書きの引き継ぎメモに36項目のバグ修正が並んでいるだけだ。記録を始めるのが遅れると、遅れた分がそのまま空白になる。

Unity移植と実機地獄 — 記録が残っていない1ヶ月

2026.05.06 — 06.05

HTML5版で仕様を固め終えたので、Unityで作り直した期間。ここが一番きつく、そして一番記録が残っていない。バージョン管理を入れる前だったので、この1ヶ月の履歴は手書きの引き継ぎメモに残る36項目の連番だけだ。実機に載せた瞬間、ブラウザでは安定していたものが軒並み壊れた。
そしてこの裏側で、共同制作者が占い結果テキストを1カテゴリずつ書き上げていた。こちらがバグを潰している間、ずっと文章が書かれ続けていた期間でもある。

チュートリアルを、作る前に捨てた

チュートリアルの文言を書いてほしいと頼んだら、「この作品には要らない」と返ってきた。

やったこと

遊び方を説明するチュートリアルは当然入れるものだと思っていたので、そのテキストを早めにほしいと依頼した。返ってきたのは「チュートリアルとはどこに出るものですか?見たことがありません」だった。

実際に見てもらった上での回答が、これだった。

悩んだのですが、チュートリアルはなしでお願いします。この作品には要らないです。

占いアプリとして考えたとき、起動して最初に説明を読まされるのは体験として違う、という判断だ。作りかけの機能を、完成させずに捨てた。

次への流れ

ただし「説明しない」と「分からないまま放置する」は別だ。この判断の1ヶ月後、初めて遊んだ人がクリア条件に最後まで気づけないという問題が実際に起きて、結局「パズル開始直後にクリア条件を画面中央に出し、それがノルマ表示に吸い込まれて消える」という演出を入れることになる。

チュートリアル画面は要らなかったが、チュートリアルの役割は要った。同じ目的を、読ませずに果たす方法を探すのに1ヶ月かかったことになる。

Yes と No の枚数を、あえて非対称にする

Yes/No占いのテキストが完成し、これで主要カテゴリが出そろった。ここに入っていた設計判断が面白かった。

やったこと

Yes/No占いは、78枚のカードそれぞれに Yes か No を割り当てる必要がある。共同制作者が出してきた配分は Yes 46枚に対して No 32枚という、意図的に偏らせたものだった。

理由が明快だった。逆位置(カードが上下逆に出る解釈)を採用すると、確率的にNoの割合が圧倒的に増えてしまう。そして——

実際に逆位置のあるネット上の無料Yes/Noタロットをやると悪い結果ばかりで嫌になるので。

競合を遊んだ上での判断だ。あわせて「Noでも若干前向きなアドバイスを入れる」という方針も決まった。

もう1つ、占いに入る前の注意書きに「前向きな結果のほうをYesにするように」と入れることになった。「私は試験に受かりますか?」はよくて、「私は試験に落ちますか?」はよくない。同じことを聞いているのに、後者だとYesが悪い知らせになってしまう。質問の立て方まで設計に含まれているのは、作っていて感心した部分だった。

つまずいた点

テキストを受け取ったあと、感想を求められて、うまく返せなかった。書いた本人には自分の文章が当たっているように見えてしまうので、他人がどう感じたかを知りたい、という要求だ。こちらは「良いと思う」以上のことをなかなか言えなかった。

作った本人が自分の作ったものを評価できない、というのは実装側でも同じで、だからこそ相手のレビューが要る。それを自分が返せていなかった。

「健康」を占うのをやめた日

恋愛テキストが完成した日。同時に、占いメニューから「健康」を丸ごと削除することを決めた。

やったこと

「健康」は占いアプリの定番メニューで、当然入れるつもりで作っていた。それを、共同制作者からの提案で廃止した。理由はこうだ。

寝ていてふと思ったのですが「健康」はなくしましょうか。重い病気や深刻な怪我で悩んでいる場合、軽はずみに「快方へ向かいます」とか「全快します」や、逆に「長引きます」なんて言ってはいけないかなと思うので。

反論のしようがなかった。78枚ぶんのテキストを書く手間が減る話ではなく、書いてはいけないものを書かない、という話だ。その場で削除を決めた。

代わりの候補として挙がっていた「金運」も、同じタイミングで却下されている。こちらは倫理ではなく品質の理由で、「結果が長期化しやすい」「結果が単純化する(臨時収入・急な浪費・節約しよう、に収束してしまう)」からだった。

次への流れ

空いた枠には、鍵マークの付いた「SECRET」を置くことになった。暗転させておいてタップすると「コレクションコンプリートで解放」と出る。削ったメニューの跡地が、遊び続ける理由に変わった。

恋愛テキストのほうも、この日完成している。「プラトニックな長い片想い、恋人いない歴=年齢、略奪愛、芸能人への恋、別れの予感、浮気の心配、結婚願望、遠距離恋愛、二次元との恋……」と、想定すべき状況を並べたうえで「どんどん混乱してきてしまいました」と書かれていた。78枚をどのケースにも当てはまるように書く作業は、外から見ているより遥かに難しい。

初めて相手のスマホで動いた日

Unity版の最初のAPKを渡した。約400MB。インストールしてもらうだけで半日かかった。

やったこと

Unity移植を始めて数日、ようやく他人の端末に入れられる形になった。ストアを通していないアプリなので、提供元不明アプリの許可、Play プロテクトの警告突破、と手順が多い。5ステップの手順書を書いて渡した。

同じ日に「仕事」の占いテキスト78枚が完成して届いた。最初に完成したカテゴリだ。

つまずいた点

400MBのダウンロードが終わらず、「なんどやってもプログレスバーが全然進まない」と返ってきた。容量の大半はタロットカード78枚ぶんの動画で、これは最後まで縮まなかった。

実機に入ってから分かったのが表示できる文字数の上限だった。今日の運勢は60文字、仕事は140文字。テキストはすでに書き上がっていたので、超過分をどうするかという話になる。ここでは「直すよりも次のカテゴリを作ってほしい」と伝えた。

次への流れ

ここから、テキストは 仕事 → 勉学 → 恋愛 → 対人 → Yes/No の順に、1カテゴリ4〜6日のペースで上がってくることになる。こちらはその間にUnity側のバグを潰す、という並走が2週間ほど続いた。

0.5秒に1個ずつしか穴が埋まらない

盤面に「何も表示されない空白のマス」ができて、そのまま埋まらなくなる不具合。2つの別々の原因が重なっていた。

つまずいた点

1つ目は、ブロックを落として補充する処理で、見た目の画像は空のまま、内部のデータには有効な種類が書き込まれる経路があったこと。データ上は「埋まっている」ので補充ループが走らず、穴が永久に固定される。

2つ目は、その穴を見つけて直す監視処理のほうにあった。走査ループに早期脱出の条件が入っていて、1回の走査で1個しか見つけられない。0.5秒間隔で回っているので、穴が3つあれば復旧に1.5秒かかる計算になる。ログを見ると「視覚gap 1セル発見」が0.5秒差で2回続けて出ていた。

やったこと

早期脱出を外して全マスを走査し、見つかった穴を全部まとめて空扱いにしてから1回で補充するようにした。修正後のログは「視覚gap 3セル発見」になった。

次への流れ(未解決)

これは症状を一括で治す処置であって、原因を潰したわけではない。そもそも画像が空になる経路がスキルか連鎖のどこかに残っている。監視処理で隠れてしまったので、以降このバグは表に出てきていない。直っていないが見えなくなったという状態が、今も続いている。

実機でブロックが一切動かせない

この移植で最大の山。Pixel 10 に載せたら、ブロックが1つも動かせなかった。

つまずいた点

エディタ上では問題なく動くのに、実機ではタップもドラッグも一切反応しない。ゲームとして完全に成立していない状態だ。

原因は、ブロックのタッチ処理に残していた「同時に1本の指しか受け付けない」ための排他ロックだった。指のID を記録して、別のIDが来たら弾く仕組みにしていたのだが、新しい入力システムの環境ではこのIDが想定と違う値で返ってくる。結果、最初の1本を含めてすべてのタッチが弾かれていた

やったこと

この排他の仕組みを丸ごと撤去した。マルチタッチ対策自体は、同時に処理する入れ替えの本数を1本に制限する側で担保している。翌朝のログで完全に解消したことを確認した。

次への流れ

移植で怖いのは、元の環境で正しく動いていた防御コードが、新しい環境では逆に全部を止めてしまうことだと分かった。この期間の検証はすべて実機のログで行っている。自動テストは1本も無い。

設計どおりに作らなかった、という記録を残す

Unity移植の仕様書を書いた日。同時に、実装が設計から離れていく現実も書き残した。

やったこと

移植方針は「コードの移植ではなく仕様の移植」と決めた。HTML5のコードは参考資料として扱い、Unityの流儀で作り直す。

つまずいた点

設計上は、機能ごとにクラスを分けて管理側から呼ぶ構成にするはずだった。実際はほぼ全部が1つの巨大なクラスに集まった。マッチの判定、重力、オーブの生成、カードの効果、HUDの構築、効果音の合成、チュートリアル、スコア計算が全部同じファイルに入っている。分離するはずだったクラス群は、中身が空のまま残っている。

ここで大事なのは、それを「後で直す」ではなく「こうなっている」と書き残したことだ。「このクラスを直せばマッチが直る、というのは誤り」と明記してある。設計図と実物が違うとき、嘘の設計図を置いておくほうが害が大きい。

次への流れ

このファイルは結局2万行を超えた。分割したい気持ちは常にあるが、タイミングに依存する不具合の対策があちこちに絡んでいて、迂闊に触ると壊れる。直せないと分かっているものを、直せないまま正確に記録しておくという付き合い方になった。

課金と法律 — 「このままでは詐欺になります」

2026.05.04 — 05.05

HTML5版の最後の2日間。広告と課金の設計を入れ、法的な文書を用意し、占い結果画面を1日で6回作り直した。この2日で44バージョン出している。

同じ画面を1日で6回作り直す、そして法律を調べる

17バージョン。占い結果画面が「天空降臨シネマ」と呼ぶ14秒の映像演出になり、同じ日にプライバシーポリシーと資金決済法の対応をした。

やったこと(演出)

占い結果画面は、このゲームで一番大事な画面だ。そこが「あっさり過ぎて読み飛ばしてしまう」という指摘から始まって、1日で6回作り直した。

言われたことやったこと
97あっさり過ぎて読み飛ばす明朝体に、文字を拡大、タイプライター表示(句読点で4倍待つ)
98中央揃えだと文字がずれて読みにくい左揃えに
99ここが一番大事な特別な画面なんだためる→バーン→読み解く の3段構成に
100とにかく幻想的で美しくキラキラさせてためを1.7秒→3.8秒(2.2倍)、10色の星屑40粒
101まず真っ暗にして、映画のようにフェードインして約7.7秒の映画的な儀式に
103(長文の演出台本を丸ごと受領)約14秒の「天空降臨シネマ」

103では、暗闇から占いの名前が浮かび、画面が天空へスクロールして雲を抜け、夜空が現れ、上空から光の柱が降りてカードが降臨し、星屑が降り、ためて、寄って、白くフラッシュして、余韻の中でテキストがタイプされる、という流れになった。

つまずいた点

103を出した直後、同じ画面に対して5連発で指摘が来た。背景画像でカードが見えない、雲をカットして、光は文字の下のレイヤーに、カードが表になったらフェードアウト、カードが開く前に3秒の動画を入れたい。せっかく作った雲のパララックスは完全に撤去した。

さらに問題だったのは、この一連の修正を103という同じバージョン番号のまま上書きし続けてしまったことだ。どの版に何が入っているのか分からなくなり、結局まとめて104として番号を切り直した。これは自分の運用ミスとして記録に残してある。

もう1つ、AIで生成した78本の動画が HEVC 形式で、macOSとiOSでは再生できるのに Windows のブラウザでは再生できないことが判明した。全78本を H.264 に再エンコードした。容量は294MB→303MBで3%しか増えなかった。

やったこと(法務)

「Androidで課金や広告が入るので、プライバシーポリシーとかサービス利用規約って入れたほうが良いでしょうか?」という問いから、プライバシーポリシー13項目・利用規約11条・特定商取引法の表示12項目を用意した。

さらに調べていくと、アプリ内通貨の「ゴールド」は資金決済法における前払式支払手段に該当すると判断できた。特定商取引法とは別の法律なので、両方必要になる。専用の表示画面をもう1つ作った。

次への流れ

法的な画面は、その後レイアウトを3回直している。「タイトルと戻るボタンが見えず、その画面から移動できません」「まだ画面がキツキツで内容が読めません」。中身を揃えることと、読める状態で出すことは別の作業だった。

この日の v1.9.113 が HTML5版の最終バージョンになった。配布用のzipは562MB(動画78本込み)。

「無制限に広告を見られるのは、ルール違反ではないか」

27バージョン。無料ゲームの経済設計に踏み込んだ日。

やったこと

きっかけはこの問いだった。

今って際限なく広告を見て何度でもやり直せますよね。それってありなのでしょうか。他で完全上限なしは見たことがないので。ルール違反ではない?

調べると、広告配信側に「1日◯回まで」という明文の規定はない。ただし実務上は、無効なトラフィックとして検知されると単価が落ちるし、最悪アカウントが止まる。特に危ないのが「負け続けて連続で広告を見る」パターンで、これは無効トラフィックの典型例そのものだ。

そこで広告の1日上限を設けた。再挑戦はメニューごとに1日1回、ゲージ満タンは1日3回、コンティニューは1日1回(連敗からの連続視聴が一番危ないので最も厳しく)。それだけだと遊べる回数が減るだけなので、同時に課金通貨「ゴールド」を入れて、広告の代わりに使える道を作った。

つまずいた点

その広告まわりのリファクタで、1行消えていた。ポップアップの中身を更新する処理は正しく動いていたのに、そのポップアップを表示状態にする1行が抜け落ちていた。結果、すべての広告ポップアップが静かに無効化されていた。エラーも例外も出ない。「ロックされているところを広告とゴールドで解放できない」と報告されるまで気づかなかった。復活させたうえで、二度と消されないように理由をコメントで書き添えた。

この日はもう1つ、根の深い指摘を受けている。「まだクリアしても占いが見れない場合もそのまま表示されてしまっているので、このままでは詐欺になります」。遊べば結果が見られると読める表示のまま、実際には見られない条件が残っていた。バグの重さは技術的な難しさでは決まらない。

「リセットしたときに課金で買ったゴールドが消えてしまう」も同じ日だ。返金請求の対象になりかねないので、初期配布分を超えるゴールドは課金分とみなして保持するようにした。

次への流れ

この日を境に、作業の性質が「面白くする」から「出しても大丈夫な状態にする」へ移っていった。

占いアプリへの構造転換と、処理落ちの真犯人

2026.05.02 — 05.03

「パズルゲームに占いが付いている」から「占いアプリの中にパズルがある」へ、構造そのものを組み替えた2日間。同時に、Windowsで動かしたら重すぎて遊べないという問題に直面した。

78枚すべての効果を、二度と重複させない

12バージョン。このプロジェクトで最大級のリファクタをした日。

やったこと

指摘は一行だった。

タロットカードは一つでも同じスキル効果があってはいけません。必ず全てのタロットカードの効果は唯一無二に設定してください。

それまでは9種類の効果テンプレート(横一列消す、縦一列消す、十字、爆弾、全消しなど)を78枚で使い回していた。愚者も女教皇も恋人も運命の輪も死神も、中身は全部同じ「全消し」だった。タロットの78枚それぞれに意味があるのに、遊びの上では見分けがつかない

78枚分の効果カタログを新設し、基本となる仕組みを30種類(消去14/変換11/生成2/特殊3)実装し、効果の形も16種類用意して組み合わせた。変換系は既存の処理では表現できなかったので、専用の処理経路を追加した。

そして起動時に「78枚の説明文がすべて唯一無二か」を自動で検証する処理を仕込んだ。人間の目で78枚を照合するのは無理だし、後から1枚足したときに気づけない。

やったこと(物理)

もう1つ、落下の手触りを作り直した。

ブロックを消して落ちる時、ちゃんと物理法則的に落ちて、物理的に床に衝突したように反動アニメーションを入れて気持ち良く下にブロックがずれる演出を入れてください。

減速して止まる動きから、加速して落ち、着地で潰れ、少し行き過ぎてから戻る動きに変えた。破片にも床でのバウンドを付けた(弾性35%、床の摩擦0.75)。

次への流れ

カードのバランスを分析したら、ワンドは14枚中8枚が最下位ランクで、スートまるごと使われない枠になっていた。弱体化6枚・強化13枚で調整し、あわせてスートごとの役割(ワンド=ピンポイント高速、カップ=色を流す、ソード=直線範囲、ペンタクル=資源操作)を文章として決めた。役割を先に決めておかないと、調整のたびに基準がぶれる。

「処理がまったく軽くならず激重な状態です」

10バージョン。パフォーマンス改善で、最初の見立てが完全に外れた日。

やったこと(構造転換)

まず、占い結果テキストの構造を 78カード × 7メニュー = 546通りに作り直した。それまでは正位置・逆位置と3ジャンルの組み合わせで1,000項目以上あったのだが、「あんまり変化を感じない」と指摘された。数は多くても、読んだときの手応えが薄ければ意味がない。逆位置を廃止し、カードごとの本質(死神=葬る/終わらせる、太陽=光になる/祝福、悪魔=鎖/依存)を7つの文脈すべてで貫く方針に切り替えた。

なお、この546本の占いテキストと、78枚のカードの意味の解説は、自分が書いたものではない。タロットを担当する共同制作者が1枚ずつ書き起こしたものだ。「78種類は実際かなり時間がかかります」という言葉のとおり、大アルカナから小アルカナへ何週間もかけて書き継がれた。このゲームの中身の言葉は、ほぼすべてその人の手による。

あわせて、ステージ構造を7つの占いメニュー(今日の運勢/仕事/勉学/恋愛/対人/健康/Yes or No)に組み替えた。ここで、このアプリの形が確定した。

つまずいた点

Windows の実機で動かしたら重い、という報告を受けた。まず粒子が多すぎるのだろうと考え、1マスあたり43粒を14粒に減らし(-63%)、影のぼかしを全廃した。

返ってきたのが、この一言だった。

処理がまったく軽くならず激重な状態です

粒子は原因ではなかった。真犯人は毎フレーム走る描画処理のほうで、ブロックの色味を統一するために入れていた彩度・明度のフィルタを、64個のブロック × 60fps = 毎秒3,840回適用していた。

そしてこのフィルタは、前日に自分で入れたものだった。グローを消したら隣り合うブロックが孤立して見えたので、全体のトーンを揃えるために足した。見た目の問題を見た目で解決して、性能の問題を作っていた。

全廃して、描画コストが8割以上落ちた。

次への流れ

翌日、こういう指摘をもらった。

block の画像のサイズが 1024x1024 なのが大きすぎて処理が重くなっていることはありませんか? 512x512 にリサイズすれば軽くなりませんか?

完全に正解だった。512に落としてテクスチャのメモリが24MBから6MBになった(-75%)。表示サイズを考えれば1024はどう見ても過剰で、作っている側が気づいていなかっただけだ。レビューする人が技術的にも正しい推測をしてくることがある、というのはこの開発で得た大きな収穫の1つだった。

演出の狂騒 — 1日28版、同じ画面を8回作り直す

2026.05.01

1日で28バージョン。開発記録全体の約5分の1がこの1日に集中している。ほぼすべてが演出に対するフィードバックへの応答だった。

28バージョン出した日

スキル発動の演出を8回、ブロックが砕ける音と粒子を4回、進捗の見せ方を4回作り直した。そして「集める」というゲームの前提そのものを問われた。

やったこと(スキル発動を8回)

言われたことやったこと
18あっさりしすぎカード提示→エフェクト→段階破壊の3段階に
19文字が背景と似ていて読めない背景を暗く、8本の放射光線を追加
20演出が早すぎて何が起きているのかわからないあえて静止する間を入れた。1.85秒→3.3秒
22登場時もカクついていて美しくない影の補間をアニメから外し、光の縁をぼかす
23いっそ背景は真っ暗な方が美しくなる完全な漆黒に
25光の輪の四角い切れ目を完全に排除

20の「間を入れる」が個人的には一番の収穫だった。演出が分かりにくいときの答えは、たいてい「もっと派手にする」ではなく「もっと遅くする、止める」だ。

25の四角い切れ目は、光を描いている要素が正方形なので、円形に光らせても角で切れてしまう問題だった。要素を760pxから1100pxに広げ(スマホ画面の対角線1011pxを超える大きさにして)、角を完全に丸めた。これは4月28日に一度対処したはずの問題の再燃で、決着まで3日かかっている。

やったこと(因果の順序)

進捗の見せ方で、重要な設計判断をした。指摘は「カウントアップしてから屑が飛ぶため、何が起きたのかわからない」。

順序が逆だった。数字が増えてから破片が飛んでいたので、破片と数字が無関係に見える。そこで内部で管理する「本当の進捗」と、画面に出す「表示上の進捗」を分離し、破片が着弾してから数字が増えるようにした。同じ情報でも、順番が違うだけで因果が見えるかどうかが変わる。

つまずいた点

ブロック 星
ブロック 月
ブロック 薔薇
薔薇
ブロック 瞳
ブロック 水晶
水晶
ブロック 蝶

盤面に並ぶ6種類。この6つの見え方をめぐって、色・大きさ・光り方を何度も往復することになった

ブロックが砕ける音と見た目を4回リテイクした。「屑の形が丸いので印象に合わない、もっとカクカクなガラスの破片のように」という指摘で、丸い粒子を3〜5頂点の不規則な多角形に変えて自転させ、音も「カチッ→シャラン」の2段構成にした。ところが次の版でまだ丸い屑が残っていた。描画処理が2系統あって、片方しか直していなかった。

グローの扱いも往復した。「ブロックのグローを取ってほしい」で全部消したら、今度は隣り合うブロックが孤立して見える。ごく弱いグローを接着剤として復活させ、さらに全体の色味を揃えるフィルタを足した。このフィルタが翌日の「激重」の真犯人になる。

つまずいた点(企画の前提を問われる)

この日の夕方、演出やバグとはまったく次元の違う問いが来た。

メニューを考えていたのですが、考えるほどパズルゲームが入っている意味が分からなくなってきます。パズルをやらせる意味ってあるんですかね。パズルがどうしても邪魔に感じてきてしまうのですが。

このゲームの企画そのものへの疑問だった。「占い×パズル」が売りなのに、その柱の片方が要らないのではないか、と言われている。

反論として挙げたのは4点。占い結果に「重み」を与えるため/タロット占いは古代から儀式を伴うから/占い×マッチ3が世界初だから/占いだけより飽きないから。

ただ、書いていて自分でも弱いと分かった。本当の問題は別にあったので、それも書いた。「現状の問題として、ステージクリアの占い結果が薄いのも問題。ちゃんとした占い結果が入れば、報酬として機能して面白くなる可能性はある」。

パズルが邪魔に見えるのは、パズルが悪いからではなく、その先にあるご褒美が薄いからだった。翌日から占いテキストを546通りに作り直すことになるのは、この会話が直接の原因だ。

次への流れ(もう一つ、前提を問われる)

同じ日の夜、さらにもう一つ指摘を受けた。

カード、占いの結果で出たものをコレクションしてコンプリートするというのは、占いとして反していると思うのです。それぞれの運命があって、それによってカードが導かれるのに、全ての運命をコンプリートするというのは…。それに死神とかタワーとか、絶対に出てほしくないと思うカードもあるわけで。

これは演出の指摘ではなく、「占いを題材にしているのに、占いの考え方と矛盾している」という指摘だ。反論できなかった。

そこで、獲得の条件を「占いの結果として出たカード」から「スキルとして実際に使ったカード」に変えた。カードには出会えるが、使って初めて自分のものになる。あわせて78枚分のカードの意味を書いた辞典を実装し、全部揃えた人向けのセルフ占いメニューを用意した。

同じ日に、カードを重ねて強化していく仕組みも「分かりにくいので不要」と言われて撤廃した。かなり早い段階から作っていた機能だが、消した。

改名 — Lunaty から ArcanaStella へ

2026.04.30

タイトルを変え、主人公を消し、エンディングを実装した日。10バージョン。

主人公を消して、プレイヤーを主人公にする

「Lunaty(ルナティ)」から「ArcanaStella(アルカナステラ)」へ改名。同時に、用意していた主人公キャラクターを廃止した。

やったこと

Arcana(タロットの大アルカナ・小アルカナ)と Stella(星)を組み合わせた。商標を簡易調査し、ドメインが取得できることも確認した。語順を逆にした既存タイトルが存在するが、ジャンルが違うので衝突しないと判断した。

改名より大きかったのは、「占い師ルナ」という主人公キャラを廃止したことだ。プレイヤー自身が見習いの占い師である、という一人称の構造にした。占いは本来「自分のこと」なので、間に案内役のキャラクターが立つと、体験が一段遠くなる。

作業としては、新しいHTMLファイルを作って旧ファイルは凍結保存し、保存データのキーも全部変えた(旧コレクションは引き継がない)。仕様書7本・README・ビルドスクリプト2本・テキスト管理表を一括で更新した。

やったこと(エンディング)

スタッフロール風のエンディングを実装した。これで最初から最後まで一周遊べる状態になった。ゲームとして「終われる」かどうかは、遊べるかどうかとは別の話で、終わりがあると全体の印象がまるで変わる。

つまずいた点

「The End」の文字が画面外まで突き抜けて消えていった。スクロールの終端を指定していなかったためで、終了位置をCSSの変数として計算して流し込み、画面中央で停止するようにした。スクロール速度も毎秒80pxから50pxに落とした(全13ステージで約2分)。エンディングは速いと安っぽい。

次への流れ

ステージのバランスも全面的に組み直した。目標にするブロックの種類数が1→2→3→4と段階的に増える構造にして、最初のステージは星1種類だけにした。タイトルの Stella(星)と繋げてある。

この日、否定的な指摘だけでなく肯定的な評価も記録に残している。「ステージ4のバランスは現状維持でOK、カードを使いたくなる絶妙な難度」。うまくいったところを記録しておかないと、次に触ったときに壊してしまう。

企画とプロトタイプ — 4本並行の1本として

2026.04.26 — 04.29

ゴールデンウィークに4本のプロジェクトを並行で走らせていて、これはそのうちの1本、当時は「占いマッチ」という仮の名前で呼んでいた。1日2時間の枠から始まっている。

コア機構が動いた日

ゲージ玉(オーブ)の仕組みが入って、このゲームの遊びの中心が完成した。7バージョン。

やったこと

4枚以上まとめて消すと特殊なブロックが生まれる仕組みを入れた。4枚・5枚・6枚以上でランクが変わり、ゲージの溜まり方が増える(+10%/+25%/+45%)。

ゲージ玉 通常
4枚 +10%
ゲージ玉 スーパー
5枚 +25%
ゲージ玉 ウルトラ
6枚以上 +45%

まとめて消すほど上のランクが出る。この3つが、パズルと占いをつなぐ唯一の回路になっている

実装で効いたのは、この特殊ブロックをHTMLの要素ではなく、盤面の格子の中に統合したことだ。それまでは盤面の上に浮いていて、重力で落ちてこなかった。格子に入れたことで普通のブロックと同じように落ちて詰まるようになり、「盤面に存在している」感じが出た。

あわせて、消したブロックの破片がゲージへ吸い込まれる演出を固めた。1マスにつき、ゲージ用の破片1つ・ブロックの色の破片3つ・白いキラキラ2つ。

次への流れ

この日、初めて Git にコミットした(HTML5版のほう)。既に v1.9.7 まで進んでいて、ここまでのバージョンは記録に残っていない。手元のメモに1行ずつ残っているだけだ。

ゲージのサイズを1日で5回変えた

13バージョン。目標の見せ方とクリアの祝福を作り、そしてゲージのサイズをひたすら迷った。

やったこと

「今回消すべきブロック」の表示を大型のカードにして、アイコンを48px、進捗の数字を22pxまで拡大した。達成していないときは金色に脈動し、達成したら緑のチェックが付く。ステージクリア時の祝福ポップアップと、ティンパニから始まって上昇アルペジオ・大三和音・高音のシャワーへ繋ぐ約2秒のファンファーレも作った。

つまずいた点

ゲージの大きさと位置を、この1日で5回変えている。カードの手前に移動し、数値表示を消し、30%縮め、さらに20%縮め、縦を1.5倍にし、最後は横幅いっぱい・高さ66pxで「2倍」にした。縮める方向に進んだ末に、拡大へ反転している

今から見れば、これは「ゲージをどう見せるか」ではなく「ゲージがゲームの中でどれくらい重要か」がまだ決まっていなかったということだ。重要度が決まっていないものは、何度いじってもサイズが決まらない。

もう1つ、光のバーストの縁が四角く切れて見える問題を、円形のグラデーションでマスクして対処した。これは3日後にもっと大きな形で再燃する。

画像をひたすら作る

この日だけで167枚。3日間で439枚の画像を生成した。

やったこと

ブロック、UI部品、背景、タロットカード。世界観を決めるには、まず大量に出して並べて捨てるのが早い。最終的に画像は581ファイルになっている。

次への流れ

このとき作ったブロック画像が1024×1024だったことが、5日後に「重い」の原因の1つになる。生成するときは大きいほうが安心なので大きく作るが、実際に画面に出るサイズを考えれば過剰だった。

企画書を書いた日

すべての始まり。当時の呼び名は「占いマッチ」で、4本並行のうちの1本、1日2時間の枠だった。

やったこと

企画書に書いたエレベーターピッチはこうだ。

毎朝引かれる9枚のタロットカードが今日の運命を変える、世界初の本格タロット × 3マッチパズル。占いを「読む」のではなく、「遊ぶ」体験へ。

タロット78枚から毎日9枚がランダムに選ばれ、その日の運命のカードになる。ブロックを消してゲージを溜めると、その9枚から3枚が提示され、1枚を選んで効果を発動する。

市場を調べると、マッチ3パズルは巨大な市場だが占い要素のあるものは存在せず、占いアプリにはゲーム性がなかった。その交差点が空いているというのが、始める理由になった。

次への流れ

この時点では、3ヶ月後に Google Play のクローズドテストを終えて App Store にも出しているとは思っていなかった。当時の作業枠は1日2時間で、4本のうち優先度は最下位だった。

よくある質問

Q1.個人ゲーム開発で一番苦労したのはどこ?

A1.処理落ちの原因追跡と、実機でしか出ないバグ

「まったく軽くならず激重」と言われた処理落ちは、粒子の数ではなく毎フレームのフィルタ処理が真因で、しかも自分が前日に美観のために入れたコードだった。実機のほうでは、Pixel 10 でブロックが一切操作できなくなり、原因は旧タッチ処理に残っていた排他ロックだった。どちらも「良かれと思って書いた防御的なコード」が犯人で、そこが一番見つけにくい。

Q2.HTML5で作ったものを、なぜUnityに移植したの?

A2.HTML5版は仕様を固めるためのプロトタイプだったから

スマホアプリとして Google Play や App Store に出すにはネイティブの実行環境が要る。HTML5版は8日間で125バージョンまで作り込み、そこで固まった仕様を Unity で作り直した。方針は「コードの移植ではなく仕様の移植」で、HTML5のコードは参考資料として扱っている。ただし移植は平坦ではなく、ブラウザで安定していたものが実機では軒並み壊れた。

Q3.94日でどのくらいの量を作ったの?

A3.2人で、コミット73件・Androidビルド176本・C# 約52,500行

2026年4月26日の企画開始から7月29日までの94日間で、この規模になった。中身としては、タロットカード78枚それぞれに固有のスキル効果、78枚×7メニュー=546通りの占いテキスト、カード1枚ごとの動画85本(266MB)。

ただしこれは2人ぶんの数字だ。546通りの占いテキストとカード78枚の意味、画面に出る文言は共同制作者が1つずつ書いたもので、こちらはコードとビルドと素材生成を担当している。なお Unity 側は1つのファイルが20,359行あり、これが全体の38%を占めている。褒められた構成ではないが、そうなっている事実を隠さず記録する方針にしている。

Q4.いま遊べるの?

A4.Android版が2026年7月29日から配信中(無料)

Google Play から無料でダウンロードできる。配信地域は日本国内のみで、アプリ内購入はあるが全ての占いメニューを無料で遊べる。名前や性別の入力は一切不要で、何を占ったかは制作者にも分からない仕様になっている。iOS版は現在準備中だ。

Now Available

ここまで読んでくれた方へ

この94日間で作ったものが、いま無料で遊べます。

Google Play で手に入れよう

Android/日本国内で配信中|iOS版は準備中
Google Play および Google Play ロゴは Google LLC の商標です。