2 This page is in the table of contents.
3 The csv.py script is an import translator plugin to get a carving from an csv file.
5 An import plugin is a script in the interpret_plugins folder which has the function getCarving. It is meant to be run from the interpret tool. To ensure that the plugin works on platforms which do not handle file capitalization properly, give the plugin a lower case name.
7 The getCarving function takes the file name of an csv file and returns the carving.
12 from __future__ import absolute_import
13 #Init has to be imported first because it has code to workaround the python bug where relative imports don't work if the module is imported as a main module.
16 from fabmetheus_utilities import archive
17 from fabmetheus_utilities import gcodec
18 from fabmetheus_utilities import xml_simple_reader
22 __author__ = 'Enrique Perez (perez_enrique@yahoo.com)'
23 __credits__ = 'Nophead <http://hydraraptor.blogspot.com/>\nArt of Illusion <http://www.artofillusion.org/>'
24 __date__ = '$Date: 2008/21/04 $'
25 __license__ = 'GNU Affero General Public License http://www.gnu.org/licenses/agpl.html'
28 def getCarving(fileName=''):
29 "Get the carving for the csv file."
30 csvText = archive.getFileText(fileName)
33 csvParser = CSVSimpleParser( fileName, None, csvText )
34 lowerLocalName = csvParser.getDocumentElement().getNodeName().lower()
35 pluginModule = archive.getModuleWithDirectoryPath( getPluginsDirectoryPath(), lowerLocalName )
36 if pluginModule == None:
38 return pluginModule.getCarvingFromParser( csvParser )
40 def getLineDictionary(line):
41 "Get the line dictionary."
43 splitLine = line.split('\t')
44 for splitLineIndex in xrange( len(splitLine) ):
45 word = splitLine[ splitLineIndex ]
47 lineDictionary[ splitLineIndex ] = word
50 def getPluginsDirectoryPath():
51 "Get the plugins directory path."
52 return archive.getInterpretPluginsPath('xml_plugins')
55 class CSVElement( xml_simple_reader.XMLElement ):
57 def continueParsingObject( self, line, lineStripped ):
58 "Parse replaced line."
59 splitLineStripped = lineStripped.split('\t')
60 key = splitLineStripped[0]
61 value = splitLineStripped[1]
62 self.attributes[key] = value
63 self.addToIdentifierDictionaries()
65 def continueParsingTable( self, line, lineStripped ):
66 "Parse replaced line."
67 if self.headingDictionary == None:
68 self.headingDictionary = getLineDictionary(line)
71 oldAttributesLength = len( self.attributes )
72 if oldAttributesLength > 0:
73 csvElement = CSVElement()
74 csvElement.parentNode = self.parentNode
75 csvElement.localName = self.localName
76 lineDictionary = getLineDictionary(line)
77 for columnIndex in lineDictionary.keys():
78 if columnIndex in self.headingDictionary:
79 key = self.headingDictionary[ columnIndex ]
80 value = lineDictionary[ columnIndex ]
81 csvElement.attributes[key] = value
82 csvElement.addToIdentifierDictionaries()
83 if len( csvElement.attributes ) == 0 or oldAttributesLength == 0 or self.parentNode == None:
85 self.parentNode.childNodes.append( csvElement )
87 def getElementFromObject( self, leadingTabCount, lineStripped, oldElement ):
88 "Parse replaced line."
89 splitLine = lineStripped.split('\t')
90 self.localName = splitLine[1]
91 if leadingTabCount == 0:
93 self.parentNode = oldElement
94 while leadingTabCount <= self.parentNode.getNumberOfParents():
95 self.parentNode = self.parentNode.parentNode
96 self.parentNode.childNodes.append(self)
99 def getElementFromTable( self, leadingTabCount, lineStripped, oldElement ):
100 "Parse replaced line."
101 self.headingDictionary = None
102 return self.getElementFromObject( leadingTabCount, lineStripped, oldElement )
104 def getNumberOfParents(self):
105 "Get the number of parent nodes."
106 if self.parentNode == None:
108 return self.parentNode.getNumberOfParents() + 1
111 class CSVSimpleParser( xml_simple_reader.DocumentNode ):
112 "A simple csv parser."
113 def __init__( self, parentNode, csvText ):
115 self.continueFunction = None
116 self.extraLeadingTabCount = None
117 self.lines = archive.getTextLines( csvText )
118 self.oldCSVElement = None
119 self.documentElement = None
120 for line in self.lines:
123 def getNewCSVElement( self, leadingTabCount, lineStripped ):
124 "Get a new csv element."
125 if self.documentElement != None and self.extraLeadingTabCount == None:
126 self.extraLeadingTabCount = 1 - leadingTabCount
127 if self.extraLeadingTabCount != None:
128 leadingTabCount += self.extraLeadingTabCount
129 if lineStripped[ : len('_table') ] == '_table' or lineStripped[ : len('_t') ] == '_t':
130 self.oldCSVElement = CSVElement().getElementFromTable( leadingTabCount, lineStripped, self.oldCSVElement )
131 self.continueFunction = self.oldCSVElement.continueParsingTable
133 self.oldCSVElement = CSVElement().getElementFromObject( leadingTabCount, lineStripped, self.oldCSVElement )
134 self.continueFunction = self.oldCSVElement.continueParsingObject
136 def parseLine(self, line):
137 "Parse a gcode line and add it to the inset skein."
138 lineStripped = line.lstrip()
139 if len( lineStripped ) < 1:
141 leadingPart = line[ : line.find( lineStripped ) ]
142 leadingTabCount = leadingPart.count('\t')
143 if lineStripped[ : len('_') ] == '_':
144 self.getNewCSVElement( leadingTabCount, lineStripped )
145 if self.documentElement == None:
146 self.documentElement = self.oldCSVElement
147 self.documentElement.document = self
149 if self.continueFunction != None:
150 self.continueFunction( line, lineStripped )
154 "Display the inset dialog."
155 if len(sys.argv) > 1:
156 getCarving(' '.join(sys.argv[1 :]))
158 if __name__ == "__main__":