生成AIを使ってWebサイト上で動く簡単なゲームを作る(PHP)

2024年末～年始にかけて、体調を崩してしまった。
ずっと寝てたけど、いい加減寝てるのも飽きたので、ちょっと生成AIと戯れてみた。
そのときのメモ。

## 環境
・シンフリーサーバー

## 前提
・Web知識はHelloWorldできるくらいのレベル
・phpもかじったことあるだけ
・生成AIにはそれなりに助けてもらってる

## 成果物
 https://cf140604.cloudfree.jp/seiseiai/game/janken/index.php

## 対話内容

>ワイ「おはよう」
>Copi「おはようございます! 😊 今日はどんなことをして過ごす予定ですか？もしお手伝いできることがあれば、気軽に教えてくださいね。」

結果：
こいつ、、寝込んでるの知ってて煽ってきよる。。。

>ワイ「phpを使うサイトで、じゃんけんゲームを作りたいんだけど」
>Copi「それは面白そうなプロジェクトですね！PHPを使ってじゃんけんゲームを作るのは素敵な挑戦です。基本的な流れを説明しますね。」

結果：
この時点でindex.htmlとgame.phpのコードを提示してくれた。
ドロップダウンで手を選ぶようになってる、めちゃめちゃ簡単なコード。
htmlに文字コードが書いてなかったので、文字化けした。

>ワイ「文字化けしちゃうから、htmlに、文字コードをutf8にするって指定して」
>Copi「了解しました。HTMLファイルに文字コードをUTF-8に指定するためのコードを追加しますね。」

結果：
headのとこに、<meta charset="UTF-8">って書いてくれた。

>ワイ「累積の勝ち・負け・引き分けの回数を記録して、画面上に表示してほしい」
>Copi「では、累積の勝ち・負け・引き分けの回数を記録して表示するために、セッションを使ってデータを保持する方法をご紹介します。まず、PHPセッションを使ってゲームの結果を保存し、HTMLファイルに結果を表示するように変更します。」

結果：
game.phpにsessionつかって結果のR/Wする仕組みを書いてくれた。
かってにsessionって使い方を答えるあたりが生成AIっぽいなって思った。
じゃんけんで結果が出たほうにしか表示してくれなかった。

>ワイ「htmlのほうにも、累積の結果を表示してほしい。」
>Copi「了解です。では、HTMLファイルの方にも累積結果を表示するためのコードを追加しますね。game.phpで計算した累積結果をフォーム送信前に表示するためには、セッション変数を使用します。」

結果：
html側にも出すように改修してくれた。
ただ、自分の環境では、htmlファイルにphpコード書いても動かなかった。

>ワイ「数が表示されなかった。htmlファイル上に書いたphpコードが読めないみたいなので、index.phpにしてくれない？」
>Copi「了解しました！HTMLファイルをPHPファイル（index.php）に変更して、PHPコードを正しく読み込めるようにします。以下が修正されたindex.phpファイルです。」

結果：
index.phpにしてくれた。
今後も対話するので、こういう細かいことを自分でなんとかしようとせず
生成AIにお願いするのが大事だと思った。

>ワイ「累積結果の下に、今までのじゃんけんの結果をテーブル形式で表示させたい。自分の手と、コンピュータの手、勝敗の結果という3列で。」
>Copi「了解です。それでは、累積結果の下に、今までのじゃんけんの結果をテーブル形式で表示する方法を追加します。まず、セッションに各ゲームの結果を保存するためのコードを追加します。」

結果：
リザルトを出してくれるようになった。
このへんから、"あいこ"じゃなくて"引き分け"って表現を使うことが
気になったけど、まあいいやですました。

>ワイ「グー・チョキ・パーの選択を、ドロップダウンリストではなくて、個々にボタンで選択できるようにしてほしい。」
>Copi「わかりました。ドロップダウンリストの代わりに、個々のボタンで選択できるように修正します。」

結果：
めんどくせードロップダウンの選択が、改善された。

>ワイ「累積結果の勝ち・負け・引き分け数の右側に、同一セッションだけではない、すべての累計結果を表示させるようにしてほしい。」
>Copi「それでは、全ての累計結果を表示するために、セッションではなく永続的にデータを保存するための手段が必要です。簡単な方法として、ファイルに累計結果を保存し、読み込む方法を使用します。」

結果：
自分のセッション以外の結果も記録するようにしてくれた。
保持するデータが少ないからか、dbじゃなくてtxtで残す提案をされた。

>ワイ「result.txtの文字コードは、何を想定している？」
>Copi「良い質問です！特に指定がなければ、文字コードはUTF-8を使用することをお勧めします。UTF-8は広く使われており、様々な言語や文字をサポートするため、互換性が高いです。」

結果：
文字コードがわからんかったので聞いたら、お褒めいただいた。

>ワイ「累積結果も、テーブルで見えるようにしてほしい。行には、勝ち・負け・引き分けを、列には、自セッション・全体を表示したい。」
>Copi「了解しました。累積結果をテーブルで表示するために、修正します。行には「勝ち」、「負け」、「引き分け」を表示し、列には「自セッション」と「全体」を表示します。」

結果：
見栄えが悪かったので、テーブルにしてってお願いしたら、してくれた。
なんとなく、自分のなかでこうだってイメージがあったので、細かく伝えたら
それに応じた出力をするコードを書いてくれた。

>ワイ「累積結果の上に、勝率を表示させたい。勝率は、引き分けを除く、勝ち数/(勝ち数+負け数)にしたい。勝率は、セッション内の勝率と、全体と比べてどれだけ差があるか？という表示にしたい。」
>Copi「わかりました。累積結果の上に勝率を表示し、セッション内の勝率と全体の勝率の差も表示するように修正します。まず、勝率を計算する関数を作成し、表示するコードを追加します。」

結果：
勝率と、全体との差異が見れるようになった。
忘れたけど、なんかめっちゃ見づらかった。
今見直すと、聞き方が悪いような気がした。

>ワイ「勝率は、以下のような表記にしたい。全体より優れてるときはプラスを、劣っているときはマイナスをつけたい。勝率: 00% (+00%)」
>Copi「了解しました。それでは、勝率の表示を指定されたフォーマットに修正します。全体の勝率との差をプラスまたはマイナスで表記するようにします。」

結果：
見やすくなってんのか？はわかんないけど、指示した通りに直してくれた。

>ワイ「じゃんけんの結果を表示するgame.php上の累積結果もindex.phpのようなテーブル形式にしてほしい」
>Copi「了解しました。game.php上の累積結果もindex.phpと同様のテーブル形式で表示するように修正します。」

結果：
じゃんけんの手を選択する画面と、じゃんけんの結果画面でUIが違ってたので
合わせるようにお願いした。合わせてくれた。

>ワイ「game.phpに直接アクセスした場合には、index.phpに飛ばすようにしたい」
>Copi「了解しました。game.phpに直接アクセスされた場合にindex.phpにリダイレクトするためのコードを追加します。game.phpの冒頭で、POSTリクエストかどうかを確認し、POSTリクエストでない場合はリダイレクトするようにします。」

結果：
このへんから、game.php上でリロードしたときのエラーが鬱陶しく思えてた。
POSTリクエストか否かを判定するif分と、リダイレクトの処理を入れて対策してくれた。

>ワイ「引き分けの場合には、勝敗がつくまでじゃんけんを続けるようにしたい。また、累積結果から引き分けの行も消したい。」
>Copi「了解しました。では、引き分けの場合には自動的に再度じゃんけんを行い、勝敗が決定するまで繰り返すようにします。また、累積結果から引き分けの行も削除します。」

結果：
引き分け！って表示でじゃんけんが終わるのはおかしくね？っておもって
あいこでしょをできるようにお願いをした。
ここはエラーが出るようになった。

>ワイ「エラーになってしまった。Fatal error: Cannot redeclare determine_winner() (previously declared in game.php:34) in game.php on line 34」
>Copi「それは申し訳ありません。determine_winner関数が二重に宣言されていることが原因のようです。では、この関数を一度だけ宣言するように修正しましょう。また、引き分けの場合にループを行い、再度ゲームを実行する部分も調整します。」

結果：
エラーの解消をしてくれた。
ただ、この指示では狙い通りにならず、内部的にあいこだった場合に
コンピューター側の手だけ変えて再試行するようなコードを吐き出してきたので
画面上は、絶対あいこにならないじゃんけんが出来上がった。

>ワイ「引き分けの時には、ユーザー側に再度どの手を出すかを選択させるようにしたい。」
>Copi「了解しました。引き分けの時にユーザー側に再度どの手を出すかを選択させるために、再選択のフォームを表示するようにします。引き分けが発生した場合には、再度選択するためのフォームを表示し、勝敗がつくまで継続します。」

結果：
あいこでしょができるようになった。
判定的に引き分けになったとき、セッションやtxtに記録されないようになってた。
まあ、それはそれでいいかなと思ったので無視した。

>ワイ「index.phpの累積結果から、引き分けを消してほしい。」
>Copi「了解しました。index.phpの累積結果から引き分けの行を削除する修正を行います。」

結果：
引き分けが記録されなくなったので、引き分けに関する枠を消してもらった。
でも、やっぱ記録してほしいなって思った。

>ワイ「過去の結果を、ひきわけの場合にも記録するようにしてほしい。」
>Copi「了解しました。引き分けの場合も過去の結果に記録するようにします。そのために、引き分けの結果を追加する処理を行い、表示するように修正します。」

結果：
ちゃんと引き分けの時にも記録してくれるようになった。

>ワイ「対戦するコンピューターを5つ用意してほしい。どのコンピューターと対戦するか？は、じゃんけんの手を選択する画面上に表示し勝ち負けがついたタイミングで、ランダムで切り替わるようにしたい。コンピューターの名前は、A・B・C・D・Eとしてほしい。」
>Copi「了解しました。それでは、対戦するコンピューターを5つ用意し、勝敗がついたタイミングでランダムに切り替わるようにします。コンピューターの名前をA・B・C・D・Eとし、どのコンピューターと対戦するかを表示するように変更します。」

結果：
なんか、個性を持たせたいなぁと思って、対戦相手の概念を入れた。
このへんから、返答の文字数制限を超えたのか、一発で回答が来なくなった。
続きPlease！
しかも、Warningエラーがでるようになった。

>ワイ「じゃんけん後にエラーが出るようになってしまった。Warning: Undefined variable $totals in game.php on line 80 Warning: Undefined array key "losses" in game.php on line 80 Warning: Undefined array key "wins" in game.php on line 110」
>Copi「エラーの原因は、$totals変数が定義されていなかったためです。それを修正し、コードを再度確認しました。以下が修正された game.php ファイルです。」

結果：
Warningエラーは、なおしてくれた。
じゃんけんで勝敗がついた直後に出る結果画面で
対戦相手が先に変わっちゃう不具合が見つかった。
"勝ち負けがついたタイミングで"って言い方がよくなかったかなぁと思った。

>ワイ「結果画面のコンピューター名が、次に対戦する相手の名前に変わってしまっている。対戦した相手の名前にするようにしてほしい。」
>Copi「了解しました。対戦した相手の名前を正確に結果画面に表示するために修正を行います。」

結果：
直してくれた。
このへんから、もうかなりブラウザの動きが重くて
↑の質問の回答も、ずっとぐるぐる状態になってた。
やべー、会話リセットか！？って思ったけど、続けて"起きてる？"って聞いたら
"起きてますよ！"って言ってたから、続投した。

>ワイ「過去の結果に、対戦相手の名前の列を追加してほしい。結果の前に列を追加してほしい。」
>Copi「了解しました。過去の結果に対戦相手の名前の列を追加し、その列を結果の前に配置するように修正します。」

結果：
リザルトに対戦相手が誰だったか？を出してくれるようになった。

>ワイ「自分のセッション以外の過去の結果を一覧で表示できるようにしたい。別のページで見えるようにしたい。"過去の結果"見出しの横に別ページへのリンクを作ってほしい。」
>Copi「了解しました。過去の結果を一覧で表示する別のページを作成し、"過去の結果"見出しの横にリンクを追加します。」

結果：
勝ち負け数みたいに、自分以外のセッションの結果を見えるようにしたかった。
ファイルうんにゃん言ってこないので、多分伝わってねえなぁって思いつつ
今更見つかった感があるエラーが出たので、先にそれを対策してもらった。

>ワイ「初めてのページにアクセスする際に、以下エラーがでる。Warning: Undefined array key "current_computer" in index.php on line 49」
>Copi「初めてのページにアクセスする際に $_SESSION['current_computer'] が未定義のためエラーが発生しているようです。これを防ぐため、$_SESSION['current_computer'] が設定されていない場合に初期値を設定する処理を追加します。」

結果：
エラーは直してくれた。
ただ、やはり挙動が狙い通りじゃなかった。
質問をちょっと練り直してみた。

>ワイ「「別ページで見る」で閲覧できる過去の結果は、全体の累積結果のように、同一セッションだけではない、すべての結果を表示させたい」
>Copi「了解しました。それでは、history.phpファイルで全セッションのすべての結果を表示するように修正します。具体的には、ゲームの結果を保存するためのファイル（history.txt）を作成し、history.phpファイルでそのデータを読み込んで表示します。」

結果：
ファイルうんにゃん言ってきたので、たぶん大丈夫だろうと思って試した。
ちゃんとやってくれた。
長々会話した影響で、ガックガクになってた。いつ止まるかドキドキだった。

>ワイ「history.phpのテーブルには、以下2列を追加したい。・ユーザーのIPアドレス・対戦した日時」
>Copi「了解しました。history.phpのテーブルにユーザーのIPアドレスと対戦日時の2列を追加します。まず、game.phpでこれらの情報を記録し、次にhistory.phpで表示するように修正します。」

結果：
表示する情報を増やしてもらった。
キーにするわけじゃないけど、区別だけつくようにしたかった。
ここで、次の回答中にブラウザエラーがでて対話が続けられなくなったので、
新しいウィンドウで会話を始めることにした。

---


>ワイ「以下のコードをつかい、じゃんけんゲームを作成した。改修をしたいので、最初にコードを提供するから読み取ってほしい。/game.php〇〇〇 /history.php〇〇〇 /index.php〇〇〇」
>Copi「ご提供いただいたコードを確認しました。以下が game.php、history.php、および index.php の内容です。」

結果：
ちゃんと読み取ってくれたことを期待する。
もちろん、回答が長すぎて途中で切れてた。

>ワイ「対戦相手A~Eに、それぞれ個性をつけたい。A:最初に、××を出す確率が〇〇% B:あいこのとき、前に出した手と同じ手を出す確率が〇〇% C:あいこのとき、前に出した手と同じ手を出さない確率が〇〇% D:××と××を出す確率がそれぞれ〇〇% E:あいこのとき、前に出した手に負ける手を出す確率が〇〇%」
>Copi「対戦相手A~Eにそれぞれ個性を付けるためのコードを追加してみました。以下に修正内容を記載します。」

結果：
対戦相手に具体的な個性をつけるように指示し、実装してもらった。
細かく検証するのはやめた。たぶん、個性出たやろってくらいで満足。

>ワイ「UIが殺風景なので、CSS使って装飾してほしい。イメージは、干支の巳年の元旦。」
>Copi「素敵なテーマですね！巳年の元旦の雰囲気を取り入れたデザインを追加するために、CSSを使って装飾しましょう。以下にスタイルを追加したHTMLとCSSコードを示します。」

結果：
めっちゃ殺風景なUIを改善する素敵なcssコードを書いてくれた。
style.cssは、idじゃなくて、bodyとかに直接指定する感じになってた。
生成AIの作るcssって、そういうやり方が多い気がする。

>ワイ「引き分けの画面にCSSが適用されていないので、適用されるようにして」
>Copi「引き分けの画面にもCSSを適用するために、スタイルシートをリンクするタグを追加しましょう。」

結果：
あいこでしょの画面だけ殺風景なままだったので、直してもらった。
直してくれた。

## 所感
前にunityのコード書いてもらったときは、バグが多いしなかなか直さないしでつらい部分が多かったけど、今回のトライでは自分の手は必要ないくらいにちゃんと書いてくれた。生成AIの進化を感じた。
出身的に、"データ分析"の観点をちょっと入れてみたかった。そういう意味で最後の個性の数字は伏せてもらってるので、興味ある方はじゃんけんの結果を分析してもらって、コンピュータの個性を理解して無双してもらえると、すごくうれしいと思った。

あと、Qiitaに限らず、たくさん書いてるとダレてくるので、もっと簡潔にしないといかんなと思った。