ゲームプログラミングC++
以下の本でSDLとOpenGLを用いたC/C++ゲーム開発の勉強を進めています。
各章には練習問題があるので、その問題の私なりの解答コードと詰まった箇所をここに残しておきます。
環境構築編はこちら
SDL_imageというライブラリを使うので、それの環境構築がまだな人は以下の記事から構築をしてください。
kurora-shumpei.hatenablog.com
練習問題1はこちら
kurora-shumpei.hatenablog.com
練習問題の内容
第2章ではゲーム開発というよりはゲーム開発の手法の説明が主題となっています。その流れでスプライトやアニメーションの実装を行い、最終的には背景のスライドと宇宙船のアニメーション描画+操作を行って終了です。
練習問題では、
- 人型のキャラクターを追加して、複数のアニメーションをサポートする
- アニメーションをループするかを指定できるようにする
- タイルマップ機能の実装
といったことを行います。
一応、ゲームオブジェクトに関する思考実験もあったのですが、それはこの記事で書くことではないかなと思ったので、省略しています。
練習問題の解答
解答のコードは以下のGithubのリポジトリのChapter2に置いています。Star押してくれたら下僕になります。
github.com
ただ、解答のコードはC/C++初心者の私が作成したもので、これが正解だ!というわけではありませんし、他にもっと簡単かつ上手い実装方法があるということを念頭に置いた上で上記の解答コードを参考にしてくれたらありがたいです。
個人的に詰まった箇所
コンポーネント指向
この章から、コンポーネント指向を取り入れた方法でゲーム開発を行います。Unityをずっと使っていた私としては馴染み深いものなのですが、いざ実装するとなると中々構造を把握することができずにソースコードの理解が滞りました...。
今でも完全に理解できたかどうかは怪しいので、確認のためにも、ここで使われているコンポーネント指向を取り入れた方法の解説記事とかを書こうかなとか思っています。
練習問題の指示内容
これは私の理解&実力不足なのかわかりませんが、各課題に取り組む前に詰まった箇所があったので一応書いておきます。
課題2.2
この課題では課題の文章の中でちょっと理解が及ばない箇所がありました。それは、「それぞれのアニメーションは、配列内のテクスチャの範囲として指定する」です。
うーん...、もう一回見てもよくわからない...。
テクスチャのアニメーションはすべて1次元配列にぶちこんで、0~3番のアニメーションはShipのアニメーションで、4~17番のアニメーションはCharacterのアニメーションとして扱う、といったことなのでしょうか???
よくわからなかったのと、上記のやり方は面倒に感じたので、2次元配列を用意して1行目にShipのアニメーション、2行目にCharacterのアニメーションといった風に実装しました。
ただ、この実装方法だとメモリを結構使ってしまうような気がしたので、あまり良い実装方法ではないような気がしました。やっぱり、1次元配列にしてやるのが正解なのか??
この辺りは時間があれば1次元配列の方法でも実装してみます。
課題2.3
この課題では、唐突にタイルマップというアプローチが紹介され、実装しろと言われます。あまり説明もなく、取り敢えず実装してね☆彡、という感じだったので中々鬼畜だなと思いました。
まあ、その辺も自分で調べて実装するというのがこの本のコンセプトのような気がするので良いんですが(自分を無理やり納得させた)、マップチップのサイズくらいは記載しといて欲しかったですね。
最近のAmazonレビューだと☆一つ消されちゃうやつですよ。
因みにマップチップのサイズは32x32です。常識だから書いていないとかだったらすごい恥ずかしい。
それと、タイルマップは以下の記事を参考にすれば割とすぐにできました。インターネットというのは本当に素晴らしいですね。
rina.jpn.ph
NULLとnullptr
コードを確認していたら、nullptrという見慣れない物体がありました。見た感じNULLの進化系かなんかだろうなとは思って自己完結させようとしたのですが、解説記事があったので貼っておきます。
maixtu-take-it-easy.hatenablog.com
NULL...、お前0だったのか...。
vectorのpush_backとemplace_back
vectorに要素を追加する方法を調べていたら、push_backとemplace_backという二つのやり方がでてきて、何が違うの??となったので、解説記事を貼っておきます。
まあemplace_back()の方が速くてナウい方法だよ!ってことです。
vectorの参照渡し
普段はPythonばっかり使って、ポインタとかアドレスとかを考えない生活をしているので、参照渡し?なにそれおいしいの?状態でした。色々調べたら分かりやすい記事があったので貼っておきます。
速度比較している記事もあったので貼っておきます。
今後は参照渡し使お
構造体のポインタ渡し
SDL_Textureに毎回「*」が引っ付いているのが気になったのです。SDL_Texureのリファレンスを見てみると構造体だったので、構造体とポインタについて調べてたらよさげな記事がありました。
ポインタってすごいんだねえ。
あと全く関係ないけど、「渡し」って入力しようとすると「私」に変換されてクソむかつく。
最後に
今回はChapter2の練習問題を扱いました。
1章と比べて難易度が急激に上がったような気がします。土日だけでやるのは難しいから平日も時間見つけてやらないとなあ...。
それと、今回のコードを実装していて気になったのが、メモリ関連のことです。C++なので、pythonとかと比べてメモリ管理を意識してプログラムする必要があります。ただ、今回はC++慣れるためにもメモリとかは何も考慮せずに実装を行いました。特にvector辺りは動的にメモリを確保してくれるのを良いことに、思うが儘に実装しました。
恐らく(というか絶対)、C/C++をがっつり使いこなしている人から見たら、クソコードになっているんじゃないかと思います。
なので、3章以降はその辺りを考慮したコードを書けるように努力する所存です。時間があれば前回と今回のコードを手直しするかもしれないので、手直ししたらTwitterとブログで更新したことをわかるように告知するつもりです。
まあ時間的にも実力的にも、当分はできないかなあ。