⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 function.lua

📁 脚本编程语言
💻 LUA
字号:
-- tolua: function class-- Written by Waldemar Celes-- TeCGraf/PUC-Rio-- Jul 1998-- $Id: $-- This code is free software; you can redistribute it and/or modify it.-- The software provided hereunder is on an "as is" basis, and-- the author has no obligation to provide maintenance, support, updates,-- enhancements, or modifications. -- Function class-- Represents a function or a class method.-- The following fields are stored:--  mod  = type modifiers--  type = type--  ptr  = "*" or "&", if representing a pointer or a reference--  name = name--  lname = lua name--  args  = list of argument declarations--  const = if it is a method receiving a const "this".classFunction = { mod = '', type = '', ptr = '', name = '', args = {n=0}, const = '',}classFunction.__index = classFunctionsetmetatable(classFunction,classFeature)-- declare tagsfunction classFunction:decltype () self.type = typevar(self.type) if strfind(self.mod,'const') then	 self.type = 'const '..self.type		self.mod = gsub(self.mod,'const%s*','')	end local i=1 while self.args[i] do  self.args[i]:decltype()  i = i+1 endend-- Write binding function-- Outputs C/C++ binding function.function classFunction:supcode () local overload = strsub(self.cname,-2,-1) - 1  -- indicate overloaded func local nret = 0      -- number of returned values local class = self:inclass() local _,_,static = strfind(self.mod,'^%s*(static)') if class then  output("/* method:",self.name," of class ",class," */") else  output("/* function:",self.name," */") end output("static int",self.cname,"(lua_State* tolua_S)") output("{") -- check types	if overload < 0 then	 output('#ifndef TOLUA_RELEASE\n')	end	output(' tolua_Error tolua_err;') output(' if (\n') -- check self local narg if class then narg=2 else narg=1 end if class then	 local func = 'tolua_isusertype'		local type = self.parent.type	 if self.name=='new' or static~=nil then		 func = 'tolua_isusertable'			type = self.parent.type		end		output('     !'..func..'(tolua_S,1,"'..type..'",0,&tolua_err) ||\n')  end -- check args if self.args[1].type ~= 'void' then  local i=1  while self.args[i] do   if isbasic(self.args[i].type) ~= 'value' then    output('     !'..self.args[i]:outchecktype(narg)..' ||\n')   end   narg = narg+1   i = i+1  end end -- check end of list  output('     !tolua_isnoobj(tolua_S,'..narg..',&tolua_err)\n )')	output('  goto tolua_lerror;') output(' else\n')	if overload < 0 then	 output('#endif\n')	end	output(' {')  -- declare self, if the case local narg if class then narg=2 else narg=1 end if class and self.name~='new' and static==nil then  output(' ',self.const,self.parent.type,'*','self = ')  output('(',self.const,self.parent.type,'*) ')  output('tolua_tousertype(tolua_S,1,0);') elseif static then  _,_,self.mod = strfind(self.mod,'^%s*static%s%s*(.*)') end -- declare parameters if self.args[1].type ~= 'void' then  local i=1  while self.args[i] do   self.args[i]:declare(narg)   narg = narg+1   i = i+1  end end -- check self if class and self.name~='new' and static==nil then 	 output('#ifndef TOLUA_RELEASE\n')  output('  if (!self) tolua_error(tolua_S,"invalid \'self\' in function \''..self.name..'\'",NULL);');	 output('#endif\n') end -- get array element values if class then narg=2 else narg=1 end if self.args[1].type ~= 'void' then  local i=1  while self.args[i] do   self.args[i]:getarray(narg)   narg = narg+1   i = i+1  end end -- call function if class and self.name=='delete' then  output('  delete self;') elseif class and self.name == 'operator&[]' then  output('  self->operator[](',self.args[1].name,'-1) = ',self.args[2].name,';') else  output('  {')  if self.type ~= '' and self.type ~= 'void' then   output('  ',self.mod,self.type,self.ptr,'tolua_ret = ')   output('(',self.mod,self.type,self.ptr,') ')  else   output('  ')  end  if class and self.name=='new' then   output('new',self.type,'(')  elseif class and static then   output(class..'::'..self.name,'(')  elseif class then   output('self->'..self.name,'(')  else   output(self.name,'(')  end  -- write parameters  local i=1  while self.args[i] do   self.args[i]:passpar()   i = i+1   if self.args[i] then    output(',')   end  end       if class and self.name == 'operator[]' then   output('-1);')		else   output(');')		end  -- return values  if self.type ~= '' and self.type ~= 'void' then   nret = nret + 1   local t,ct = isbasic(self.type)   if t then    output('   tolua_push'..t..'(tolua_S,(',ct,')tolua_ret);')   else			 t = self.type    if self.ptr == '' then     output('   {')     output('#ifdef __cplusplus\n')     output('    void* tolua_obj = new',t,'(tolua_ret);')      output('    tolua_pushusertype(tolua_S,tolua_clone(tolua_S,tolua_obj,tolua_collect_'.._collect[t]..'),"',t,'");')     output('#else\n')     output('    void* tolua_obj = tolua_copy(tolua_S,(void*)&tolua_ret,sizeof(',t,'));')     output('    tolua_pushusertype(tolua_S,tolua_clone(tolua_S,tolua_obj,tolua_collect),"',t,'");')     output('#endif\n')     output('   }')    elseif self.ptr == '&' then     output('   tolua_pushusertype(tolua_S,(void*)&tolua_ret,"',t,'");')    else     output('   tolua_pushusertype(tolua_S,(void*)tolua_ret,"',t,'");')    end   end  end  local i=1  while self.args[i] do   nret = nret + self.args[i]:retvalue()   i = i+1  end  output('  }')  -- set array element values  if class then narg=2 else narg=1 end  if self.args[1].type ~= 'void' then   local i=1   while self.args[i] do    self.args[i]:setarray(narg)    narg = narg+1    i = i+1   end  end   -- free dynamically allocated array  if self.args[1].type ~= 'void' then   local i=1   while self.args[i] do    self.args[i]:freearray()    i = i+1   end  end end output(' }') output(' return '..nret..';') -- call overloaded function or generate error	if overload < 0 then	 output('#ifndef TOLUA_RELEASE\n')  output('tolua_lerror:\n')  output(' tolua_error(tolua_S,"#ferror in function \''..self.lname..'\'.",&tolua_err);')  output(' return 0;')  output('#endif\n')	else  output('tolua_lerror:\n')  output(' return '..strsub(self.cname,1,-3)..format("%02d",overload)..'(tolua_S);') end output('}') output('\n')end-- register functionfunction classFunction:register () output(' tolua_function(tolua_S,"'..self.lname..'",'..self.cname..');')end-- Print methodfunction classFunction:print (ident,close) print(ident.."Function{") print(ident.." mod  = '"..self.mod.."',") print(ident.." type = '"..self.type.."',") print(ident.." ptr  = '"..self.ptr.."',") print(ident.." name = '"..self.name.."',") print(ident.." lname = '"..self.lname.."',") print(ident.." const = '"..self.const.."',") print(ident.." cname = '"..self.cname.."',") print(ident.." lname = '"..self.lname.."',") print(ident.." args = {") local i=1 while self.args[i] do  self.args[i]:print(ident.."  ",",")  i = i+1 end print(ident.." }") print(ident.."}"..close)end-- check if it returns a object by valuefunction classFunction:requirecollection (t)	local r = false	if self.type ~= '' and not isbasic(self.type) and self.ptr=='' then	 t[self.type] = gsub(self.type,"::","_")	 r = true	end	local i=1	while self.args[i] do		r = self.args[i]:requirecollection(t) or r		i = i+1	end	return rend-- determine lua function name overloadfunction classFunction:overload () return self.parent:overload(self.lname)end-- Internal constructorfunction _Function (t) setmetatable(t,classFunction) if t.const ~= 'const' and t.const ~= '' then  error("#invalid 'const' specification") end append(t) if t:inclass() then  if t.name == t.parent.name then   t.name = 'new'   t.lname = 'new'   t.type = t.parent.name   t.ptr = '*'  elseif t.name == '~'..t.parent.name then   t.name = 'delete'   t.lname = 'delete'  end end t.cname = t:cfuncname("tolua")..t:overload(t) return tend-- Constructor-- Expects three strings: one representing the function declaration,-- another representing the argument list, and the third representing-- the "const" or empty string.function Function (d,a,c) local t = split(strsub(a,2,-2),',') -- eliminate braces local i=1 local l = {n=0} while t[i] do  l.n = l.n+1  l[l.n] = Declaration(t[i],'var')  i = i+1 end local f = Declaration(d,'func') f.args = l f.const = c return _Function(f)end

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -