""" Gcodec is a collection of utilities to decode and encode gcode. To run gcodec, install python 2.x on your machine, which is avaliable from http://www.python.org/download/ Then in the folder which gcodec is in, type 'python' in a shell to run the python interpreter. Finally type 'from gcodec import *' to import this program. Below is an example of gcodec use. This example is run in a terminal in the folder which contains Hollow Square.gcode and gcodec.py. >>> from gcodec import * >>> getFileText('Hollow Square.gcode') '( GCode generated by April 17,2007 Skeinforge )\n( Extruder Initialization )\nM100 P210\nM103\nM105\n( P0.7\n( P0.654\n( P0.654\nG21\nG90\nG28\n( Extruder Movement )\n( Extruder paths for layer 0 of Hollow Square )\n(\nG1 X2.727 Y-2.505 Z0.33 F600.0\n .. many lines of text .. """ from vec3 import Vec3 import os __author__ = "Enrique Perez (perez_enrique@yahoo.com)" __date__ = "$Date: 2008/21/04 $" __license__ = "GPL 3.0" def getDoubleAfterFirstLetter( word ): """Get the double value of the word after the first letter. Keyword arguments: word -- string with value starting after the first letter""" return float( word[ 1 : ] ) def getDoubleForLetter( letter, splitLine ): "Get the double value of the word after the first occurence of the letter in the split line." return getDoubleAfterFirstLetter( splitLine[ indexOfStartingWithSecond( letter, splitLine ) ] ) def getFeedrateMinute( feedrateMinute, splitLine ): "Get the feedrate per minute if the split line has a feedrate." indexOfF = indexOfStartingWithSecond( "F", splitLine ) if indexOfF > 0: return getDoubleAfterFirstLetter( splitLine[ indexOfF ] ) return feedrateMinute def getFilesWithFileTypeWithoutWords( fileType, words = [], fileInDirectory = '' ): """Get files which have a given file type, but with do not contain a word in a list. Keyword arguments: fileType -- file type required words -- list of words which the file must not have""" filesWithFileType = [] directoryName = os.getcwd() if fileInDirectory != '': directoryName = os.path.dirname( fileInDirectory ) directory = os.listdir( directoryName ) for filename in directory: joinedFilename = filename if fileInDirectory != '': joinedFilename = os.path.join( directoryName, filename ) if isFileWithFileTypeWithoutWords( fileType, joinedFilename, words ) == 1: filesWithFileType.append( joinedFilename ) return filesWithFileType def getFileText( filename ): """Get the entire text of a file. Keyword arguments: filename -- name of the file""" try: file = open( filename, 'r' ) fileText = file.read() file.close() return fileText except IOError: print( 'The file ' + filename + ' does not exist, an empty string will be returned.' ) return '' def getGNUGcode( fileInDirectory = '' ): "Get GNU Triangulated Surface files and gcode files which are not modified." return getGNUTriangulatedSurfaceFiles( fileInDirectory ) + getUnmodifiedGCodeFiles( fileInDirectory ) def getGcodeDirectoryOrFile( isDirectory, filename, wasCancelled ): "Get the gcode files in the directory the file is in if isDirectory is true. Otherwise, return the file in a list." if str( filename ) == '()' or wasCancelled: return [] if isDirectory: return getGNUGcode( filename ) return [ filename ] def getGNUDirectoryOrFile( isDirectory, filename, wasCancelled ): "Get the GNU Triangulated Surface files in the directory the file is in if isDirectory is true. Otherwise, return the file in a list." if str( filename ) == '()' or wasCancelled: return [] if isDirectory: return getGNUTriangulatedSurfaceFiles( filename ) return [ filename ] def getGNUTriangulatedSurfaceFiles( fileInDirectory = '' ): "Get GNU Triangulated Surface files." return getFilesWithFileTypeWithoutWords( 'gts', [], fileInDirectory ) def getLocationFromSplitLine( oldLocation, splitLine ): location = Vec3() if oldLocation != None: location.setToVec3( oldLocation ) indexOfX = indexOfStartingWithSecond( "X", splitLine ) if indexOfX > 0: location.x = getDoubleAfterFirstLetter( splitLine[ indexOfX ] ) indexOfY = indexOfStartingWithSecond( "Y", splitLine ) if indexOfY > 0: location.y = getDoubleAfterFirstLetter( splitLine[ indexOfY ] ) indexOfZ = indexOfStartingWithSecond( "Z", splitLine ) if indexOfZ > 0: location.z = getDoubleAfterFirstLetter( splitLine[ indexOfZ ] ) return location def getSummarizedFilename( filename ): "Get the filename basename if the file is in the current working directory, otherwise return the original full name." if os.getcwd() == os.path.dirname( filename ): return os.path.basename( filename ) return filename def getTextLines( text ): """Get the all the lines of text of a text. Keyword arguments: text -- text""" return text.replace( '\r', '\n' ).split( '\n' ) def getUnmodifiedGCodeFiles( fileInDirectory = '' ): "Get gcode files which are not modified." return getFilesWithFileTypeWithoutWords( 'gcode', [ '_comb', '_comment', '_fill', '_fillet', '_hop', '_raft', '_transform', '_slice', '_wipe' ], fileInDirectory ) def indexOfStartingWithSecond( letter, splitLine ): "Get index of the first occurence of the given letter in the split line, starting with the second word. Return - 1 if letter is not found" for wordIndex in range( 1, len( splitLine ) ): word = splitLine[ wordIndex ] firstLetter = word[ 0 ] if firstLetter == letter: return wordIndex return - 1 def isFileWithFileTypeWithoutWords( fileType, filename, words ): """Determine if file has a given file type, but with does not contain a word in a list. Keyword arguments: fileType -- file type required filename -- name of the file words -- list of words which the filename must not have""" filename = os.path.basename( filename ) splitFile = filename.split( '.' ) if splitFile[ - 1 ] != fileType: return 0 for word in words: if filename.find( word ) >= 0: return 0 return 1 def isProcedureDone( gcodeText, procedure ): "Determine if the procedure has been done on the gcode text." lines = getTextLines( gcodeText ) for line in lines: splitLine = line.split( ' ' ) firstWord = '' if len( splitLine ) > 0: firstWord = splitLine[ 0 ] if firstWord == '(': if splitLine[ 1 ].find( procedure ) != - 1: return True elif firstWord == '(': return False return False def replaceWords( filenames, wordReplacements ): "Replace in files the first word of a tuple with the second word of the tuple, from a list of tuples." for filename in filenames: fileText = getFileText( filename ) print( 'In the file ' + filename ) print( 'The following replacements are being made:' ) for wordReplacement in wordReplacements: fileText = fileText.replace( wordReplacement[ 0 ], wordReplacement[ 1 ] ) writeFileText( filename, fileText ) for wordReplacement in wordReplacements: print( wordReplacement[ 0 ] + ' with ' + wordReplacement[ 1 ] ) def writeFileMessageEnd( end, filename, fileText, message ): "Write to a filename with a suffix and print a message." suffixFilename = filename[ : filename.rfind( '.' ) ] + end writeFileText( suffixFilename, fileText ) print( message + getSummarizedFilename( suffixFilename ) ) def writeFileText( filename, fileText ): """Write a text to a file. Keyword arguments: filename -- name of the file fileText -- text which will be written to the file""" try: file = open( filename, 'w+' ) file.write( fileText ) file.close() except IOError: print( 'The file ' + filename + ' can not be written to.' )