# HG changeset patch # User etisserant # Date 1187709686 -7200 # Node ID a1f9e514f708f285f925001e7fd330cec58a5e99 # Parent 75ae893d5eedd7835a008d8ed5ea9b3fcda6b464 plugin framework organization being defined diff -r 75ae893d5eed -r a1f9e514f708 .cvsignore --- a/.cvsignore Mon Aug 20 14:28:08 2007 +0200 +++ b/.cvsignore Tue Aug 21 17:21:26 2007 +0200 @@ -1,1 +1,4 @@ *.pyc +.settings +.pydevproject +.project diff -r 75ae893d5eed -r a1f9e514f708 Beremiz.py --- a/Beremiz.py Mon Aug 20 14:28:08 2007 +0200 +++ b/Beremiz.py Tue Aug 21 17:21:26 2007 +0200 @@ -31,13 +31,14 @@ base_folder = os.path.split(sys.path[0])[0] sys.path.append(os.path.join(base_folder, "plcopeneditor")) sys.path.append(os.path.join(base_folder, "CanFestival-3", "objdictgen")) +sys.path.append(os.path.join(base_folder, "wxsvg", "svgui", "defeditor")) iec2cc_path = os.path.join(base_folder, "matiec", "iec2cc") ieclib_path = os.path.join(base_folder, "matiec", "lib") from PLCOpenEditor import PLCOpenEditor, ProjectDialog from TextViewer import TextViewer -from plcopen.structures import IEC_KEYWORDS, AddPlugin +from plcopen.structures import IEC_KEYWORDS#, AddPlugin from PLCControler import PLCControler import plugins @@ -333,12 +334,8 @@ for name in plugins.__all__: module = getattr(plugins, name) - if len(module.BlockList) > 0: - function = module.GetBlockGenerationFunction(self) - blocklist = module.BlockList - for blocktype in blocklist["list"]: - blocktype["generate"] = function - AddPlugin(module.BlockList) + + #AddPlugin(module.GetBlockGenerationFunction(self)) self.CurrentProjectPath = "" @@ -664,15 +661,15 @@ ready = select.select([outfd,errfd],[],[]) # wait for input if outfd in ready[0]: outchunk = outfile.readline() - if outchunk == '': outeof = 1 + if outchunk == '': outeof = 1 + else : outlen += 1 outdata += outchunk - outlen += 1 self.Log.write(outchunk) if errfd in ready[0]: errchunk = errfile.readline() - if errchunk == '': erreof = 1 + if errchunk == '': erreof = 1 + else : errlen += 1 errdata += errchunk - errlen += 1 self.Log.write_warning(errchunk) if outeof and erreof : break if errlen > sz_limit or outlen > sz_limit : @@ -705,6 +702,9 @@ ST_viewer.SetText(file(plc_file).read()) new_dialog.Show() raise Exception, "Error : IEC to C compiler returned %d"%status + C_files = result.splitlines() + C_files.remove("POUS.c") + C_files = map(lambda filename:os.path.join(self.TargetDir, filename), C_files) self.Log.write("Extracting Located Variables...\n") location_file = open(os.path.join(self.TargetDir,"LOCATED_VARIABLES.h")) locations = [] @@ -715,12 +715,15 @@ locations.append(result.groups()) self.Log.write("Generating Network Configurations...\n") for bus_id, bus_infos in self.BusManagers.items(): - if bus_infos["Manager"]: - filepath = "%s.c"%os.path.join(self.TargetDir, gen_cfile.FormatName(bus_infos["Name"])) - result = bus_infos["Manager"].GenerateBus(filepath, bus_id, locations) + if bus_infos["Manager"]: + c_filename = "%s.c"%os.path.join(self.TargetDir, gen_cfile.FormatName(bus_infos["Name"])) + result = bus_infos["Manager"].GenerateBus(c_filename, locations) if result: - raise Exception, "Bus with id \"0x%2.2X\" can't be generated!"%bus_id + raise Exception + else: + C_files.append(c_filename) self.Log.write("Generating Makefiles...\n") + self.Log.write(str(C_files)) self.Log.write("Compiling Project...\n") diff -r 75ae893d5eed -r a1f9e514f708 plugins/README.plugins --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/plugins/README.plugins Tue Aug 21 17:21:26 2007 +0200 @@ -0,0 +1,28 @@ + BlockTypesFactory(beremiz_inst) + return list similar to plcopeneditor/plcopen/structure.py BlockTypes + [ST_LibraryFactory(beremiz_inst)] + + [C_Library -- "C Code"] + Build -- {"CC":"gcc" , "C_FLAGS" : "..." , "LD_FLAGS" : "..." , ... ,} + Plugin_Params_XSD -- Defini les paramertres optionels du plugin + Plugin_Controller_Factory -- Sert a instancier chaque controler de bus + + GenerateC(bus_controler_list) -> C_file + [canfestival : InitNodes(){0_post_init(); 1_post_init();}] + plugname_pre_init(){...} + plugname_post_init(){[canfestival : StarTimerLoop(&InitNodes)]} + + Save/Load XML + Bus_Params_XSD -- Defini les paramertres optionels du bus + Bus_Controller_Factory -- Sert a instancier chaque controler de bus + () -> controller + + GenerateC -> C_file + /*declarations*/ + ... + busnb_pre_init(){...} + busnb_init(){...} + busnb_post_init(){...} + busnb_IN(){...} + busnb_OUT(){...} + + Save/Load XML + + Save/Load model + [Bus_View_Factory -- ] + MasterCapable -- Bool, true si peut etre le maitre de synchro diff -r 75ae893d5eed -r a1f9e514f708 plugins/__init__.py --- a/plugins/__init__.py Mon Aug 20 14:28:08 2007 +0200 +++ b/plugins/__init__.py Tue Aug 21 17:21:26 2007 +0200 @@ -1,8 +1,11 @@ from os import listdir, path +from xmlclass import DeclareXSDClass +from __templates import * -base_path = path.split(__file__)[0] +_base_path = path.split(__file__)[0] -__all__ = [name for name in listdir(base_path) if path.isdir(path.join(base_path, name)) and name != "CVS" or name.endswith(".py") and not name.startswith("__")] +__all__ = [name for name in listdir(_base_path) if path.isdir(path.join(_base_path, name)) and name != "CVS" or name.endswith(".py") and not name.startswith("__")] for name in __all__: __import__(name, globals(), locals(), []) + diff -r 75ae893d5eed -r a1f9e514f708 plugins/__templates.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/plugins/__templates.py Tue Aug 21 17:21:26 2007 +0200 @@ -0,0 +1,72 @@ +" Here are base type definitions for plugins " + +class PluggableTemplate: + + XSD = None + + def __init__(self, buspath): + pass + + def TestModified(self): + return False + + def ReqSave(self): + return False + + def Generate_C(self, dirpath, locations): + return [] # [filenames, ...] + + def BlockTypesFactory(self): + return [] + + def STLibraryFactory(self): + return "" + + ViewClass = None + View = None + def ViewFactory(self): + if self.ViewClass: + if not self.View: + def _onclose(): + self.View = None + self.View = self.ViewClass() + self.View.OnPluggClose = _onclose + return self.View + return None + + +def _do_BaseParamsClasses(): + Classes = {} + Types = {} + GenerateClassesFromXSDstring(""" + + + + + + + + """) + CreateClasses(Classes, Types) + + PluginsBaseParamsClass = Classes["BaseParams"] + + Classes = {} + Types = {} + GenerateClassesFromXSDstring(""" + + + + + + + + + """) + CreateClasses(Classes, Types) + + BusBaseParamsClass = Classes["BaseParams"] + return PluginsBaseParamsClass, BusBaseParamsClass + +PluginsBaseParamsClass, BusBaseParamsClass = _do_BaseParamsClasses() + diff -r 75ae893d5eed -r a1f9e514f708 plugins/canfestival/__init__.py --- a/plugins/canfestival/__init__.py Mon Aug 20 14:28:08 2007 +0200 +++ b/plugins/canfestival/__init__.py Tue Aug 21 17:21:26 2007 +0200 @@ -1,2 +1,1 @@ -from networkedit import networkedit as view from canfestival import * diff -r 75ae893d5eed -r a1f9e514f708 plugins/canfestival/canfestival.py --- a/plugins/canfestival/canfestival.py Mon Aug 20 14:28:08 2007 +0200 +++ b/plugins/canfestival/canfestival.py Tue Aug 21 17:21:26 2007 +0200 @@ -1,16 +1,65 @@ +import os from nodelist import NodeList from nodemanager import NodeManager import config_utils, gen_cfile +from networkedit import networkedit -class _Beremiz_CanFestival_Controller(NodeList): - def __init__(self, buspath, bus_id): - self.bus_id = bus_id +class _NetworkEditPlugg(networkedit): + def OnCloseFrame(self, event): + self.OnPluggClose() + event.Skip() + +class BusController(NodeList): + XSD = """ + + + + + + + + """ + + ViewClass = _NetworkEditPlugg + + def __init__(self, buspath): manager = NodeManager() NodeList.__init__(self, manager) self.LoadProject(buspath) - def SaveBus(self): + def TestModified(self): + return self.HasChanged() + + def ReqSave(self): self.SaveProject() + return True + + def Generate_C(self, dirpath, locations): + """ + return C code for network dictionnary + """ + filepath = os.path.join(dirpath, "master.c") + master = config_utils.GenerateConciseDCF(locations, self) + res = gen_cfile.GenerateFile(filepath, master) + if not res: + s = str(self.BaseParams.BusId)+"_IN(){}\n" + s += "CanOpen(str(\""+self.CanFestivalNode.CAN_Device)+"\")" + f = file(filepath, 'a') + f.write(s) + else: + pass # error + return {"headers":["master.h"],"sources":["master.c"]} + +class PluginController: + XSD = """ + + + + + + + + """ def Generate_C(self, filepath, locations): """ @@ -19,14 +68,10 @@ master = config_utils.GenerateConciseDCF(locations, self) res = gen_cfile.GenerateFile(filepath, master) if not res: - s = str(self.bus_id)+"_IN(){}\n" + s = str(self.BaseParams.BusId)+"_IN(){}\n" + s += "CanOpen(str(\""+self.CanFestivalNode.CAN_Device)+"\")" f = file(filepath, 'a') f.write(s) else: pass # error -def BlockListFactory(bmz_inst): - return [] - -def ControllerFactory(): - return _Beremiz_CanFestival_Controller() \ No newline at end of file diff -r 75ae893d5eed -r a1f9e514f708 plugins/svgui/svgui.py --- a/plugins/svgui/svgui.py Mon Aug 20 14:28:08 2007 +0200 +++ b/plugins/svgui/svgui.py Tue Aug 21 17:21:26 2007 +0200 @@ -1,60 +1,97 @@ +import os +from DEFControler import DEFControler +from defeditor import EditorFrame +class _EditorFramePlugg(EditorFrame): + def OnClose(self, event): + self.OnPluggClose() + event.Skip() + +class BusController(DEFControler): + + ViewClass = _EditorFramePlugg + + def __init__(self, buspath): + filepath = os.path.join(buspath, "gui.def") + if os.path.isfile(filepath): + self.OpenXMLFile(filepath) + else + self.CreateRootElement() + self.SetFilePath(filepath) + + def ReqSave(self): + self.SaveXMLFile() + return True + + def Generate_C(self, dirpath, locations): + self.GenerateProgram(filepath) + return {"headers":["program.h"],"sources":["program.cpp"]} + TYPECONVERSION = {"BOOL" : "X", "SINT" : "B", "INT" : "W", "DINT" : "D", "LINT" : "L", "USINT" : "B", "UINT" : "W", "UDINT" : "D", "ULINT" : "L", "REAL" : "D", "LREAL" : "L", "STRING" : "B", "BYTE" : "B", "WORD" : "W", "DWORD" : "D", "LWORD" : "L", "WSTRING" : "W"} -def GetBlockGenerationFunction(beremiz): - def generate_svgui_block(generator, block, body, link): - controller = generator.GetController() - name = block.getInstanceName() - type = block.getTypeName() - block_infos = GetBlockType(type) - bus_id, name = [word for word in name.split("_") if word != ""] - block_id = beremiz.GetSVGUIElementId(bus_id, name) - if block_id == None: - raise ValueError, "No corresponding block found" - if not generator.ComputedBlocks.get(name, False): - for num, variable in enumerate(block.inputVariables.getVariable()): - connections = variable.connectionPointIn.getConnections() - if connections and len(connections) == 1: - parameter = "__I%s%d_%d_%d"%(TYPECONVERSION[block_infos["inputs"][num][1]], bus_id, block_id, num) - value = generator.ComputeFBDExpression(body, connections[0]) - generator.Program += (" %s := %s;\n"%(parameter, generator.ExtractModifier(variable, value))) - generator.ComputedBlocks[name] = True - if link: - connectionPoint = link.getPosition()[-1] - for num, variable in enumerate(block.outputVariables.getVariable()): - blockPointx, blockPointy = variable.connectionPointOut.getRelPosition() - if block.getX() + blockPointx == connectionPoint.getX() and block.getY() + blockPointy == connectionPoint.getY(): - return "__Q%s%d_%d_%d"%(TYPECONVERSION[block_infos["outputs"][num][1]], bus_id, block_id, num) - raise ValueError, "No output variable found" - else: - return None - return generate_svgui_block +class PluginController: + def BlockTypesFactory(self): + def generate_svgui_block(generator, block, body, link): + controller = generator.GetController() + name = block.getInstanceName() + type = block.getTypeName() + block_infos = GetBlockType(type) + bus_id, name = [word for word in name.split("_") if word != ""] + block_id = self.PluginBuses[bus_id].GetElementIdFromName(name) + if block_id == None: + raise ValueError, "No corresponding block found" + if not generator.ComputedBlocks.get(name, False): + for num, variable in enumerate(block.inputVariables.getVariable()): + connections = variable.connectionPointIn.getConnections() + if connections and len(connections) == 1: + parameter = "__I%s%d_%d_%d"%(TYPECONVERSION[block_infos["inputs"][num][1]], bus_id, block_id, num) + value = generator.ComputeFBDExpression(body, connections[0]) + generator.Program += (" %s := %s;\n"%(parameter, generator.ExtractModifier(variable, value))) + generator.ComputedBlocks[name] = True + if link: + connectionPoint = link.getPosition()[-1] + for num, variable in enumerate(block.outputVariables.getVariable()): + blockPointx, blockPointy = variable.connectionPointOut.getRelPosition() + if block.getX() + blockPointx == connectionPoint.getX() and block.getY() + blockPointy == connectionPoint.getY(): + return "__Q%s%d_%d_%d"%(TYPECONVERSION[block_infos["outputs"][num][1]], bus_id, block_id, num) + raise ValueError, "No output variable found" + else: + return None -BlockList = {"name" : "SVGUI function blocks", "list" : - [{"name" : "Container", "type" : "functionBlock", "extensible" : False, - "inputs" : [("X","FLOAT","none"),("SetX","BOOL","none"),("Y","FLOAT","none"),("SetY","BOOL","none"),("Angle","FLOAT","none"),("SetAngle","BOOL","none")], - "outputs" : [("X","FLOAT","none"),("X Changed","BOOL","none"),("Y","FLOAT","none"),("Y Changed","BOOL","none"),("Angle","FLOAT","none"),("Angle Changed","BOOL","none")], - "comment" : "SVGUI Container"}, - {"name" : "Button", "type" : "functionBlock", "extensible" : False, - "inputs" : [("Show","BOOL","none"),("Toggle","BOOL","none")], - "outputs" : [("Visible","BOOL","none"),("State","BOOL","none")], - "comment" : "SVGUI Button"}, - {"name" : "TextCtrl", "type" : "functionBlock", "extensible" : False, - "inputs" : [("Text","STRING","none"),("Set Text","BOOL","none")], - "outputs" : [("Text","STRING","none"),("Text Changed","BOOL","none")], - "comment" : "SVGUI Text Control"}, - {"name" : "ScrollBar", "type" : "functionBlock", "extensible" : False, - "inputs" : [("Position","UINT","none"),("Set Position","BOOL","none")], - "outputs" : [("Position","UINT","none"),("Position Changed","BOOL","none")], - "comment" : "SVGUI ScrollBar"}, - {"name" : "NoteBook", "type" : "functionBlock", "extensible" : False, - "inputs" : [("Selected","UINT","none"),("Set Selected","BOOL","none")], - "outputs" : [("Selected","UINT","none"),("Selected Changed","BOOL","none")], - "comment" : "SVGUI Notebook"}, - {"name" : "RotatingCtrl", "type" : "functionBlock", "extensible" : False, - "inputs" : [("Angle","FLOAT","none"),("Set Angle","BOOL","none")], - "outputs" : [("Angle","FLOAT","none"),("Angle changed","BOOL","none")], - "comment" : "SVGUI Rotating Control"}, - ]} + return [{"name" : "SVGUI function blocks", "list" : + [{"name" : "Container", "type" : "functionBlock", "extensible" : False, + "inputs" : [("X","FLOAT","none"),("SetX","BOOL","none"),("Y","FLOAT","none"),("SetY","BOOL","none"),("Angle","FLOAT","none"),("SetAngle","BOOL","none")], + "outputs" : [("X","FLOAT","none"),("X Changed","BOOL","none"),("Y","FLOAT","none"),("Y Changed","BOOL","none"),("Angle","FLOAT","none"),("Angle Changed","BOOL","none")], + "comment" : "SVGUI Container", "generate": generate_svgui_block}, + {"name" : "Button", "type" : "functionBlock", "extensible" : False, + "inputs" : [("Show","BOOL","none"),("Toggle","BOOL","none")], + "outputs" : [("Visible","BOOL","none"),("State","BOOL","none")], + "comment" : "SVGUI Button", "generate": generate_svgui_block}, + {"name" : "TextCtrl", "type" : "functionBlock", "extensible" : False, + "inputs" : [("Text","STRING","none"),("Set Text","BOOL","none")], + "outputs" : [("Text","STRING","none"),("Text Changed","BOOL","none")], + "comment" : "SVGUI Text Control", "generate": generate_svgui_block}, + {"name" : "ScrollBar", "type" : "functionBlock", "extensible" : False, + "inputs" : [("Position","UINT","none"),("Set Position","BOOL","none")], + "outputs" : [("Position","UINT","none"),("Position Changed","BOOL","none")], + "comment" : "SVGUI ScrollBar", "generate": generate_svgui_block}, + {"name" : "NoteBook", "type" : "functionBlock", "extensible" : False, + "inputs" : [("Selected","UINT","none"),("Set Selected","BOOL","none")], + "outputs" : [("Selected","UINT","none"),("Selected Changed","BOOL","none")], + "comment" : "SVGUI Notebook", "generate": generate_svgui_block}, + {"name" : "RotatingCtrl", "type" : "functionBlock", "extensible" : False, + "inputs" : [("Angle","FLOAT","none"),("Set Angle","BOOL","none")], + "outputs" : [("Angle","FLOAT","none"),("Angle changed","BOOL","none")], + "comment" : "SVGUI Rotating Control", "generate": generate_svgui_block} + ]}] + + + + + + + + +