Small BASICで簡単ブロック崩しを作ったよ

2010/3/11 読まれた回数4481
このエントリーを含むはてなブックマーク |  このページを Google Bookmarks に追加 | Yahoo!ブックマークに登録 | このエントリの Delicious history

窓の杜を見てたらSmallBASICって言語が紹介されていた。
ということで、早速ブロック崩しを作ってみたんだけど、
インストールから作成までが一日で出来るほどの簡単ぷりだったので作り方を紹介してみる。

完成図 SmallBASICはさっぱり知らない状態から数時間でブロック崩しが出来ちゃった。
ブロック崩しを作ってみました


Windows用Basicと言えばVisualBasicを思い出すけれど、実際にブロック崩しを作ってみるとVisualBasicより、もっとシンプルなN88 Basicやファミリーベーシックに近い感じがした。

※N88 Basicはかつてパソコン入門書とかにも載ってた超簡単プログラム言語)
 ファミリーベーシックはファミコンで動くBasic

VisualBasicで初心者が躓きやすい部分が隠されて、かなり取っつき易くなっている。

コンピュータを趣味程度に何か作ってみたいとか
初めてコンピューターゲームを作ってみたいと思う小学生たち、あるいはRPGツクールのような簡易ゲームエディタから次のステップとしても良さそう。

SmallBASICのインストール方法とブロック崩しの作り方

Small BASICの入手方法
Small BASICは無料で公開されている。
http://msdn.microsoft.com/en-us/ff384126.aspxでDownload Small BASICをクリック

ダウンロードしたインストーラを実行する。
Welcome to the Microsoft Small Basic v0.8 Setup Wizardが表示されたら
Nextをクリック

License Agreementが表示され承認するなら
I AgreeにチェックしNextをクリック

Select Installation Folderが表示されたら
インストール先を選択して
全ユーザが使用するならEveryone
インストールしたユーザーのみが使用するならJust meにチェックを入れてNextをクリック
途中でUACの確認画面が出たらOKを選択。
Installation Completeが表示されたらCloseをクリックでインストール完了

プログラムの実行
言語毎にショートカットが作られるので実行時は注意が必要
Small BASICを日本語で起動するにはスタートメニューから
「Small Basic」-「Localized」-「Microsoft Small Basic(Japanese)」を実行する。
(次回からは「Small Basic」-「Microsoft Small Basic」を直接実行してもOK)


動作画面はこんな感じで、VisualBasicと比べると随分とグラフィカルになってる。
特にトグル風に入力候補が表示されるのが目を引いた
SmallBASIC実行画面

ボタンの少なさも特筆的で
ファイルとクリップボードを除くSmall Basic特有のボタンは
インポート、発行、実行、等級をつけるの4つだけ

それぞれ、
インポートはMicrosoft Small Basic Program Listing上にあるプログラムをインポートする。
発行は逆にプログラムをMicrosoft Small Basic Program Listing上にアップロードする。
パフォーマンスは落ちるけれどSilverlightが入っていればブラウザ上で実行できる。
実行はプログラムをローカルで実行する Webで実行するのと違ってexeで実行されるのでパフォーマンスが良い
等級をつける(誤訳と思われる)はVisualBasicに出力できる

プログラムがWebでも実行できるあたりもScrachっぽい

言語はVisualBasicに近いけれど削られている部分もあって、
関数に引数を持たせられないとか、Functionが定義出来ないとかはビックリした。(方法を見つけられてないだけか?)

文法上の簡素さを保つために、Goto文とかグローバル変数だとか普通の言語だと汚いとされている方法が推奨されている感じがする。

逆に描画したオブジェクトがそのままクラスになって後から変更可能とかは素敵な仕様だと思う。
おかげで今回作ったブロック崩しでも関数すら使っていないのにソースコードが凄く少ないし、自然とオブジェクト指向になってる。

と言うことでブロック崩しのソースコードを解説

もっと簡単なプログラム HelloWorld!についての紹介も書きました。
初めてプログラムを作る人はHelloWorld!から見ることをオススメします。


GraphicsWindow.MouseMove = OnMouseMove
GraphicsWindow.MouseUp = OnMouseUp

マウス移動時とマウスクリック時のイベントハンドラを設定。
イベント = 処理する関数
と設定するだけ シンプル


width = 640
height = 480
padSize = 120
BOX_WIDTH = 64
BOX_HEIGHT = 24
halfPadSize = padSize/2

変数のセット。Basic同様変数を定義する必要はないけれど、
初期値が設定されていない変数を読み込もうとするとコンパイル時にエラーになる。
Const(定数)は使えないぽい


start:

Goto文で飛ばすためのラベル。
VBではエラーハンドリングぐらいにしか使われないGotoだけど、
マニュアルにはループにGotoを使っていたりしてN88っぽい
GotoでパスタになるようなプログラムはSmall BASICの出番じゃないんだろうな


GraphicsWindow.Clear()
GraphicsWindow.BrushColor = "White"
GraphicsWindow.DrawText(2,420,"Click to end")
GraphicsWindow.BackgroundColor = "Black"
GraphicsWindow.BrushColor = "Orange"
GraphicsWindow.PenWidth = 0

画面を描画するためにはGraphicsWindowオブジェクトを使う。
Clear()で画面を消し
BrushColor = "White"で描画色を白にセット
DrawText(2,420,"Click to end")で画面上 横2 縦420の位置にClick to endと出力
BackgroundColor = "Black"で画面の背景色を黒にする。
BrushColor = "Orange" 打ち返すパッドを作るために塗りつぶし色をオレンジにする
PenWidth = 0 枠線の幅を0にして枠を描画しない


pad = Shapes.AddRectangle(padSize, 12)

幅padSize、高さ12pxの長方形を変数padに設定する。
単に長方形が描画されるだけじゃなくて、padに長方形のインスタンスが格納される。
一回作っちゃえばpadのプロパティをいじって位置を変更したりも出来る

ブロックを作る。

GraphicsWindow.BrushColor = "Red"
boxCount = 0
For r = 0 to 9
 繰り返す処理
EndFor

Forでの繰り返しはBasic同様
For 変数名 = 初期値 To 終了値 [Step 増分値]
 繰り返し処理


box[r][c] = Shapes.AddRectangle(BOX_WIDTH-2,BOX_HEIGHT-2)

配列は添え字を[]でつけるのに注意
ここでは、作ったブロックを2次元配列に格納している
添え字を並べれば多次元配列もいけるし、初期化する必要もない

boxEnable[r][c] = "True"

ブロックが存在するかのチェックをBooleanで登録する。
Trueをダブルクオーテーションでくくるのに要注意


Shapes.Move(box[r][c],r*BOX_WIDTH+1,c*BOX_HEIGHT+1)

作成したブロックを並べる。
Shapes.Move(オブジェクト、横位置、縦位置)とするだけでオブジェクトを好きな位置に移動できる。
消去や再描画を考える必要がない


GraphicsWindow.Width = width
GraphicsWindow.Height = height

画面サイズを設定している。


runState = "True"
While(runState)
 繰り返す処理
EndWhile

While(条件)での繰り返し処理も可能。
今回は繰り返しの終了時はGoToで飛ばすようにしてみた



ySpeed = ySpeed + g
If ySpeed > maxYSpeed Then
ySpeed = maxYSpeed
EndIf
If ySpeed < -maxYSpeed Then
ySpeed = -maxYSpeed
EndIf
If xSpeed > maxXSpeed Then
xSpeed = maxXSpeed
EndIf
If xSpeed < -maxXSpeed Then
xSpeed = -maxXSpeed
EndIf
x = x + xSpeed
y = y + ySpeed

ボールの座標に速度を足してボールを移動している。
最高速度をセットすることで速くなりすぎないようにしている

If (x+SIZE+xSpeed >= width or x <= 0) Then
Sound.PlayClick()
xSpeed = -xSpeed
If x<=0 Then
x=1
Else
x=width-SIZE -1
EndIf
EndIf
If (y <= 0) Then
Sound.PlayClick()
ySpeed = -ySpeed
y=1
EndIf

壁に当たってボールが跳ね返る処理
Sound.PlayClick()は組み込みのクリック風の音を再生する。
もちろんPC内の音声ファイルを再生することもできる。


padY = Shapes.GetTop (pad)
padX = Shapes.GetLeft(pad)

パッドの座標を取得する。
特にプログラムしたわけでもないのに、あっさり好きな位置の座標が取得できるのが凄い


If (y+SIZE > padY and x+SIZE >= padX and x <= padX + padSize) Then
Sound.PlayClick()
padPoint = ((x + HALF_SIZE )-(padX+halfPadSize))
ySpeed = -(ySpeed*0.50 + (halfPadSize+SIZE-Math.Abs(padPoint))/30)
xSpeed = xSpeed + padPoint/20
y = padY-SIZE
EndIf

パッドとボールの衝突判定
座標を元に、パッドの中間位置に近いほど高く、
端に近いほど横に飛ぶように設定する。

Shapes.Move(ball, x, y)

新しい座標を指定するだけでボールが移動する。


xIndex1 = Math.Floor(x / BOX_WIDTH)
yIndex1 = Math.Floor(y / BOX_HEIGHT)
xIndex2 = Math.Floor((x+SIZE) / BOX_WIDTH)
yIndex2 = Math.Floor((y+SIZE) / BOX_HEIGHT)
xCrash = 0
yCrash = 0
If boxEnable[xIndex1][yIndex1] Then
xCrash = 1
yCrash = 1
EndIf
If boxEnable[xIndex2][yIndex1] Then
xCrash = xCrash-1
yCrash = yCrash+1
EndIf
If boxEnable[xIndex1][yIndex2] Then
xCrash = xCrash+1
yCrash = yCrash-1
EndIf
If boxEnable[xIndex2][yIndex2] Then
xCrash = xCrash-1
yCrash = yCrash-1
EndIf
If boxEnable[xIndex1][yIndex1] Then
Sound.PlayClick()
boxEnable[xIndex1][yIndex1]="False"
Shapes.Remove(box[xIndex1][yIndex1])
boxCount = boxCount -1
EndIf
If boxEnable[xIndex2][yIndex1] Then
Sound.PlayClick()
boxEnable[xIndex2][yIndex1]="False"
Shapes.Remove(box[xIndex2][yIndex1])
boxCount = boxCount -1
EndIf
If boxEnable[xIndex1][yIndex2] Then
Sound.PlayClick()
boxEnable[xIndex1][yIndex2]="False"
Shapes.Remove(box[xIndex1][yIndex2])
boxCount = boxCount -1
EndIf
If boxEnable[xIndex2][yIndex2] Then
Sound.PlayClick()
boxEnable[xIndex2][yIndex2]="False"
Shapes.Remove(box[xIndex2][yIndex2])
boxCount = boxCount -1
EndIf
If boxCount = 0 Then
Goto GameClear
EndIf
If xCrash <> 0 Then
xSpeed = -xSpeed * 0.9
EndIf
If yCrash <> 0 Then
ySpeed = -ySpeed * 0.9
EndIf

ブロックとボールの衝突判定
ボールの当たり具合でどのようにはじくのかを設定している。
※詳しく知りたい場合はAndroidでブロック崩しを見てね

If boxCount = 0 Then
Goto GameClear
EndIf

でボールの数が0個になったらクリア処理を行う


Program.Delay(7)

ボールの速度を調整するためにプログラムを一瞬停止している。

If (y > height) Then
Goto GameOVer
EndIf

ボールが奈落に落ちたらゲームオーバー処理を行う。


GameOver:
Sound.PlayBellRing()
GraphicsWindow.ShowMessage("You Lose", "GAME OVER")
Goto start

ゲームオーバーのメッセージを表示してスタートへ

GameClear:
Sound.PlayChime()
GraphicsWindow.ShowMessage("You Win", "CLEAR")
Goto start

ゲームクリアのメッセージを表示してスタートへ


Sub OnMouseMove
paddleX = Mouse.MouseX
Shapes.Move(pad, paddleX - padsize/2, GraphicsWindow.Height - 12)
EndSub

冒頭で設定したマウスが移動したときに呼ばれる処理。
マウスの座標を元にパッドを移動する。


Sub OnMouseUp
Program.End()
EndSub

マウスがクリックしたときに呼ばれる処理
プログラムを終了させる。


ソースコード全文は以下

GraphicsWindow.MouseMove = OnMouseMove
GraphicsWindow.MouseUp = OnMouseUp
width = 640
height = 480
padSize = 120
BOX_WIDTH = 64
BOX_HEIGHT = 24
halfPadSize = padSize/2
start:
GraphicsWindow.Clear()
GraphicsWindow.BrushColor = "White"
GraphicsWindow.DrawText(2,420,"Click to end")
GraphicsWindow.BackgroundColor = "Black"
GraphicsWindow.BrushColor = "Orange"
GraphicsWindow.PenWidth = 0
pad = Shapes.AddRectangle(padSize, 12)

GraphicsWindow.BrushColor = "Red"
boxCount = 0
For r = 0 to 9
For c = 0 To 8
box[r][c] = Shapes.AddRectangle(BOX_WIDTH-2,BOX_HEIGHT-2)
boxEnable[r][c] = "True"
Shapes.Move(box[r][c],r*BOX_WIDTH+1,c*BOX_HEIGHT+1)
boxCount = boxCount + 1
EndFor
Endfor

GraphicsWindow.Width = width
GraphicsWindow.Height = height
x = width /2
y = height /2
xSpeed = 0
ySpeed = 0

SIZE = 16
HALF_SIZE = SIZE / 2
maxYSpeed = 6
maxXSpeed = 2
x = width/2
y = width/2
g = 0.015
GraphicsWindow.BrushColor = "White"
GraphicsWindow.PenColor="White"
ball = Shapes.AddEllipse(SIZE, SIZE)

runState = "True"
while(runState)
ySpeed = ySpeed + g
If ySpeed > maxYSpeed Then
ySpeed = maxYSpeed
EndIf
If ySpeed < -maxYSpeed Then
ySpeed = -maxYSpeed
EndIf
If xSpeed > maxXSpeed Then
xSpeed = maxXSpeed
EndIf
If xSpeed < -maxXSpeed Then
xSpeed = -maxXSpeed
EndIf
x = x + xSpeed
y = y + ySpeed
If (x+SIZE+xSpeed >= width or x <= 0) Then
Sound.PlayClick()
xSpeed = -xSpeed
If x<=0 Then
x=1
Else
x=width-SIZE -1
EndIf
EndIf
If (y <= 0) Then
Sound.PlayClick()
ySpeed = -ySpeed
y=1
EndIf
padY = Shapes.GetTop (pad)
padX = Shapes.GetLeft(pad)

If (y+SIZE > padY and x+SIZE >= padX and x <= padX + padSize) Then
Sound.PlayClick()
padPoint = ((x + HALF_SIZE )-(padX+halfPadSize))
ySpeed = -(ySpeed*0.50 + (halfPadSize+SIZE-Math.Abs(padPoint))/30)
xSpeed = xSpeed + padPoint/20
y = padY-SIZE
EndIf
Shapes.Move(ball, x, y)
xIndex1 = Math.Floor(x / BOX_WIDTH)
yIndex1 = Math.Floor(y / BOX_HEIGHT)
xIndex2 = Math.Floor((x+SIZE) / BOX_WIDTH)
yIndex2 = Math.Floor((y+SIZE) / BOX_HEIGHT)
xCrash = 0
yCrash = 0
If boxEnable[xIndex1][yIndex1] Then
xCrash = 1
yCrash = 1
EndIf
If boxEnable[xIndex2][yIndex1] Then
xCrash = xCrash-1
yCrash = yCrash+1
EndIf
If boxEnable[xIndex1][yIndex2] Then
xCrash = xCrash+1
yCrash = yCrash-1
EndIf
If boxEnable[xIndex2][yIndex2] Then
xCrash = xCrash-1
yCrash = yCrash-1
EndIf
If boxEnable[xIndex1][yIndex1] Then
Sound.PlayClick()
boxEnable[xIndex1][yIndex1]="False"
Shapes.Remove(box[xIndex1][yIndex1])
boxCount = boxCount -1
EndIf
If boxEnable[xIndex2][yIndex1] Then
Sound.PlayClick()
boxEnable[xIndex2][yIndex1]="False"
Shapes.Remove(box[xIndex2][yIndex1])
boxCount = boxCount -1
EndIf
If boxEnable[xIndex1][yIndex2] Then
Sound.PlayClick()
boxEnable[xIndex1][yIndex2]="False"
Shapes.Remove(box[xIndex1][yIndex2])
boxCount = boxCount -1
EndIf
If boxEnable[xIndex2][yIndex2] Then
Sound.PlayClick()
boxEnable[xIndex2][yIndex2]="False"
Shapes.Remove(box[xIndex2][yIndex2])
boxCount = boxCount -1
EndIf
If boxCount = 0 Then
Goto GameClear
EndIf
If xCrash <> 0 Then
xSpeed = -xSpeed * 0.9
EndIf
If yCrash <> 0 Then
ySpeed = -ySpeed * 0.9
EndIf
Program.Delay(7)
If (y > height) Then
Goto GameOVer
EndIf
EndWhile

GameOver:
Sound.PlayBellRing()
GraphicsWindow.ShowMessage("You Lose", "GAME OVER")
Goto start

GameClear:
Sound.PlayChime()
GraphicsWindow.ShowMessage("You Win", "CLEAR")
Goto start

Sub OnMouseMove
paddleX = Mouse.MouseX
Shapes.Move(pad, paddleX - padsize/2, GraphicsWindow.Height - 12)
EndSub
Sub OnMouseUp
Program.End()
EndSub


Exe版の実行イメージ
SmallBasicでブロック崩し

ブラウザ上でプログラムを実行する
要Silverlight ※音が鳴ります


ソースコードを保存したフォルダにExeも出来るのでExeを実行も可能です。
Exe版ダウンロード
要SmallBasicLibrary.DLL



最近はプログラム言語が複雑になって初心者が取っつきづらくなっているから、こういう掴みやすくて結果が出やすい言語って凄く素敵だと思う。

「ネットやメール」しかしないなんてもったいないよ

関連キーワード

[簡易言語][SmallBasic]

コメントを投稿する

名前URI
コメント

トラックバック一覧

biac の それさえもおそらくは幸せな日々@nifty Firespeed ニッキ: Small BASIC で簡単 [http://bluewatersoft.cocolog-nifty.com/blog/2010/03/small-basic-b04.html]

トラックバック URL(β)

テルマエ・ロマエ 一巻

2010/3/6 読まれた回数1118
このエントリーを含むはてなブックマーク |  このページを Google Bookmarks に追加 | Yahoo!ブックマークに登録 | このエントリの Delicious history

ドロヘドロ以外で久しぶりに漫画を買ったよ
しかもかなり変なギャグマンガ

テルマエ・ロマエっていうタイトルなんだけれど
ローマ時代の浴場技師ルシウスが、
ある日突然日本の銭湯にタイムスリップしてしまう。

日本の風呂文化に驚愕したルシウスは、見よう見まねで風呂技術をローマに伝えていく

過去の人が現在にタイムスリップして驚き戸惑うっていう流れは使い古された感じがあるけれど、ありがちな現在技術すげーで終わらずに、ローマと日本における風呂文化の対比がうまく描かれていて、読んでいる方が逆にローマ時代にタイムスリップしたみたいな気持ちになれる。

ローマ時代の風呂も凄かったんだね、 一度入ってみたいし
金属の垢擦りとか試してみたい

フルーツ牛乳のおいしさに感動するけれど、牛乳瓶がうまく作れないとか、蓋を空けようとして瓶に指をつっこんでしまうとか
「王様はロバ」的な緩いギャグマンガタッチなほのぼの調もツボ
展開もだらだらと引き延ばさずに数ページで元のローマ時代に戻ってしまうスピーディーさでサクサク読める

1巻しか出てないけれど、かなり濃いよ
続編を作っているみたいだけどこんなに濃くてネタ切れにならないのか心配

関連日記

kenzの日記 最近買った本2冊

kenseiの日記 今月の本2009 Pert2

kenzの日記 初めてのGoogleAndroidプログラミング

kenzの日記 本が届いたよ

kenzの日記 今日買った本

関連キーワード

[書籍]

コメントを投稿する

名前URI
コメント

トラックバック URL(β)

ThinkPad X201シリーズが発表

2010/3/5 読まれた回数1492
このエントリーを含むはてなブックマーク |  このページを Google Bookmarks に追加 | Yahoo!ブックマークに登録 | このエントリの Delicious history

LenovoからThinkPadX201シリーズが発売された
Core i化でスペックが強化されてます。

X20xシリーズはモバイルPCでは珍しく通常電圧版のCPUを搭載して
国産超軽量モバイルより重めの重量だけど、
メインPCとして使えるくらいパワフルな処理能力を持ってるのが特徴
今回新たに出たX201は
CPUの強化を始めとしたX200シリーズを順当に進化させた物になってる。

全モデルCore i化とそれに伴うメモリーDDR3化、最大8GBに倍増(自力での増設が必要)

加えて、タッチパッドが搭載可能になった。
あとは内蔵カメラが高画素化してたり
キーボードがT410シリーズの様なキーボード間のスペースが詰まったものに変更されている。
T410の変則キーはなくなって従来通りThinkPad7列配列

X201X201iX201sX201Tablet
製品特徴ベーシックモデルX201の低価格CPU搭載モデル低電圧CPUを搭載した軽量モデル指、デジタイザでの操作が可能な
タブレットモデル
CPUCore i5-520M
2.40〜2.93GHz
Core i5-540M
2.53〜3.07GHz
Core i7-620M
2.66〜3.33GHz
Core i3-330M
2.13GHz
Core i5-430M
2.26〜2.4GHz
Core i7-620LM
2.00〜2.80GHz
(Lenovoサイトでは2.66GHzになっているが誤記か?)
Core i7-640LM
2.13〜2.93GHz
Core i7-620LM
2.00〜2.80GHz
Core i7-640LM
2.13〜2.93GHz
稼働時間約3.8h(4セル)
約7.6h(6セル)
約12.8h(9セル)
約4.1h(4セル)
約8.13h(6セル)
約13.6h(9セル)
約3.8h(4セル)
重量約1.34kg(4セル)
約1.47kg(6セル)
約1.63kg(9セル)
約1.1kg(4セル)
約1.23kg(6セル)
約1.39kg(9セル)
約1.67kg(4セル)

価格は相変わらずのThinkPad価格で、発売初日から9万円引きキャンペーンとかカオスな状態になっているので省略
安CPUモデルにわざわざiって文字を追加するあたり、えげつない

X201sはx200sより値段がかなり上がったけれど、その分性能も大幅引き上げされているので
利用用途にあわせて選ぶのが良さそう。

関連キーワード

[Windows][モバイル][IT]

コメントを投稿する

名前URI
コメント

トラックバック URL(β)

RSSで読むRSSフィードを購読

プロフィール

kenz

新しいものが大好き
仕事ではクラウドをプライベートではAndroidアプリを作ってます。
最近、プログラムしている人が減っているのでSmallBasicの紹介記事でプログラム好きな人が増えてくれたら嬉しい

FriendFeed

日記の一覧

follow me

☆最新コメント

MacBookPro 
accelerando hentai torrents:Congratula...

MacBookPro 
naruto no hentai:Could I ha...

MacBookPro 
gender changing hentai manga:What they ...

☆今注目されている日記

kenzの日記
iPhone4 バンパー無償配布は怪我の功名(157pt)

kenzの日記
日産JUKE試乗してきました(107pt)

kenzの日記
iPhone4とXperiaの壁紙(83pt)

kenzの日記
日産JUKEを見てきました(81pt)

kenzの日記
iPhone4用の壁紙を作ってみた(59pt)

オリジナルグッズ

あわせて読みたいブログパーツ