<   2009年 07月 ( 6 )   > この月の画像一覧
保存と復帰
 自分で作ったテーブル周りのサンプルを使ってて、バグに気がつきました。テーブルにboolean型の値が格納されている場合にエラーが出ることと、格納されてる値の型情報が失われていることです。前者はすぐに対応できるんですよ。テーブルを文字列化する際にちゃんとtostring()してやればいいだけなので。問題は後者です。たとえばboolean型が複数個格納されているテーブルをCSVで保存し、復帰させたあと、復帰前のテーブルと復帰後のテーブルで値を逐一比較した場合、全部不一致になってしまうわけです。true == "true"はtrueになりませんからね。なので、何とかして型情報を正しく保存する必要があります。
 ひとつ思いついたのは、保存する時に格納する値の前にカッコで型情報を記述し、復帰させる時にstring.gmatch()で型情報を取り出す方法。たとえば{1,"2",true}というテーブルがあれば、それぞれを"(number)1","(string)2","(boolean)true"と変換するのです。これならいけそうですね。

 あと、自作サンプルではテーブル内にテーブルが含まれている場合もエラーが出ます。これも何とかしたいですね。
[PR]
by lyricist_m | 2009-07-23 18:39 | NSLua
アニメーション応用
 アニメーションコールバック(NSCALL_animation)を使用したサンプル(アニメーション応用)をDelusionist's Utopiaにアップしました。

 このスクリプトの特徴は、テーブルを使用することによって、一度の割り込みで複数の処理ができる点です。だいたいの流れは、まずテーブルに関数を登録し、割り込み時にテーブルを巡回して関数を呼び出し、処理を止める場合はテーブルから関数を削除する、という形になります。関数は呼び出される際にNSTiimerで取得した現在時間を渡されるので、それに応じた処理を行なうことにより、コールバックのインターバルに左右されない処理が可能です。逆に言えば、関数を記述する際はインターバルに左右されないように気をつける必要があります。できればインターバルを自動で調整(処理に時間がかかる場合は長めに、早く終わる場合は短めに)してくれるようにしたかったのですが、ちょっと微妙だったので今回は省きました。いい具合にスクリプトを組めたら更新しようと思います。
 で、コールバックで呼び出す関数のサンプルを3つ用意しました。時計を表示するclock命令と00からカウントアップしていくタイマーを表示するtimer命令、そしてマウスカーソルを徐々に移動させるmovemousecursor2命令の3つです。もっと数を増やしたかったのですが、時間に関する処理で思いついたのがこれくらいだったので……。まあ、複雑なことはしていないし、自分にしてはコメントをつけた方なので、そこそこ解りやすいかと思います。



 今回のスクリプトを組んでいて「複数のスプライトの移動を管理できる機構が欲しいなぁ」と思いました。吉里吉里のDefaultMover.tjsあたりを参考にして、書いてみようと思います。目標としては、あらかじめ読み込んでおいたスプライトの番号と移動方法、処理にかける時間なんかをLuaに渡すことで動かしてくれるような感じにしようかと。移動方法はせっかくスプライン補間があるから、それも使ってみたいですね。
[PR]
by lyricist_m | 2009-07-22 21:57 | NSLua
新ボタン命令によるシステムカスタマイズのサンプル
 新ボタン命令(bexecなど)を使用したシステムカスタマイズのサンプルスクリプトをDelusionist's UtopiaのNScripterページにアップしました。
 Luaを使用しない純正NScripter仕上げです。新ボタン命令の使い方や注意点、問題点などを知ってもらうために作成したので、なるべく難しいことはしないように注意してスクリプトを書きました。今回はtextgosubのみですが、今後は→ックリックメニューや回想、セーブ・ロード画面などもbexecでカスタマイズしていく予定です。



 Luaを使用したシステムカスタマイズに関しても興味があるのですが、現在むいむい。さんが頑張ってらっしゃるようなので、Luaに関して自分はひとまず別方向に進もうかと思ってます。
 今考えているのは、
・アニメーション割り込み(NSCALL_animation)を応用した、画像描画以外の何か
・Luaを使ってキーコンフィグ
 といった内容です。
[PR]
by lyricist_m | 2009-07-16 04:39 | NScripter
ローカル宣言を行なう場所に対しての注意
local a = "test"

luasub("test")
function NSCOM_test ()
NSExec('caption "'..a..'"')
end

--local a = "test"


 上記Luaスクリプトにおいて、上のlocal aをコメントアウトして、反対に下にあるlocal aのコメントアウトを外すと、エラーになります。どうやら、関数宣言より下にあるローカル宣言は、関数内からは見えないようで。test命令が呼び出されるのはNScripter側、つまりLuaスクリプトを全て読み込んだ後なので、ちゃんと変数aに値がセットされるものだと思ったのですが。ちなみに上記Luaスクリプトからlocalを外して通常の代入文にした場合は、上でも下でも普通に動きます。うーん、これってLuaリファレンス読めば書いてあるんだろうか。
 スクリプト中でローカル宣言をベタ書きする(関数外に書く)場合は、順番に注意が必要ですね。とりあえず、ローカル宣言はファイルの先頭にまとめて書いてしまった方がいいと思います。
[PR]
by lyricist_m | 2009-07-15 23:50 | NSLua
bexecをキーアップに対応させる
 bexec命令は、マウスに関しては「ボタンが離された瞬間」に処理が返ってくるのですが、キーボードに関しては「キーが押された瞬間」に処理が返ってきます。この点が旧ボタン命令と異なるので、単に命令を置き換えるだけでは誤動作する場合が多々あります。なので、旧ボタン命令と同じ感覚で使えるように、bexec命令を用いた自作命令bexec2を作成し、「キーが離された瞬間」に処理が返ってくるようにしてみました。以下、スクリプト。

*bexec2
getparam s%0

bexec $%0
;if $%0 == "CTRL" return
mov $1,$%0
len %1,$1
if 1 < %1 && %1 < 5 && "S" < $1 && $1 < "T" mov $1,"LCLICK"
if $1 != "LCLICK" jumpf
checkkey %1,"SPACE":if %1 == 1 mov $1,"SPACE":jumpf
checkkey %1,"RETURN":if %1 == 1 mov $1,"RETURN":jumpf

~
checkkey %1,$1
if %1 == 0 return
wait 10
jumpb
return


 bexec2命令はbexec命令と同様、押されたボタンを文字列として返します。スプライトボタンの場合はS+スプライト番号という形式ですね。この命令を使えば、キーダウン時ではなくキーアップ時に処理が返ってきます。また、bcursor命令を指定していない場合でもスペースキーとリターンキーが正常に動作するように、bexec命令でLCLICKが返ってきたらcheckkey命令で実際に押されたキーは何なのかを判別しています。あと、bexec命令の下のコメントアウトを外すと、コントロールキーの場合のみキーダウン時に返ってくるようになるので、クリック待ち時のコントロールスキップも可能になります。



 話変わって。
 現在、bexec命令を用いたシステムカスタマイズ用サンプルスクリプトを作成中です。一応、nsluaサンプルスクリプト内のシステムカスタマイズサンプルでbexecが使われているのですが、Luaが使われているので、単純にbexec命令の使い方を知りたい人は手が出しづらいんじゃないかと思いまして。「俺はLuaなんて使わないぞ!」なんて方もいるでしょうからね。
 とりあえずクリック待ちの部分はできたので、あとはちょこちょこ調整してから公開しようと思います。右クリックメニューとかセーブロード画面などその他諸々は、公開してから追加していく形で。
[PR]
by lyricist_m | 2009-07-07 18:31 | NScripter
bcursor命令について
[2009年7月5日修正、追記]
 更新.txtには「カーソルキー入力を得たい場合はbclearとbexecの間にbcursor命令を入れてください。」と書いてありますが、エンターキーとスペースキーの入力を得たい場合もbcursor命令を使用する必要があります。
 以下、検証用スクリプト。

*define
game

*start
;bcursor
bexec $0
caption $0
goto *start


 押されたキーをタイトルバーに表示するだけのスクリプトです。bcursor命令をコメントアウトしていない場合とした場合で、カーソルキー・エンターキー・スペースキーに対する挙動が変化することを確認できるはずです。bcursor命令を使用しない場合、カーソルキーに対しての反応は無く、エンターキーとスペースキーに対してはLCLICKが返りますカーソルキーはスプライトボタンの選択に用いられ、エンタキー・スペースキーは左クリックと同様の動作をします(ただしbexecから処理が返ってくるのはキーアップ時ではなくキーダウン時)。使用した場合はカーソルキーはUP・DOWN・RIGHT・LEFT、エンターキー=RETURN、スペースキー=SPACEとなります。

[追記]
 きなこさんからのコメントを受けて、スプライトボタンに関して調べていなかったことに気がついたので、ちょっと試してみました。

*define
game

*start
bclear
lsp 1,":s#FFFFFF#FF0000あいうえお",0,0
print 1
bsp 1
;btrans

*loop
bexec $0,%0
if %0 > 0 inc %1:itoa $1,%1:caption "sp"+$1:goto *start
goto *loop


 上記スクリプトは、スプライトボタンを1個設置し、それがクリックされるとspX(Xにはボタンがクリックされた回数が入る)という文字列をタイトルバーに表示するものです。このスクリプトにおいて、スプライトボタンに対して左クリックをした場合とカーソルで選択→エンターキーないしスペースキーで決定した場合では、明らかに動作が異なります。
 具体的には、左クリックの場合はマウスの左ボタンがアップされた後でbexecから処理が返ってくるのに対し、エンターキー・スペースキーの場合はキーがダウンされてすぐに処理が返るという違いがあります。なので、後者ではキーを押している間中数字が増え続けることになります。
 もしbcursor命令を使用しない場合は「戻り値がLCLICKでもマウスからの入力とキーボードからの入力の2通りの場合があり、動作が異なる」ことを覚えておかなければなりませんね。

 余談ですが。
 上記スクリプトでbtrans命令のコメントアウトを外すと、カーソルキーでボタンを選択しようとしても透過部分にカーソルがあってしまい、エンターキーを押しても決定できません。
 まあ、bexecで選択肢命令を自作する(=文字列をスプライトボタン化する)場合はbtransを使用しないでしょうし、真ん中が透過されているボタンというのも想像できないので、実害はないでしょう。
[PR]
by lyricist_m | 2009-07-05 16:49 | NScripter