AOYAMA Koji's プログラミングブログ - プログラミングを楽しく体験

【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】プログラミング初心者向け・入門編・基礎編初中級者向けプログラミング解説プログラマー向け実装解説[初心者向けゲーム開発入門]

2026/04/20
【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門]

 40年以上のゲームプログラミング経験をマンガで可視化。 今回はプログラミング。 指示をひとつひとつ順番に組み合わせて、意図しているものを作ります。
【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門]

プログラミングブログ記事一覧


[PR]

【マンガで感じる】プログラミング ~指示を順に番組み合わせて実現~


【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] 社長「まずは」「OXゲームをするために…」 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] 社長「盤面を準備してください」 クリスタル「承知しました」 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] プログラミング ~指示を順番に組み合わせて実現~ 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] (クリスタル)「メカ・ライン!」「お願い」 メカ・ライン登場 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] クリスタル「まず」「ペンの位置を(100,0)へ移動して」 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] (0,0)-(300,300)の白ボード メカ・ラインがペンの位置を(100,0)へ移動 座標を緑色で明示(dot16) 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] クリスタル「そこから」「(100,300)まで線を引いて」 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] メカ・ラインが指示された通りに黒い線を引く(途中の絵) 座標(100,300)を緑色で明示 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] (100,0)-(100,300)のラインが書かれたボード 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] クリスタル「次はペンを(200,0)へ移動」「そこから(200,300)」まで線を引いて 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] (100,0)-(100,300) (200,0)-(200,300) のラインが書かれたボード 座標(200,0)と(200,300)を緑色で明示 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] クリスタル「次は」「(0,100)から(300,100)まで線を引いて」 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] (100,0)-(100,300) (200,0)-(200,300) (0,100)-(300,100) のラインが書かれたボード 座標(0,100)と(300,100)を緑色で明示 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] クリスタル「最後に」「(0,200)から(300,200)まで線を引いて」 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] (100,0)-(100,300) (200,0)-(200,300) (0,100)-(300,100) のラインが書かれたボード 座標(0,200)と(300,200)を緑色で明示 メカ・ラインが引いている途中 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] 完成盤面(バーン) 【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] クリスタル「社長!完成いたしました」 社長「準備完了ですね!」 大喜び
次のエピソードへ
【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] 変数

OXゲーム開発編 第2話:エピソード「プログラミング」


 本エピソード「プログラミング」は、OXゲーム開発編 第2話です。
 OXゲーム開発編は、OXゲーム(三目並べ・マルバツ)の開発を通じて、ゲームプログラミングの基礎の基礎を解説しています。
 OXゲーム開発編の各エピソードは、それまでのエピソードのマンガ(と解説)を前提としていますので、 もし途中から読み始めた方は、ぜひ最初のエピソード「プログラム」から読み進めてください。


「プログラミング」のソースコード例


JavaScript

// (100,0)へペンを持っていく
oContext.moveTo( 100 , 0 );
// (100,300)まで線を引く
oContext.lineTo( 100 , 300 );

OXゲーム(三目並べ・マルバツ):盤面を描く「プログラミング」実装検証



[PR]

「プログラミング」とは:指示を順番に組み合わせて実現


 「プログラミング」の本質「指示を順番に組み合わせて実現」です。
 今回の例は、まず moveTo でペンの位置を決めて、そこから lineTo で線を引きます。 これらは、片方だけではうまく動きません。「順番」もとても重要です。 適切な順番で適切に指示することで、うまく動きます。
 このように、順番に組み合わせて実現するのがプログラミングです。 うまく動く指示の順番と組み合わせを発見すると、パズルが解けたような感覚で、楽しくなります。

ソースコードの仕組み


 今回のプログラムは、以下のような構造になっています。

ペンを移動する

// (100,0)へペンを持っていく
oContext.moveTo( 100 , 0 );
 oContext.moveTo は、oContext が指定する画像の中で、括弧内の座標に、ペンを移動するプログラムです。
 ここでは座標 ( 100 , 0 ) へペンを移動させます。
 描画はしません。 紙から話したまま、ペンを移動するイメージです。

線を引く

// (100,300)まで線を引く
oContext.lineTo( 100 , 300 );
 oContext.lineTo は、oContext が指定する画像の中で、今のペンの位置から、括弧内の座標の位置まで、まっすぐな線を引くプログラムです。
 ここでは座標 ( 100 , 0 ) から ( 100 , 300 ) まで線を引きます。

座標について


【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] 2次元座標系  プログラムで扱う画像には座標があります。 2次元の画像は (X,Y) の座標で表します。 基本的に左上が (0,0) で、右に行くほど X が大きく、下に行くほど Y が大きくなります。


 本プログラムの例は HTML の canvas (キャンバス) という仕組みを使用して、描画しています。
<canvas width="300" height="300">

 ここでは、幅(width)と高さ(height)をそれぞれ 300 と指定しています。 その場合、右下の座標が (300,300) になります。
 前述の oContext は、このキャンバスを指すようにプログラムされています。

「実装検証」で体験しよう


 前記「実装検証」セクションにて、ボタンがいっぱい並んでいます。 それぞれ、ボタンに記載のプログラムを実行します。 押す順番で結果が変わるところを、ぜひとも体験してみてください。
 なお、どの順番でボタンを押しても、それが原因で壊れることはありませんので、例えば lineTo を連続で呼んだりなど、怖がらずに色々と試してみてください!

【参考】実際の盤面描画プログラム全体


 本エピソードで解説している本質、プログラムは指示を順番に組み合わせたもの、という部分については、前述の通りです。
 ただし、実際の盤面描画プログラム(関数)は以下になりますので、気になる方向けに解説します。
 この解説および正確な理解には、関数や変数、オブジェクトなど後のエピソードで詳述する技術が必要です。 そのため、ここは読み飛ばしていただいて問題ありません。 もし用語を理解してから、この仕組みに興味が沸いたら、ぜひ戻ってきてください。


盤面描画JavaScriptプログラム全体

//**********************************************************************
// 初期盤面を描画
//**********************************************************************
function drawBoard() {
    // キャンバスエレメント(描画先)を取得
    let oCanvas = document.getElementById( "IdCanvasOX" );
    // コンテキスト(描画指示用紙)を取得
    let oContext = oCanvas.getContext( '2d' );
    // キャンバスクリア
    oContext.clearRect( 0,0 , 300,300 );
    // コンテキストに線の色と太さを設定
    oContext.strokeStyle = 'black';
    oContext.lineWidth    = 1;
    // コンテキストにパスを4本引く
    oContext.beginPath();
    oContext.moveTo( 100 , 0 ); oContext.lineTo( 100 , 300 );
    oContext.moveTo( 200 , 0 ); oContext.lineTo( 200 , 300 );
    oContext.moveTo( 0 , 100 ); oContext.lineTo( 300 , 100 );
    oContext.moveTo( 0 , 200 ); oContext.lineTo( 300 , 200 );
    // キャンバスに線を描く
    oContext.stroke();
}


1.キャンバスエレメント(描画先)を取得

let oCanvas  = document.getElementById( "IdCanvasOX" );
 まずは、キャンバスエレメント、すなわち描画先オブジェクトを取得して、変数 oCanvas に格納します。 このとき、HTML と JavaScript を連携するために、キャンバスに IdCanvasOX という名前(id)を付けます。
 具体的には、HTML のキャンバス部分を以下にします。
(HTML部分)
<canvas id="IdCanvasOX" width="300" height="300">


2.コンテキスト(描画指示用紙)を取得

let oContext = oCanvas.getContext( '2d' );
 次に、対象のキャンバスエレメントのコンテキストオブジェクトを取得して、変数 oContext に格納します。 コンテキストは、ここでは、描画を指示するための用紙、設計図のようなものをイメージしてください。
 実際の moveTolineTo の挙動は、直接キャンバスに線を引くのではなく、設計図に線を引きます。


3.キャンバスクリア

oContext.clearRect( 0,0 , 300,300 );
 最初に、キャンバスをクリアします。


4.コンテキストに線の色と太さを設定

oContext.strokeStyle = 'black';
oContext.lineWidth   = 1;
 次に、線の太さ(1)と色(black:黒)を、描画指示用紙に指定します。


5.コンテキストにパスを4本引く

oContext.beginPath();
oContext.moveTo( 100 , 0 ); oContext.lineTo( 100 , 300 );
oContext.moveTo( 200 , 0 ); oContext.lineTo( 200 , 300 );
oContext.moveTo( 0 , 100 ); oContext.lineTo( 300 , 100 );
oContext.moveTo( 0 , 200 ); oContext.lineTo( 300 , 200 );
 続けて、OX盤面の座標の通りに、描画指示用紙に4本の線を描くためのパス(ペンの動き)を書き込みます。
 ここでは moveTolineTo を 1行にまとめていることにご注意ください。 それぞれ行を分けても問題ありません。


6.キャンバスに線を描く

oContext.stroke();
 最後に、キャンバスに線を描画します。
 この stroke により、今まで oContext すなわち描画指示用紙に設定した線の太さや、色、パス(線の座標)に従って、まとめてキャンバスに線を引きます。

【職人の視点】直値ではなく定数を使おう


 本エピソードでは、座標を ( 100 , 0 )( 100 , 300 ) などと、数値を直接指定していました。

直値を使用する問題点


 こうした直値(ちょくち)指定は、プロとしては避けるべきプログラミングです。 それは、100300 が、どういう意味かわかりづらいプログラムだからです。
 実務的な問題もあります。 例えば、canvasの横幅を 300 から 600 に変更した場合や、3x3 マスを 5x5 マスに変更した場合などに、プログラムの多くの箇所を変更する必要があり、保守性に乏しいからです。

定数を使用


 そのため例えば以下のように定数を定義して、
// 定義
const iCANVAS_WIDTH        = 300;
const iCANVAS_HEIGHT       = 300;
const iBOARD_MARGIN_WIDTH  = 0;
const iBOARD_MARGIN_HEIGHT = 0;
const iSQUARE_COUNT_X      = 3;
const iSQUARE_COUNT_Y      = 3;
// 自動計算
const iBOARD_LEFT     = 0 + iBOARD_MARGIN_WIDTH;
const iBOARD_TOP      = 0 + iBOARD_MARGIN_HEIGHT;
const iBOARD_WIDTH    = iCANVAS_WIDTH  - iBOARD_MARGIN_WIDTH*2;
const iBOARD_HEIGHT   = iCANVAS_HEIGHT - iBOARD_MARGIN_HEIGHT*2;
const iSQUARE_WIDTH   = iBOARD_WIDTH  / iSQUARE_COUNT_X;
const iSQUARE_HEIGHT  = iBOARD_HEIGHT / iSQUARE_COUNT_Y;
 線を引くプログラムは、この定数を用いて以下にすべきです。
oContext.moveTo( iBOARD_LEFT + iSQUARE_WIDTH*iX , iBOARD_TOP );
oContext.lineTo( iBOARD_LEFT + iSQUARE_WIDTH*iX , iBOARD_TOP + iBOARD_HEIGHT );
 この iX には、横3マスであれば 12 が入ります。

解説では直値を使用


 プロとしてはこうあるべきですが、初心者向けプログラミング解説としては読みづらいプログラムになってしまいます。 そのため本エピソード以降も含めて、解説では直視指定を多用しますが、ご了承ください。
 保守性については、後のエピソードに「保守編」を予定していますので、改めてそこで詳細に解説予定です。


 なお、実はもっと根本的な話として、プロならグラフィックデザイナーが描いたグラフィックリソースを読み込んで使用するので、そもそも盤面描画プログラムは書かないのでは、という話もあります。 画像やリソースに関しても、後のエピソードで解説予定です。
 OXゲーム開発編では、すべてを JavaScriptプログラミング(とHTML)のみで完結します。

【職人の視点】パス登録からまとめて描画で並列処理


 マンガの解説では便宜上、lineTo が実施される度に、逐次キャンバスに描画する形で説明しました。
 しかし実際の盤面描画 JavaScript プログラムでは、前述の通り、すべてのパスを登録してから strokeまとめてキャンバスに描画します。
 この方式は、1本1本描画する方式に比べて、CPUGPU の描画終了を細かく待つ必要が無く、並列動作させやすくなります。 これは 3Dグラフィックスでも用いられている手法で、高速化に繋ががっています。
 CPU と GPU および、並列動作と高速化について詳しくは、後のエピソードで解説予定です。
[PR]

マンガで感じる!本当の基礎から学ぶゲームプログラミングとは


 「マンガで感じる!本当の基礎から学ぶゲームプログラミング」シリーズでは、 主に、ゲーム開発を題材として、プログラミング時に筆者が脳内でイメージするコンピューター内部動作や本質を、マンガにてお伝えします。

プログラミングの本質をマンガで理解


 AI時代のプログラミングは、本質理解が重要です。 本質を理解していれば、あとはAIに任せて、自身を持って完成したプログラムに責任が持てるでしょう。
 そのため本シリーズでは、コーディングの実例や詳細よりも、「本質をイメージとして感じられること」を最優先としています。 まずマンガで、情報をできる限り絞り、プログラミングの仕組みやコンピューターの内部動作を、物理的に可視化してお届けします。
 そして文章の解説で徹底的に深堀りします。

登場人物紹介

【マンガで感じる】プログラミング ~指示を順番に組み合わせて実現~ 【本当の基礎から学ぶゲームプログラミング】[初心者向けゲーム開発入門] 登場人物 社長 クリスタル メカたち  マンガで感じる!本当の基礎から学ぶゲームプログラミングシリーズには、主に社長、クリスタル、およびメカたちが登場します。 ※実在の人物とは関係ありません

社長

 本シリーズの偉い人です。
 マンガでは、指示すなわち「要件定義」を行います。

クリスタル

 社長の指示を、メカを活用して解決します。
 名前は、コンピューター内部で指揮者の役割を果たす「水晶発振子」に由来します。

メカたち

 用途に応じて多数存在し、果たす役割がそれぞれ与えられています。
 クリスタルの指示に従い、ある時はプログラムの変数や関数のように、ある時は電子回路の素子のように振る舞います。

「マンガで感じる!本当の基礎から学ぶゲームプログラミング」にかける想い


 筆者が本シリーズにかける想いや、 より詳しいコンセプトは「マンガで感じる!本当の基礎から学ぶゲームプログラミング」にて語っています。 そちらもぜひご覧ください。

AIを専属の家庭教師にしてプログラミングを学ぼう


 本記事では、本シリーズの根本となる「プログラミング」について解説しました。
 マンガを読んで興味が湧いた、解説のこのキーワードが気になった、などあれば、AIを専属の家庭教師に見立てて対話してみましょう。 各人の理解度に応じた質疑応答ができて、理解が深まりますので強くオススメします。
 プログラミングの本質理解に少しでもお役に立てれば幸いです。

補足

  • 本記事に記載のプログラムソースコードは、悪意のない範囲で自由に使用・改変していただいて問題ありません。ただし、ご自身の判断と責任でお願いします。
  • 記事内容の検討および検証・添削に生成AIの Anthropic Claude と Google Gemini を利用しております。
  • 記事内の画像の作成に生成AIの Google Gemini を利用しております。
  • 画像内のラスタライズ文字フォントにOpen Font LicenseNoto Sans JapaneseZen AntiqueDotGothic16を使用しております。
  • ※各社の登録商標または商標について「®」「™」等の表記はしておりません。



カテゴリー:マンガで感じる!本当の基礎から学ぶゲームプログラミング,OXゲーム開発編
[PR]