plugins/__templates.py
author etisserant
Mon, 27 Aug 2007 17:54:55 +0200
changeset 13 f1f0edbeb313
parent 12 a1f9e514f708
permissions -rw-r--r--
More precise design for plugins.... to be continued...
13
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     1
"""
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     2
Base definitions for beremiz plugins
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     3
"""
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     4
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     5
import os
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     6
import types
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     7
import shutil
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     8
from xml.dom import minidom
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
     9
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    10
_BaseParamsClass = GenerateClassesFromXSDstring("""<?xml version="1.0" encoding="ISO-8859-1" ?>
12
a1f9e514f708 plugin framework organization being defined
etisserant
parents:
diff changeset
    11
        <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
a1f9e514f708 plugin framework organization being defined
etisserant
parents:
diff changeset
    12
          <xsd:element name="BaseParams">
a1f9e514f708 plugin framework organization being defined
etisserant
parents:
diff changeset
    13
            <xsd:complexType>
13
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    14
              <xsd:attribute name="Name" type="xsd:string" use="required"/>
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    15
              <xsd:attribute name="IEC_Channel" type="xsd:integer" use="required"  default="-1"/>
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    16
              <xsd:attribute name="Enabled" type="xsd:boolean" use="required" default="true"/>
12
a1f9e514f708 plugin framework organization being defined
etisserant
parents:
diff changeset
    17
            </xsd:complexType>
a1f9e514f708 plugin framework organization being defined
etisserant
parents:
diff changeset
    18
          </xsd:element>
13
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    19
        </xsd:schema>""")[0]["BaseParams"]
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    20
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    21
NameTypeSeparator = '@'
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    22
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    23
class PlugTemplate:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    24
    """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    25
    This class is the one that define plugins.
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    26
    """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    27
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    28
    XSD = None
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    29
    PlugChildsTypes = []
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    30
    PlugMaxCount = None
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    31
    PluginMethods = []
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    32
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    33
    def _AddParamsMembers(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    34
        Classes = GenerateClassesFromXSDstring(self.XSD)[0]
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    35
        self.PlugParams = []
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    36
        for name, XSDclass in Classes.items():
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    37
            if XSDclass.IsBaseClass:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    38
                obj = XSDclass()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    39
                self.PlugParams.append( (name, obj) )
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    40
                setattr(self, name, obj)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    41
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    42
    def __init__(self, PlugPath):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    43
        # Create BaseParam 
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    44
        self.BaseParams = _BaseParamsClass()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    45
        self.MandatoryParams = [("BaseParams", self.BaseParams)]
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    46
        self._AddParamsMembers()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    47
        self.PluggedChilds = {}
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    48
    
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    49
    def PluginXmlFilePath(self, PlugName=None):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    50
        return os.path.join(self.PlugPath(PlugName), "plugin.xml")
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    51
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    52
    def PlugPath(self,PlugName=None):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    53
        if not PlugName:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    54
            PlugName = self.BaseParams.getName()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    55
        return os.path.join(self.PlugParent.PlugPath(), PlugName + NameTypeSeparator + self.PlugType)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    56
    
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    57
    def PlugTestModified(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    58
        return False
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    59
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    60
    def OnPlugSave(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    61
        return True
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    62
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    63
    def PlugRequestSave(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    64
        # If plugin do not have corresponding directory
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    65
        if not os.path.isdir(self.PlugPath(PlugName)):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    66
            # Create it
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    67
            os.mkdir(self.PlugPath(PlugName))
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    68
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    69
        # generate XML for all XML parameters controllers of the plugin
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    70
        XMLString = '<?xml version="1.0" encoding="UTF-8"?>'
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    71
        for nodeName, XMLController in self.PlugParams + self.MandatoryParams:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    72
            XMLString += XMLController.generateXMLTextMethod(self, nodeName, 0)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    73
        XMLFile = open(self.PluginXmlFilePath(PlugName),'w')
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    74
        XMLFile.write(XMLString)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    75
        XMLFile.close()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    76
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    77
        # Call the plugin specific OnPlugSave method
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    78
        self.OnPlugSave()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    79
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    80
        # go through all childs and do the same
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    81
        for PlugChild in self.IterChilds():
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    82
            PlugChild.PlugRequestSave()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    83
    
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    84
    def PlugImport(self, src_PlugPath):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    85
        shutil.copytree(src_PlugPath, self.PlugPath)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    86
        return True
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    87
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    88
    def PlugGenerate_C(self, buildpath, current_location, locations):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    89
        """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    90
        Generate C code
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    91
        @param current_location: Tupple containing plugin IEC location : %I0.0.4.5 => (0,0,4,5)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    92
        @param locations: List of complete variables locations \
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    93
            [(IEC_loc, IEC_Direction IEC_Type, Name)]\
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    94
            ex: [((0,0,4,5),'I','X','__IX_0_0_4_5'),...]
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    95
        """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    96
        return [],""
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    97
    
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    98
    def _Generate_C(self, buildpath, current_location, locations):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
    99
        # Generate plugins [(Cfiles, CFLAGS)], LDFLAGS
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   100
        PlugCFilesAndCFLAGS, PlugLDFLAGS = self._Generate_C(buildpath, current_location, locations)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   101
        # recurse through all childs, and stack their results
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   102
        for PlugChild in self.IterChilds():
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   103
            # Get childs [(Cfiles, CFLAGS)], LDFLAGS
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   104
            CFilesAndCFLAGS, LDFLAGS = \
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   105
                PlugChild._Generate_C(
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   106
                    #keep the same path
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   107
                    buildpath,
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   108
                    # but update location (add curent IEC channel at the end)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   109
                    current_location + (self.BaseParams.getIEC_Channel()),
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   110
                    # filter locations that start with current IEC location
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   111
                    [ (l,d,t,n) for l,d,t,n in locations if l[0:len(current_location)] == current_location ])
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   112
            # stack the result
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   113
            PlugCFilesAndCFLAGS += CFilesAndCFLAGS
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   114
            PlugLDFLAGS += LDFLAGS
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   115
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   116
        return PlugCFilesAndCFLAGS,PlugLDFLAGS
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   117
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   118
    def BlockTypesFactory(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   119
        return []
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   120
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   121
    def STLibraryFactory(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   122
        return ""
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   123
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   124
    def IterChilds(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   125
        for PlugType, PluggedChilds in self.PluggedChilds.items():
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   126
            for PlugInstance in PluggedChilds:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   127
                   yield PlugInstance
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   128
    
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   129
    def _GetChildBySomething(self, sep, something, matching):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   130
        toks = matching.split(sep,1)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   131
        for PlugInstance in self.IterChilds:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   132
            # if match component of the name
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   133
            if getattr(PlugInstance.BaseParams, something) == toks[0]:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   134
                # if Name have other components
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   135
                if len(toks) == 2:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   136
                    # Recurse in order to find the latest object
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   137
                    return PlugInstance._GetChildBySomething( sep, something, toks[1])
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   138
                # No sub name -> found
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   139
                return PlugInstance
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   140
        # Not found
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   141
        return None
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   142
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   143
    def GetChildByName(self, Name):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   144
        return self._GetChildBySomething('.',"Name", Name)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   145
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   146
    def GetChildByIECLocation(self, Location):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   147
        return self._GetChildBySomething('_',"IEC_Channel", Name)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   148
    
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   149
    def FindNewIEC_Channel(self, DesiredChannel):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   150
        """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   151
        Changes IEC Channel number to DesiredChannel if available, nearest available if not.
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   152
        @param DesiredChannel: The desired IEC channel (int)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   153
        """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   154
        # Get Current IEC channel
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   155
        CurrentChannel = self.BaseParams.getIEC_Channel()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   156
        # Do nothing if no change
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   157
        if CurrentChannel == DesiredChannel: return CurrentChannel
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   158
        # Build a list of used Channels out of parent's PluggedChilds
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   159
        AllChannels=[]
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   160
        for PlugInstance in self.PlugParent.IterChilds():
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   161
            if PlugInstance != self:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   162
                AllChannels.append(PlugInstance.BaseParams.getIEC_Channel())
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   163
        AllChannels.sort()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   164
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   165
        # Now, try to guess the nearest available channel
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   166
        res = DesiredChannel
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   167
        while res in AllChannels: # While channel not free
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   168
            if res < CurrentChannel: # Want to go down ?
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   169
                res -=  1 # Test for n-1
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   170
                if res < 0 : return CurrentChannel # Can't go bellow 0, do nothing
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   171
            else : # Want to go up ?
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   172
                res +=  1 # Test for n-1
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   173
        # Finally set IEC Channel
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   174
        self.BaseParams.setIEC_Channel(res)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   175
        return res
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   176
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   177
    def OnPlugClose(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   178
        return True
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   179
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   180
    def _doRemoveChild(self, PlugInstance):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   181
        # Remove all childs of child
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   182
        for SubPlugInstance in PlugInstance.IterChilds():
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   183
            PlugInstance._doRemoveChild(SubPlugInstance)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   184
        # Call the OnCloseMethod
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   185
        PlugInstance.OnPlugClose()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   186
        # Delete plugin dir
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   187
        shutil.rmtree(PlugInstance.PlugPath())
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   188
        # Remove child of PluggedChilds
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   189
        self.PluggedChilds[PlugInstance.PlugType].remove(PlugInstance)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   190
        # Forget it... (View have to refresh)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   191
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   192
    def PlugRemoveChild(self, PlugName):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   193
        # Fetch the plugin
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   194
        PlugInstance = self.GetChildByName(PlugName)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   195
        # Ask to his parent to remove it
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   196
        PlugInstance.PlugParent._doRemoveChild(PlugInstance)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   197
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   198
    def PlugAddChild(self, PlugName, PlugType):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   199
        """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   200
        Create the plugins that may be added as child to this node self
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   201
        @param PlugType: string desining the plugin class name (get name from PlugChildsTypes)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   202
        @param PlugName: string for the name of the plugin instance
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   203
        """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   204
        PlugChildsTypes = dict(self.PlugChildsTypes)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   205
        # Check that adding this plugin is allowed
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   206
        try:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   207
            PlugClass = PlugChildsTypes[PlugType]
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   208
        except KeyError:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   209
            raise Exception, "Cannot create child %s of type %s "%(PlugName, PlugType)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   210
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   211
        # if PlugClass is a class factory, call it. (prevent unneeded imports)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   212
        if type(PlugClass) == types.FunctionType:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   213
            PlugClass = PlugClass()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   214
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   215
        # Eventualy Initialize child instance list for this class of plugin
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   216
        PluggedChildsWithSameClass = self.PluggedChilds.setdefault(PlugType,list())
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   217
        # Check count
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   218
        if PlugClass.MaxCount and len(PluggedChildsWithSameClass) >= PlugClass.MaxCount:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   219
            raise Exception, "Max count (%d) reached for this plugin of type %s "%(PlugClass.MaxCount, PlugType)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   220
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   221
        # create the final class, derived of provided plugin and template
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   222
        class FinalPlugClass(PlugClass, PlugTemplate):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   223
            """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   224
            Plugin class is derivated into FinalPlugClass before being instanciated
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   225
            This way __init__ is overloaded to ensure PlugTemplate.__init__ is called 
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   226
            before PlugClass.__init__, and to do the file related stuff.
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   227
            """
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   228
            def __init__(_self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   229
                # self is the parent
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   230
                _self.PlugParent = self
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   231
                # Keep track of the plugin type name
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   232
                _self.PlugType = PlugType
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   233
                # Call the base plugin template init - change XSD into class members
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   234
                PlugTemplate.__init__(_self)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   235
                # If dir have already be made, and file exist
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   236
                if os.path.isdir(_self.PlugPath(PlugName)) and os.path.isfile(_self.PluginXmlFilePath(PlugName)):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   237
                    #Load the plugin.xml file into parameters members
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   238
                    _self.LoadXMLParams()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   239
                    # Call the plugin real __init__
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   240
                    PlugClass.__init__(_self)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   241
                    #Load and init all the childs
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   242
                    _self.LoadChilds()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   243
                    # Check that IEC_Channel is not already in use.
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   244
                    self.FindNewIEC_Channel(self.BaseParams.getIEC_Channel())
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   245
                else:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   246
                    # If plugin do not have corresponding file/dirs - they will be created on Save
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   247
                    # Set plugin name
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   248
                    _self.BaseParams.setName(PlugName)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   249
                    # Find an IEC number
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   250
                    _self.FindNewIEC_Channel(0)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   251
                    # Call the plugin real __init__
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   252
                    PlugClass.__init__(_self)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   253
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   254
        # Create the object out of the resulting class
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   255
        newPluginOpj = FinalPlugClass()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   256
        # Store it in PluggedChils
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   257
        PluggedChildsWithSameClass.append(newPluginOpj)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   258
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   259
        return newPluginOpj
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   260
            
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   261
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   262
    def LoadXMLParams(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   263
        # PlugParams have been filled, make a local dict to work with
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   264
        PlugParams = dict(self.PlugParams + self.MandatoryParams)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   265
        # Get the xml tree
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   266
        xmlfile = open(self.PluginXmlFilePath(PlugName), 'r')
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   267
        tree = minidom.parse(xmlfile)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   268
        xmlfile.close()
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   269
        # for each root elements
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   270
        for subtree in tree.childNodes:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   271
            # if a plugin specific parameter set
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   272
            if subtree.nodeName in PlugParams:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   273
                #Load into associated xmlclass.
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   274
                PlugParams[subtree.nodeName].loadXMLTree(subtree)
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   275
        
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   276
        # Basic check. Better to fail immediately.
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   277
        if(self.BaseParams.getName() != PlugName):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   278
            raise Exception, "Project tree layout do not match plugin.xml %s!=%s "%(PlugName,self.BaseParams.getName())
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   279
        # Now, self.PlugPath() should be OK
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   280
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   281
    def LoadChilds(self):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   282
        # Iterate over all PlugName@PlugType in plugin directory, and try to open them
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   283
        for PlugDir in os.listdir(self.PlugPath()):
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   284
            if os.path.isdir(os.path.join(self.PlugPath(),PlugDir)) and \
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   285
               PlugDir.count(NameTypeSeparator) == 1:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   286
                try:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   287
                    self.PlugAddChild(*PlugDir.split[NameTypeSeparator])
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   288
                except Exception, e:
f1f0edbeb313 More precise design for plugins.... to be continued...
etisserant
parents: 12
diff changeset
   289
                    print e