inp = """ struct ImDrawListSplitter { int _Current; int _Count; ImVector_ImDrawChannel _Channels; }; """ ''' struct ImGuiInputEvent { ImGuiInputEventType Type; ImGuiInputSource Source; union { ImGuiInputEventMousePos MousePos; ImGuiInputEventMouseWheel MouseWheel; ImGuiInputEventMouseButton MouseButton; ImGuiInputEventMouseViewport MouseViewport; ImGuiInputEventKey Key; ImGuiInputEventText Text; ImGuiInputEventAppFocused AppFocused; }; bool AddedByTestEngine; }; ''' def parseFunction(line): line = line.strip(' \n;') line = line.replace(')', '') s = line.split('(') returnType = convertTypeName(s[0].strip(' ')) funcName = convertVarName(s[1].strip('* ')) funcName = funcName.replace('__', '_') argsRaw = s[2].split(',') args = [] for a in argsRaw: if len(a) >= 1: args.append(a) argList = [] for a in args: a = a.strip(' ') tname, vname = splitTypeAndLabel(a) argList.append([convertTypeName(tname), convertVarName(vname)]) return (returnType, funcName, argList) def convertVarName(name): ostr = "" first = True for c in name: if c.isupper(): if first: first = False else: ostr += '_' ostr += c.lower() return ostr def convertTypeName(entry): if 'void*' == entry: return '?*anyopaque' if 'void' == entry: return 'void' isVector = False if entry[:8] == 'ImVector': isVector = True typeName = entry const = False pointer = False if '*' in typeName: pointer = True; typeName = typeName.strip('*') if typeName[:5] == 'const': const = True typeName = typeName[5:] typeName = typeName.strip(' ') if '_' in typeName: x = typeName.split('_') typeName = x[-1] rv = convertInner(typeName) if const: rv = 'const ' + rv if pointer: rv = '[*c]' + rv if isVector: rv += 'Vector' return rv def convertInner(typeName): if 'float' == typeName: return 'f32' if 'char' == typeName: return 'u8' if 'int' == typeName: return 'c_int' if 'short' == typeName: return 'c_short' if 'unsigned int' == typeName: return 'c_uint' if 'unsigned short' == typeName: return 'c_ushort' if 'unsigned long' == typeName: return 'c_ulong' if 'long' == typeName: return 'c_long' if 'longlong' == typeName: return 'c_longlong' if 'ImGui' == typeName[0:5]: return typeName[5:] if 'Im' == typeName[0:2]: return typeName[2:] return typeName def splitTypeAndLabel(line): spaceIndex = line.rindex(' ') left = line[:spaceIndex] right = line[spaceIndex + 1:] return left, right def generateStruct(inp): inp = inp.strip('\n ') defs = [] name = '' nameLine = '' for l in inp.split('\n'): line = l.strip(' {') if len(line) < 1: continue if 'struct' in line: name = line.split(' ')[1] nameLine = line continue if '{' in line: continue if '}' in line: continue if '(*' not in line: typeName, varName = splitTypeAndLabel(line) varName = varName.strip(';') arraySpec = None if '[' in varName: varName, rhs = varName.split('[') arraySpec = rhs.strip(']') varName = convertVarName(varName) if arraySpec is not None: arraySpec = arraySpec.replace('ImGui', '') arraySpec = arraySpec.replace('_', '.') # varName += '[' + arraySpec + ']' typeName = convertTypeName(typeName) defs.append([typeName, varName, arraySpec]) else: returnType, funcName, argList = parseFunction(line) ostr = funcName + ': *const fn (' first = True for arg in argList: if first: first = False else: ostr += ', ' ostr += arg[0] ostr += ') ' + returnType + ',' defs.append([None, None, None, ostr]) print(f'pub const {convertTypeName(name)} = extern struct ' + '{ // ' + nameLine) for d in defs: if d[0] is not None: typedef = d[0] if d[2] is not None: typedef = f"[{d[2]}]" + d[0] print(f" {d[1]}: {typedef},") elif d[3] is not None: print(' ', d[3]) print('};') generateStruct(inp) structs = """ ImDrawCmd {int Size;int Capacity;ImDrawCmd* Data;} ImVector_ImDrawCmd; ImDrawIdx {int Size;int Capacity;ImDrawIdx* Data;} ImVector_ImDrawIdx; """ """ unsigned_char {int Size;int Capacity;unsigned char* Data;} ImVector_unsigned_char; typedef struct ImPool_ImGuiTable {ImVector_ImGuiTable Buf;ImGuiStorage Map;ImPoolIdx FreeIdx;ImPoolIdx AliveCount;} ImPool_ImGuiTable; typedef struct ImPool_ImGuiTabBar {ImVector_ImGuiTabBar Buf;ImGuiStorage Map;ImPoolIdx FreeIdx;ImPoolIdx AliveCount;} ImPool_ImGuiTabBar; typedef struct ImChunkStream_ImGuiWindowSettings {ImVector_char Buf;} ImChunkStream_ImGuiWindowSettings; typedef struct ImChunkStream_ImGuiTableSettings {ImVector_char Buf;} ImChunkStream_ImGuiTableSettings; """ for i in structs.split('\n'): sname = i.split(' ')[0] tname = convertTypeName(sname) # print(sname, tname) o = f""" pub const {tname}Vector = extern struct {{ // struct ImVector_{sname} size: c_int, capacity: c_int, data: [*c]{tname}, }}; """ print(o)