Преглед изворни кода

create_lua_library now generates documentation in XML form

Ivan Safrin пре 13 година
родитељ
комит
dc8204753b

+ 68 - 6
Bindings/Scripts/create_lua_library/create_lua_library.py

@@ -36,11 +36,15 @@ def template_returnPtrLookup(prefix, className, ptr):
 def template_quote(str):
 def template_quote(str):
 	return "\"%s\"" % str;
 	return "\"%s\"" % str;
 
 
+def cleanDocs(docs):
+	return docs.replace("/*", "").replace("*/", "").replace("*", "").replace("\n", "")
+
 # FIXME: Some "unsigned int *" functions are still being generated on the polycode API?
 # FIXME: Some "unsigned int *" functions are still being generated on the polycode API?
 def typeFilter(ty):
 def typeFilter(ty):
 	ty = ty.replace("Polycode::", "")
 	ty = ty.replace("Polycode::", "")
 	ty = ty.replace("std::", "")
 	ty = ty.replace("std::", "")
 	ty = ty.replace("const", "")
 	ty = ty.replace("const", "")
+	ty = ty.replace("inline", "")
 	ty = ty.replace("&", "")
 	ty = ty.replace("&", "")
 	ty = re.sub(r'^.*\sint\s*$', 'int', ty) # eg "unsigned int"
 	ty = re.sub(r'^.*\sint\s*$', 'int', ty) # eg "unsigned int"
 	ty = re.sub(r'^.*\slong\s*$', 'int', ty)
 	ty = re.sub(r'^.*\slong\s*$', 'int', ty)
@@ -57,7 +61,8 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 	wrappersHeaderOut = "" # Def: Global C++ *LUAWrappers.h
 	wrappersHeaderOut = "" # Def: Global C++ *LUAWrappers.h
 	cppRegisterOut = "" # Def: Global C++ *LUA.cpp
 	cppRegisterOut = "" # Def: Global C++ *LUA.cpp
 	cppLoaderOut = "" # Def: Global C++ *LUA.cpp
 	cppLoaderOut = "" # Def: Global C++ *LUA.cpp
-	
+	luaDocOut = ""	
+
 	luaIndexOut = "" # Def: Global Lua everything-gets-required-from-this-file file
 	luaIndexOut = "" # Def: Global Lua everything-gets-required-from-this-file file
 	
 	
 	# Header boilerplate for wrappersHeaderOut and cppRegisterOut
 	# Header boilerplate for wrappersHeaderOut and cppRegisterOut
@@ -80,6 +85,10 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 	wrappersHeaderOut += "#include \"lauxlib.h\"\n"
 	wrappersHeaderOut += "#include \"lauxlib.h\"\n"
 	wrappersHeaderOut += "} // extern \"C\" \n\n"
 	wrappersHeaderOut += "} // extern \"C\" \n\n"
 
 
+	luaDocOut += "<?xml version=\"1.0\" ?>\n"
+	luaDocOut += "<docs>\n"
+
+
 	# Get list of headers to create bindings from
 	# Get list of headers to create bindings from
 	inputPathIsDir = os.path.isdir(inputPath)
 	inputPathIsDir = os.path.isdir(inputPath)
 	if inputPathIsDir:
 	if inputPathIsDir:
@@ -155,11 +164,6 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 				print ">> Parsing class %s" % ckey
 				print ">> Parsing class %s" % ckey
 				c = cppHeader.classes[ckey] # Def: The class structure
 				c = cppHeader.classes[ckey] # Def: The class structure
 
 
-				#if 'doxygen' in c:
-				#	print("DOXYGEN START")
-				#	print(c['doxygen'])
-				#	print("DOXYGEN END")
-
 				luaClassBindingOut = "" # Def: The local lua file to generate for this class.
 				luaClassBindingOut = "" # Def: The local lua file to generate for this class.
 				inherits = False
 				inherits = False
 				parentClass = ""
 				parentClass = ""
@@ -187,6 +191,10 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 					print("Warning: Lua-binding class with less than two methods")
 					print("Warning: Lua-binding class with less than two methods")
 					continue # FIXME: Remove this, move any non-compileable classes into ignore_classes
 					continue # FIXME: Remove this, move any non-compileable classes into ignore_classes
 
 
+				luaDocOut += "\t<class name=\"%s\">\n" % (ckey)
+				if 'doxygen' in c:
+					luaDocOut += "\t\t<desc><![CDATA[%s]]></desc>\n" % (cleanDocs(c['doxygen']))
+
 				parsed_methods = [] # Def: List of discovered methods
 				parsed_methods = [] # Def: List of discovered methods
 				ignore_methods = ["readByte32", "readByte16", "getCustomEntitiesByType", "Core", "Renderer", "Shader", "Texture", "handleEvent", "secondaryHandler", "getSTLString"]
 				ignore_methods = ["readByte32", "readByte16", "getCustomEntitiesByType", "Core", "Renderer", "Shader", "Texture", "handleEvent", "secondaryHandler", "getSTLString"]
 				luaClassBindingOut += "\n\n"
 				luaClassBindingOut += "\n\n"
@@ -210,6 +218,8 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 
 
 				# TODO: Remove or generalize ParticleEmitter special casing. These lines are marked with #SPEC
 				# TODO: Remove or generalize ParticleEmitter special casing. These lines are marked with #SPEC
 
 
+				luaDocOut += "\t\t<members>\n"
+
 				if len(classProperties) > 0: # If there are properties, add index lookup to the metatable
 				if len(classProperties) > 0: # If there are properties, add index lookup to the metatable
 					luaClassBindingOut += "function %s:__getvar(name)\n" % ckey
 					luaClassBindingOut += "function %s:__getvar(name)\n" % ckey
 					# Iterate over property structures, creating if/else clauses for each.
 					# Iterate over property structures, creating if/else clauses for each.
@@ -238,6 +248,13 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 							luaClassBindingOut += "\t\tlocal retVal = %s.%s_get_%s(self.__ptr)\n" % (libName, ckey, pp["name"])
 							luaClassBindingOut += "\t\tlocal retVal = %s.%s_get_%s(self.__ptr)\n" % (libName, ckey, pp["name"])
 							luaClassBindingOut += template_returnPtrLookup("\t\t", template_quote(pp["type"]), "retVal")
 							luaClassBindingOut += template_returnPtrLookup("\t\t", template_quote(pp["type"]), "retVal")
 
 
+						
+						luaDocOut += "\t\t\t<member name=\"%s\" type=\"%s\">\n" % (pp["name"],  typeFilter(pp["type"]))
+						if 'doxygen' in pp:
+							luaDocOut += "\t\t\t\t<desc><![CDATA[%s]]></desc>\n" % (cleanDocs(pp['doxygen']))
+						
+						luaDocOut += "\t\t\t</member>\n"
+
 						# Generate C++ side of binding:
 						# Generate C++ side of binding:
 						if not ((ckey == "ScreenParticleEmitter" or ckey == "SceneParticleEmitter") and pp["name"] == "emitter"): #SPEC
 						if not ((ckey == "ScreenParticleEmitter" or ckey == "SceneParticleEmitter") and pp["name"] == "emitter"): #SPEC
 							cppRegisterOut += "\t\t{\"%s_get_%s\", %s_%s_get_%s},\n" % (ckey, pp["name"], libName, ckey, pp["name"])
 							cppRegisterOut += "\t\t{\"%s_get_%s\", %s_%s_get_%s},\n" % (ckey, pp["name"], libName, ckey, pp["name"])
@@ -275,6 +292,8 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 						luaClassBindingOut += "\tend\n"
 						luaClassBindingOut += "\tend\n"
 					luaClassBindingOut += "end\n"
 					luaClassBindingOut += "end\n"
 
 
+				luaDocOut += "\t\t</members>\n"
+
 				luaClassBindingOut += "\n\n"
 				luaClassBindingOut += "\n\n"
 				
 				
 				# Iterate over properties again, creating setters
 				# Iterate over properties again, creating setters
@@ -330,6 +349,9 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 
 
 				# Iterate over methods
 				# Iterate over methods
 				luaClassBindingOut += "\n\n"
 				luaClassBindingOut += "\n\n"
+				
+				luaDocOut += "\t\t<methods>\n"
+
 				for pm in c["methods"]["public"]:
 				for pm in c["methods"]["public"]:
 					# Skip argument-overloaded methods and operators.
 					# Skip argument-overloaded methods and operators.
 					# TODO: Instead of skipping arguemnt overloads, have special behavior.
 					# TODO: Instead of skipping arguemnt overloads, have special behavior.
@@ -342,6 +364,35 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 					if pm["name"] == "~"+ckey:
 					if pm["name"] == "~"+ckey:
 						continue
 						continue
 					
 					
+					luaDocOut += "\t\t\t<method name=\"%s\" return_type=\"%s\">\n" % (pm["name"],  typeFilter(pm["rtnType"].replace("*", "")))
+					docs = None
+					if 'doxygen' in pm:
+						docs = cleanDocs(pm['doxygen']).split("@return")[0].split("@param")
+						luaDocOut += "\t\t\t\t<desc><![CDATA[%s]]></desc>\n" % (docs[0])
+						
+					if len(pm["parameters"]) > 0:
+						luaDocOut += "\t\t\t\t<params>\n"
+						
+						paramIndex = 0
+						for param in pm["parameters"]:
+							if "name" in param:
+								if not param.has_key("type"):
+									continue
+								if param["type"] == "0":
+									continue
+								luaDocOut += "\t\t\t\t\t<param name=\"%s\" type=\"%s\">\n" % (param["name"], typeFilter(param["type"]).replace("*",""))
+								if docs != None:
+									if len(docs) > paramIndex+1:
+										cdoc = docs[paramIndex+1].split()
+										cdoc.pop(0)
+										luaDocOut += "\t\t\t\t\t\t<desc><![CDATA[%s]]></desc>\n" % (" ".join(cdoc))
+								luaDocOut += "\t\t\t\t\t</param>\n"
+								paramIndex = paramIndex + 1
+						luaDocOut += "\t\t\t\t</params>\n"
+								
+						
+					luaDocOut += "\t\t\t</method>\n"
+
 					basicType = False
 					basicType = False
 					voidRet = False
 					voidRet = False
 					vectorReturn = False
 					vectorReturn = False
@@ -596,6 +647,8 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 
 
 					parsed_methods.append(pm["name"]) # Method parse success
 					parsed_methods.append(pm["name"]) # Method parse success
 
 
+				luaDocOut += "\t\t</methods>\n"
+
 				# With methods out of the way, do some final cleanup:
 				# With methods out of the way, do some final cleanup:
 				
 				
 				# user pointer metatable creation in C++
 				# user pointer metatable creation in C++
@@ -640,10 +693,15 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 				mkdir_p(apiClassPath)
 				mkdir_p(apiClassPath)
 				fout = open("%s/%s.lua" % (apiClassPath, ckey), "w")
 				fout = open("%s/%s.lua" % (apiClassPath, ckey), "w")
 				fout.write(luaClassBindingOut)
 				fout.write(luaClassBindingOut)
+
+				luaDocOut += "\t</class>\n"
+	
 		except CppHeaderParser.CppParseError,  e: # One input file parse; failed.
 		except CppHeaderParser.CppParseError,  e: # One input file parse; failed.
 			print e
 			print e
 			sys.exit(1)
 			sys.exit(1)
 
 
+	luaDocOut += "</docs>\n"
+
 	# Footer boilerplate for wrappersHeaderOut and cppRegisterOut.
 	# Footer boilerplate for wrappersHeaderOut and cppRegisterOut.
 	wrappersHeaderOut += "} // namespace Polycode\n"
 	wrappersHeaderOut += "} // namespace Polycode\n"
 	
 	
@@ -674,6 +732,10 @@ def createLUABindings(inputPath, prefix, mainInclude, libSmallName, libName, api
 	fout = open("%s/%sLUA.h" % (includePath, prefix), "w")
 	fout = open("%s/%sLUA.h" % (includePath, prefix), "w")
 	fout.write(cppRegisterHeaderOut)
 	fout.write(cppRegisterHeaderOut)
 
 
+	luaDocPath = "../../../Documentation/Lua/xml"
+	fout = open("%s/%s.xml" % (luaDocPath, prefix), "w")
+	fout.write(luaDocOut)
+
 	fout = open("%s/%s.lua" % (apiPath, prefix), "w")
 	fout = open("%s/%s.lua" % (apiPath, prefix), "w")
 	fout.write(luaIndexOut)
 	fout.write(luaIndexOut)
 	
 	

+ 1 - 0
Documentation/Lua/xml/.gitignore

@@ -0,0 +1 @@
+!.gitignore