LuaInterfaceその2
ヘルプ作成
前回アトリビュートにデスクリプションを記述したものを取得し、ファンクションの説明を出力できるようにしてみます。
/// <summary> /// Lua登録ファンクションのデスクリプション作成 /// </summary> class LuaFuncDescriptor { /// <summary> /// /// </summary> /// <param name="funcName">ファンクション名</param> /// <param name="funcDoc">ファンクションに対するドキュメント</param> /// <param name="_params">型とパラメータ名のペアのリスト</param> public LuaFuncDescriptor( String funcName, String funcDoc, List<Pair<String, String>> _params) { m_FunctionName = funcName; m_FunctionDoc = funcDoc; m_FunctionParameters = _params; String funcHeader = funcName + "(%params%) - " + funcDoc; String funcBody = "\n\n"; String funcParams = ""; Boolean bFirst = true; for( int i = 0; i < _params.Count; i++ ) { if( !bFirst ) funcParams += ", "; funcParams += _params[ i ].First; funcBody += "\t" + _params[ i ].First + "\t\t" + _params[ i ].Second + "\n"; bFirst = false; } funcBody = funcBody.Substring( 0, funcBody.Length - 1 ); if( bFirst ) funcBody = funcBody.Substring( 0, funcBody.Length - 1 ); m_FunctionDocString = funcHeader.Replace( "%params%", funcParams ) + funcBody; // Console.WriteLine( m_FunctionDocString ); } public String FuncName { get { return this.m_FunctionName; } } public String FuncDoc { get { return this.m_FunctionDoc; } } public List<Pair<String, String>> FuncParams { get { return this.m_FunctionParameters; } } public String FuncHeader( ) { if( m_FunctionDocString.IndexOf( "\n" ) == -1 ) return m_FunctionDocString; return m_FunctionDocString.Substring( 0, m_FunctionDocString.IndexOf( "\n" ) ); } private String m_FunctionName; private String m_FunctionDoc; private List<Pair<String, String>> m_FunctionParameters = null; private String m_FunctionDocString; }
/// <summary> /// 一般的なペア /// </summary> /// <typeparam name="F"></typeparam> /// <typeparam name="S"></typeparam> class Pair<F, S> { public F First { get; set; } public S Second{ get; set; } public Pair( F first, S second ) { First = first; Second = second; } }
これでファンクションについてのデスクリプションがつくられました。これを前回のLuaObjectクラスに組み込み、
using YS = Yanesdk.Script; class LuaObject : YS.Lua { public LuaObject( ) { m_LuaFuncs = new Hashtable( ); } /// <summary> /// オブジェクト内に存在するファンクションアトリビュートを登録 /// </summary> /// <param name="target"></param> public void RegisterObjectFunctions( Object target ) { Type targetType = target.GetType( ); foreach( MethodInfo mInfo in targetType.GetMethods( ) ) { foreach( Attribute attr in Attribute.GetCustomAttributes( mInfo ) ) { if( attr.GetType( ) == typeof( AttrLuaFunc ) ) { AttrLuaFunc attrFunc = ( AttrLuaFunc )attr; List<Pair<String, String>> _params = new List<Pair<String, String>>( ); String funcName = attrFunc.FuncName; String funcDoc = attrFunc.FuncDoc; String[ ] paramDocs = attrFunc.FuncParams; ParameterInfo[ ] prmInfo = mInfo.GetParameters( ); if( paramDocs != null && ( prmInfo.Length != paramDocs.Length ) ) { Console.WriteLine( "Function " + mInfo.Name + " (exported as " + funcName + ") argument number mismatch. Declared " + paramDocs.Length + " but requires " + prmInfo.Length + "." ); break; } for( int i = 0; i < prmInfo.Length; i++ ) { _params.Add( new Pair<String, String>(prmInfo[ i ].ParameterType.ToString(), paramDocs[ i ] )); } LuaFuncDescriptor desc = new LuaFuncDescriptor( funcName, funcDoc, _params ); m_LuaFuncs.Add( funcName, desc ); RegisterFunction( funcName, target, mInfo ); } } } } private Hashtable m_LuaFuncs = null; }
これをあとはLua側から呼べるようにしたり、外部に出力なりすればよろしいのかな。