【HSP3】DXライブラリのDxDLL.cs(C#)をHSPのasに変換するアレ(手抜き)Ver.3(2015/08/10)

Codetterからコピペする際、空行にゴミが混入するので、削除してから使ってください。(コンパイルエラーになります)
関数と定数が DxLib.as として出力されます。めっちゃ手抜きです。構造体が戻り値で使用されているものに対応。
出力結果: http://hsp.moe/download/DxLib.as

Codetterからコピペする際、空行にゴミが混入するので、削除してから使ってください。(コンパイルエラーになります)
関数と定数が DxLib.as として出力されます。めっちゃ手抜きです。構造体が戻り値で使用されているものに対応。
出力結果: http://hsp.moe/download/DxLib.as

  • hk1v
  • 2015/8/10 21:54
#module
// 指定オフセットから右から検索していき見つけた位置を返す。(1byteのみ)
#defcfunc searchR1 str _in, int ps, int sh
	idx = -1
	in = _in
	max = strlen(in)
	repeat max, ps
		if peek(in, max-cnt) == sh : idx = max-cnt : break
	loop
return idx
// instr 右から検索版
#defcfunc instrl var s1, str s2
ind = 0
repeat
	res = instr(s1, ind, s2)
	if res == -1 : break
	ind += res + 1
loop
return ind-1
#defcfunc GetMacroName str _tmp, var macro, var const
	sdim tmp, 1024
	tmp = _tmp
	sdim macro, 128
	sdim const, 128
	flag = 0
	if instr(tmp, 0, "public const int ") != -1{
		flag = 1
		sdim res, 128
		split tmp, " ", res
		;markpos = -1
		repeat length(res)
			if res(cnt) == "="{
				tmpcnt = cnt
				// スペースの可能性を考慮して検索(マクロ名を取得)
				repeat tmpcnt
					tmpcnt--
					if res(tmpcnt) != ""{
						macro = res(tmpcnt)
						break
					}
				loop
				// スペースの場合があるので連結処理をする(定数値を取得)
				tmpcnt = cnt + 1	// 足しておく
				sdim tmpconst, 128
				repeat length(res)-tmpcnt, tmpcnt
					tmpconst += res(cnt)+" "
				loop
				// セミコロンを除去
				tmpconst = strtrim(tmpconst, 0, ' ')
				const = strtrim(tmpconst, 0, ';')
						//
			}
		loop
	}
return flag
// 戻り値の型を取得します。とれないときは空。
#defcfunc GetFuncReturn str _lineTmp, str _funcName
	sdim lineTmp, 1024
	lineTmp = _lineTmp
	if instr(lineTmp, 0, "extern") != -1{
		_posFuncName = instr(lineTmp, 0, _funcName)
		if _posFuncName != -1{
			_trimedFuncLine = strmid(lineTmp, 0, _posFuncName)
			strrep _trimedFuncLine, "extern unsafe static ", ""
			strrep _trimedFuncLine, "extern static ", ""
			strrep _trimedFuncLine, "\t", ""
			_trimedFuncLine = strtrim(_trimedFuncLine, 0, ' ')
			return _trimedFuncLine
		}
	}
return ""
#defcfunc GetFuncName str _tmp, var _fnc, array _arg, var _retType
	sdim tmp, 1024
	tmp = _tmp
	sdim _arg, 256 : sdim _fnc, 128
	num = -1
	if instr(tmp, 0, "extern") != -1{
		num = 0
		ks = instr(tmp, 0, "(")
		ke = instrl(tmp, ")")
		if ks != -1 | ke != -1{
			args = strmid(tmp, ks+1, ke-ks-1)
			tmp2 = strmid(tmp, 0, ks)
			tmp2 = strtrim(tmp2, 0, ' ')
			ps = searchR1(tmp2, 0, ' ')
			if ps != -1 {
				// 関数名を取得
				tmp3 = strmid(tmp2, ps, strlen(tmp2))
				_fnc = strtrim(tmp3, 0, ' ')
	
				// 末尾が_x64の場合(対象外として-1を返す)
				if "_x64" == strmid(_fnc, -1, strlen("_x64")){
					return -1
				}
	
				// 末尾が_x86の場合(取り除きます)
				if "_x86" == strmid(_fnc, -1, strlen("_x86")){
					_fnc = strmid(_fnc, 0, strlen(_fnc) - strlen("_x86"))
				}
	
				// 戻り値の型を取得
				_retType = GetFuncReturn(tmp, _fnc)

				// 引き続き引数を取得
				// 引数がないケースを取得
				cargs = args
				cargs = strtrim(cargs, 3, ' ')
				cargs = strtrim(cargs, 3, '\t')
				if cargs == "" : num = 0 : return num
				// 引数ありのケース
				sdim tmp2
				split args, ",", tmp2
				num = stat
				repeat num
					tmp3 = tmp2(cnt)
					tmp3 = strtrim(tmp3, 3, '\t')
					tmp3 = strtrim(tmp3, 0, ' ')
					ps = searchR1(tmp3, 0, ' ')
					if ps != -1{
						tmp4 = strmid(tmp3, 0, ps)
						tmp4 = strtrim(tmp4, 0, ' ')
						_arg(cnt) = tmp4
					}
				loop
			}
		}
	}
return num
#global

	dialog "cs",16
	if stat == 0 : end
	fname = refstr

	notesel buf
	noteload fname

	sdim def, 1024*512
	sdim fncs, 1024*512

	repeat notemax
		noteget tmp, cnt
		if GetMacroName(tmp, macro, const){
			def += "#define global "+ macro +" "+ const +"\n"
		}
		num = GetFuncName(tmp, fnc, arg, ret)
		if num != -1{
			sdim outargs
			repeat num
				// 引数で使われているものだけピックアップしているので構造体は全部ではない。
				if arg(cnt) == "int" || arg(cnt) == "ulong" || arg(cnt) == "uint" || arg(cnt) == "char"{
					outargs += "int"
				}else:if arg(cnt) == "System.Text.StringBuilder" || arg(cnt) == "string"{
					outargs += "str"
				}else:if arg(cnt) == "double"{
					outargs += "double"
				}else:if arg(cnt) == "float"{
					outargs += "float"
				}else:if arg(cnt) == "VECTOR"{
					outargs += "float,float,float"
				}else:if arg(cnt) == "VECTOR_D"{
					outargs += "double,double,double"
				}else:if arg(cnt) == "UV"{
					outargs += "float,float"
				}else:if arg(cnt) == "COLOR_F" || arg(cnt) == "FLOAT4"{
					outargs += "float,float,float,float"
				}else:if arg(cnt) == "COLOR_U8"{
					outargs += "int"
				}else:if arg(cnt) == "IPDATA" || arg(cnt) == "IPDATA_IPv6"{
					outargs += "int"
				}else:if arg(cnt) == "RECT" || arg(cnt) == "INT4"{	// ポインタとかは "RECT *" といった感じに来ます。
					outargs += "int,int,int,int"
				}else:if arg(cnt) == "MATRIX"{
					outargs += "float,float,float,float,float,float,float,float,float,float,float,float,float,float,float,float"
				}else:if arg(cnt) == "MATRIX_D"{
					outargs += "double,double,double,double,double,double,double,double,double,double,double,double,double,double,double,double"
				}else:if arg(cnt) == "MV1_COLL_RESULT_POLY"{
					outargs += "int,float,float,float,int,int,int,float,float,float,float,float,float,float,float,float,float,float,float"
				}else:if arg(cnt) == "MV1_REF_POLYGON"{
					outargs += "int,int,int,int,int,float,float,float,float,float,float"
				}else:if arg(cnt) == "MV1_REF_VERTEX"{
					outargs += "float,float,float,float,float,float"
				}else:if arg(cnt) == "MATERIALPARAM"{
					outargs += "float,float,float,float,float,float,float,float,float,float,float,float,float,float,float,float,float"
				}else:if arg(cnt) == "HITRESULT_LINE"{
					outargs += "int,float,float,float"
				}else:if arg(cnt) == "MV1_COLL_RESULT_POLY_DIM"{
					outargs += "int,int"
				}else:if arg(cnt) == "System.IntPtr"{
					outargs += "sptr"
				}else:if arg(cnt) == "void"{
					outargs += ""
				}else{
					// out~、*は気にしない
					// logmes arg(cnt)
					outargs += "sptr"
				}
				// 最後以外は , をつける
				if cnt != num - 1 : outargs += ","
			loop
	
			// 戻り値の型をチェックします(構造体のもの)
			retTypeStruct = 0
			if ((ret == "COLOR_F") || (ret == "COLOR_U8") || (ret == "DISPLAYMODEDATA") || (ret == "DOUBLE4") || (ret == "FLOAT4") || (ret == "HITRESULT_LINE") || (ret == "MATRIX") || (ret == "MATRIX_D") || 	(ret == "MV1_COLL_RESULT_POLY") ||(ret == "MV1_COLL_RESULT_POLY_DIM") || (ret == "VECTOR") ||(ret == "VECTOR_D")){
				retTypeStruct = 1
		 	}
	
		 	if retTypeStruct == 1{
				fncs += "// 戻り値が構造体です(" + ret +")\n// 第一引数に戻り値を返却します。パラメタは第二引数以降にずれます。\n"
				outargs = "var," + outargs
			}

			// 接頭辞の dx_ を外す(手抜き)
			split fnc, "dx_", fnc2
			fncs += "#func global "+ fnc2(1) +" \""+ fnc +"\" "+outargs+"\n"
		}
	loop

	def2 = {"// VECTOR => float, float, float
#define global ctype VGet(%1,%2,%3) %1, %2, %3
#define global ctype VAdd(%1,%2,%3,%4,%5,%6) %1+%4, %2+%5, %3+%6
#define global ctype VSub(%1,%2,%3,%4,%5,%6) %1-%4, %2-%5, %3-%6
#define global ctype VDot(%1,%2,%3,%4,%5,%6) %1*%4+%2*%5+%3*%6
#define global ctype VCross(%1,%2,%3,%4,%5,%6) %2*%6-%3*%5, %3*%4-%1*%6, %1*%5-%2*%4
#define global ctype VScale(%1,%2,%3,%4) %1*%4, %2*%4, %3*%4
#define global ctype VSquareSize(%1,%2,%3) %1*%1+%2*%2+%3*%3
// 行列だからdimの方が良いのか…(MATRIX 4x4)
#define global ctype VTransform(%1,%2,%3, %4,%5,%6,%7, %8,%9,%10,%11, %12,%13,%14,%15, %16,%17,%18,%19) %1*%4 + %2*%8 + %3*%12 + %16, %1*%5 + %2*%9 + %3*%13 + %17, %1*%6 + %2*%10 + %3*%14 + %18
#define global ctype VTransformSR(%1,%2,%3, %4,%5,%6,%7, %8,%9,%10,%11, %12,%13,%14,%15, %16,%17,%18,%19) %1*%4 + %2*%8 + %3*%12, %1*%5 + %2*%9 + %3*%13, %1*%6 + %2*%10 + %3*%14
// VConvFtoD, VConvDtoF未実装
#define global VGetD VGet
#define global VAddD VAdd
#define global VSubD VSub
#define global VDotD VDot
#define global VCrossD VCross
#define global VScaleD VScale
#define global VSquareSizeD VSquareSize
#define global VTransformD VTransform
#define global VTransformSRD VTransformSR
"}

	sdim outbuf, 1024*5120
	notesel outbuf
	noteadd "// "
	noteadd "// DxLib for HSP " + strf("(%04d/%02d/%02d)", gettime(0), gettime(1), gettime(3))
	noteadd "// http://hsp.moe/"
	noteadd "// https://twitter.com/hk1v"
	noteadd "// by inovia."
	noteadd "// "
	noteadd "// 【本モジュールを利用するにはC#版に付属しているDxLib.dllが必要です】"
	noteadd "// http://homepage2.nifty.com/natupaji/DxLib/dxdload.html"
	noteadd "// "
	noteadd "// ※本モジュールをスムーズに使用するには、構造体に対する理解が必要です。"
	noteadd "// また、C言語で書いてあるソースがそれとなく分かるぐらいの知識が必要です。"
	noteadd "// (世の中にあるDxLibのサンプルコードのほとんどがC/C++/C#なので)"
	noteadd "// HSPの知識だけですと、かなりきついと思います。"
	noteadd "// 推奨レベル:★★★★☆(Lv.4) 当社比...?"
	noteadd "// "
	noteadd "// 【旧バージョンのDxLib.as】"
	noteadd "// http://hsp.moe/download/DxLib_old.as"
	noteadd "// 【TIPS】"
	noteadd "// 構造体が戻り値の場合、HSPがクラッシュする問題(解決方法)"
	noteadd "// http://codetter.com/?p=1192"
	noteadd "// DxLib関連のサンプル(HSP用)"
	noteadd "// http://codetter.com/?extag=dxlib"
	noteadd "// HSPとDxLibで2D描画の基礎ら辺とか(えくー氏)"
	noteadd "// http://fe0km.blog.fc2.com/blog-entry-53.html"
	noteadd "// hspからDXlibの利用方法について"
	noteadd "// http://hsp.tv/play/pforum.php?mode=all&num=70321"
	noteadd "#ifndef __DXLIB__"
	noteadd "#define __DXLIB__"
	noteadd "// 定義ファイルのバージョン(=作成時のDxLibのバージョン+連番4桁数字)"
	noteadd "#define DEFINE_DXLIB_VERSION \"3.14f0000\""
	noteadd "#uselib \"DxLib.dll\""
	noteadd fncs
	noteadd def
	noteadd def2
	noteadd "#endif"
	notesave "DxLib.as"

	end