CodeFileTreeNode.py
branch1.1 Korean release
changeset 1280 72a826dfcfbb
parent 1153 5bdd82497925
child 1315 ff14a66bbd12
equal deleted inserted replaced
977:c8e008b8cefe 1280:72a826dfcfbb
       
     1 import os
       
     2 from xml.dom import minidom
       
     3 import cPickle
       
     4 
       
     5 from xmlclass import GenerateClassesFromXSDstring, UpdateXMLClassGlobals
       
     6 
       
     7 from PLCControler import UndoBuffer
       
     8 
       
     9 CODEFILE_XSD = """<?xml version="1.0" encoding="ISO-8859-1" ?>
       
    10 <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
       
    11   <xsd:element name="%(codefile_name)s">
       
    12     <xsd:complexType>
       
    13       <xsd:sequence>
       
    14         %(includes_section)s
       
    15         <xsd:element name="variables">
       
    16           <xsd:complexType>
       
    17             <xsd:sequence>
       
    18               <xsd:element name="variable" minOccurs="0" maxOccurs="unbounded">
       
    19                 <xsd:complexType>
       
    20                   <xsd:attribute name="name" type="xsd:string" use="required"/>
       
    21                   <xsd:attribute name="type" type="xsd:string" use="required"/>
       
    22                   <xsd:attribute name="class" use="optional">
       
    23                     <xsd:simpleType>
       
    24                       <xsd:restriction base="xsd:string">
       
    25                         <xsd:enumeration value="input"/>
       
    26                         <xsd:enumeration value="memory"/>
       
    27                         <xsd:enumeration value="output"/>
       
    28                       </xsd:restriction>
       
    29                     </xsd:simpleType>
       
    30                   </xsd:attribute>
       
    31                   <xsd:attribute name="initial" type="xsd:string" use="optional" default=""/>
       
    32                 </xsd:complexType>
       
    33               </xsd:element>
       
    34             </xsd:sequence>
       
    35           </xsd:complexType>
       
    36         </xsd:element>
       
    37         %(sections)s
       
    38       </xsd:sequence>
       
    39     </xsd:complexType>
       
    40   </xsd:element>
       
    41   <xsd:complexType name="CodeText">
       
    42     <xsd:annotation>
       
    43       <xsd:documentation>Formatted text according to parts of XHTML 1.1</xsd:documentation>
       
    44     </xsd:annotation>
       
    45     <xsd:sequence>
       
    46       <xsd:any namespace="http://www.w3.org/1999/xhtml" processContents="lax"/>
       
    47     </xsd:sequence>
       
    48   </xsd:complexType>
       
    49 </xsd:schema>"""
       
    50 
       
    51 SECTION_TAG_ELEMENT = "<xsd:element name=\"%s\" type=\"CodeText\"/>"
       
    52 
       
    53 class CodeFile:
       
    54     
       
    55     CODEFILE_NAME = "CodeFile"
       
    56     SECTIONS_NAMES = []
       
    57     
       
    58     def __init__(self):
       
    59         sections_str = {"codefile_name": self.CODEFILE_NAME}
       
    60         if "includes" in self.SECTIONS_NAMES:
       
    61             sections_str["includes_section"] = SECTION_TAG_ELEMENT % "includes"
       
    62         else:
       
    63             sections_str["includes_section"] = ""
       
    64         sections_str["sections"] = "\n".join(
       
    65             [SECTION_TAG_ELEMENT % name
       
    66              for name in self.SECTIONS_NAMES if name != "includes"])
       
    67         
       
    68         self.CodeFileClasses = GenerateClassesFromXSDstring(
       
    69             CODEFILE_XSD % sections_str)
       
    70         
       
    71         filepath = self.CodeFileName()
       
    72         
       
    73         self.CodeFile = self.CodeFileClasses[self.CODEFILE_NAME]()
       
    74         if os.path.isfile(filepath):
       
    75             xmlfile = open(filepath, 'r')
       
    76             tree = minidom.parse(xmlfile)
       
    77             xmlfile.close()
       
    78             
       
    79             for child in tree.childNodes:
       
    80                 if child.nodeType == tree.ELEMENT_NODE and child.nodeName in [self.CODEFILE_NAME]:
       
    81                     self.CodeFile.loadXMLTree(child, ["xmlns", "xmlns:xsi", "xsi:schemaLocation"])
       
    82                     self.CreateCodeFileBuffer(True)
       
    83         else:
       
    84             self.CreateCodeFileBuffer(False)
       
    85             self.OnCTNSave()
       
    86 
       
    87     def GetBaseTypes(self):
       
    88         return self.GetCTRoot().GetBaseTypes()
       
    89 
       
    90     def GetDataTypes(self, basetypes = False):
       
    91         return self.GetCTRoot().GetDataTypes(basetypes=basetypes)
       
    92 
       
    93     def GenerateNewName(self, format, start_idx):
       
    94         return self.GetCTRoot().GenerateNewName(
       
    95             None, None, format, start_idx,
       
    96             dict([(var.getname().upper(), True) 
       
    97                   for var in self.CodeFile.variables.getvariable()]))
       
    98 
       
    99     def SetVariables(self, variables):
       
   100         self.CodeFile.variables.setvariable([])
       
   101         for var in variables:
       
   102             variable = self.CodeFileClasses["variables_variable"]()
       
   103             variable.setname(var["Name"])
       
   104             variable.settype(var["Type"])
       
   105             variable.setinitial(var["Initial"])
       
   106             self.CodeFile.variables.appendvariable(variable)
       
   107     
       
   108     def GetVariables(self):
       
   109         datas = []
       
   110         for var in self.CodeFile.variables.getvariable():
       
   111             datas.append({"Name" : var.getname(), 
       
   112                           "Type" : var.gettype(), 
       
   113                           "Initial" : var.getinitial()})
       
   114         return datas
       
   115 
       
   116     def SetTextParts(self, parts):
       
   117         for section in self.SECTIONS_NAMES:
       
   118             section_code = parts.get(section)
       
   119             if section_code is not None:
       
   120                 getattr(self.CodeFile, section).settext(section_code)
       
   121     
       
   122     def GetTextParts(self):
       
   123         return dict([(section, getattr(self.CodeFile, section).gettext())
       
   124                      for section in self.SECTIONS_NAMES])
       
   125             
       
   126     def CTNTestModified(self):
       
   127         return self.ChangesToSave or not self.CodeFileIsSaved()    
       
   128 
       
   129     def OnCTNSave(self, from_project_path=None):
       
   130         filepath = self.CodeFileName()
       
   131         
       
   132         text = "<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\"?>\n"
       
   133         text += self.CodeFile.generateXMLText(self.CODEFILE_NAME, 0)
       
   134 
       
   135         xmlfile = open(filepath,"w")
       
   136         xmlfile.write(text.encode("utf-8"))
       
   137         xmlfile.close()
       
   138         
       
   139         self.MarkCodeFileAsSaved()
       
   140         return True
       
   141 
       
   142     def CTNGlobalInstances(self):
       
   143         current_location = self.GetCurrentLocation()
       
   144         return [(variable.getname(),
       
   145                  variable.gettype(),
       
   146                  variable.getinitial())
       
   147                 for variable in self.CodeFile.variables.variable]
       
   148 
       
   149 #-------------------------------------------------------------------------------
       
   150 #                      Current Buffering Management Functions
       
   151 #-------------------------------------------------------------------------------
       
   152 
       
   153     def cPickle_loads(self, str_obj):
       
   154         UpdateXMLClassGlobals(self.CodeFileClasses)
       
   155         return cPickle.loads(str_obj)
       
   156 
       
   157     def cPickle_dumps(self, obj):
       
   158         UpdateXMLClassGlobals(self.CodeFileClasses)
       
   159         return cPickle.dumps(obj)
       
   160 
       
   161     """
       
   162     Return a copy of the codefile model
       
   163     """
       
   164     def Copy(self, model):
       
   165         return self.cPickle_loads(self.cPickle_dumps(model))
       
   166 
       
   167     def CreateCodeFileBuffer(self, saved):
       
   168         self.Buffering = False
       
   169         self.CodeFileBuffer = UndoBuffer(self.cPickle_dumps(self.CodeFile), saved)
       
   170 
       
   171     def BufferCodeFile(self):
       
   172         self.CodeFileBuffer.Buffering(self.cPickle_dumps(self.CodeFile))
       
   173     
       
   174     def StartBuffering(self):
       
   175         self.Buffering = True
       
   176         
       
   177     def EndBuffering(self):
       
   178         if self.Buffering:
       
   179             self.CodeFileBuffer.Buffering(self.cPickle_dumps(self.CodeFile))
       
   180             self.Buffering = False
       
   181     
       
   182     def MarkCodeFileAsSaved(self):
       
   183         self.EndBuffering()
       
   184         self.CodeFileBuffer.CurrentSaved()
       
   185     
       
   186     def CodeFileIsSaved(self):
       
   187         return self.CodeFileBuffer.IsCurrentSaved() and not self.Buffering
       
   188         
       
   189     def LoadPrevious(self):
       
   190         self.EndBuffering()
       
   191         self.CodeFile = self.cPickle_loads(self.CodeFileBuffer.Previous())
       
   192     
       
   193     def LoadNext(self):
       
   194         self.CodeFile = self.cPickle_loads(self.CodeFileBuffer.Next())
       
   195     
       
   196     def GetBufferState(self):
       
   197         first = self.CodeFileBuffer.IsFirst() and not self.Buffering
       
   198         last = self.CodeFileBuffer.IsLast()
       
   199         return not first, not last
       
   200