chiark / gitweb /
26d5fd86f167cc94abcadce5dca286d11b015483
[cura.git] /
1 """
2 This page is in the table of contents.
3 Scalable vector graphics is an export canvas plugin to export the canvas to a scalable vector graphics (.svg) file.
4
5 When the export menu item in the file menu in an analyze viewer tool, like skeinlayer or skeiniso is clicked, the postscript dialog will be displayed.  When the 'Export to Scalable Vector Graphics' button on that dialog is clicked, the canvas will be exported as a scalable vector graphics file.  If the 'Scalable Vector Graphics Program' is set to the default 'webbrowser', the scalable vector graphics file will be sent to the default browser to be opened.  If the 'Scalable Vector Graphics Program' is set to a program name, the scalable vector graphics file will be sent to that program to be opened.
6
7 If furthermore the 'File Extension' is set to a file extension, the scalable vector graphics file will be sent to the program, along with the file extension for the converted output.  The default is blank because some systems do not have an image conversion program; if you have or will install an image conversion program, a common 'File Extension' is png.  A good open source conversion program is Image Magick, which is available at:
8 http://www.imagemagick.org/script/index.php
9
10 An export canvas plugin is a script in the export_canvas_plugins folder which has the function getNewRepository, and which has a repository class with the functions setCanvasFileNameSuffix to set variables and execute to save the file.  It is meant to be run from an analyze viewer tool, like skeinlayer or skeiniso.  To ensure that the plugin works on platforms which do not handle file capitalization properly, give the plugin a lower case name.
11
12 """
13
14 from __future__ import absolute_import
15 #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 import __init__
17
18 from fabmetheus_utilities import archive
19 from fabmetheus_utilities import gcodec
20 from fabmetheus_utilities import settings
21 from skeinforge_application.skeinforge_utilities import skeinforge_profile
22 import cStringIO
23 import os
24 import sys
25
26
27 __author__ = 'Enrique Perez (perez_enrique@yahoo.com)'
28 __date__ = '$Date: 2008/21/04 $'
29 __license__ = 'GNU Affero General Public License http://www.gnu.org/licenses/agpl.html'
30
31
32 def getNewRepository():
33         'Get new repository.'
34         return ScalableVectorGraphicsRepository()
35
36 def parseLineReplace( firstWordTable, line, output ):
37         "Parse the line and replace it if the first word of the line is in the first word table."
38         firstWord = gcodec.getFirstWordFromLine(line)
39         if firstWord in firstWordTable:
40                 line = firstWordTable[ firstWord ]
41         gcodec.addLineAndNewlineIfNecessary( line, output )
42
43
44 class ScalableVectorGraphicsRepository:
45         "A class to handle the export settings."
46         def __init__(self):
47                 "Set the default settings, execute title & settings fileName."
48                 skeinforge_profile.addListsToCraftTypeRepository(
49                         'skeinforge_application.skeinforge_plugins.analyze_plugins.export_canvas_plugins.scalable_vector_graphics.html', self)
50                 self.fileExtension = settings.StringSetting().getFromValue('File Extension:', self, '')
51                 self.svgViewer = settings.StringSetting().getFromValue('SVG Viewer:', self, 'webbrowser')
52
53         def addCanvasLineToOutput( self, canvasLinesOutput, objectIDNumber ):
54                 "Add the canvas line to the output."
55                 coordinates = self.canvas.coords( objectIDNumber )
56                 xBegin = coordinates[0] - self.boxW
57                 xEnd = coordinates[2] - self.boxW
58                 yBegin = coordinates[1] - self.boxN
59                 yEnd = coordinates[3] - self.boxN
60                 west = self.boxW
61                 color = self.canvas.itemcget( objectIDNumber, 'fill')
62                 width = self.canvas.itemcget( objectIDNumber, 'width')
63                 line = '<line x1="%s" y1="%s" x2="%s" y2="%s" stroke="%s" stroke-width="%spx"/>\n' % ( xBegin, yBegin, xEnd, yEnd, color, width )
64                 canvasLinesOutput.write(line + '\n')
65
66         def execute(self):
67                 "Export the canvas as an svg file."
68                 svgFileName = archive.getFilePathWithUnderscoredBasename( self.fileName, self.suffix )
69                 boundingBox = self.canvas.bbox( settings.Tkinter.ALL ) # tuple (w, n, e, s)
70                 self.boxW = boundingBox[0]
71                 self.boxN = boundingBox[1]
72                 boxWidth = boundingBox[2] - self.boxW
73                 boxHeight = boundingBox[3] - self.boxN
74                 print('Exported svg file saved as ' + svgFileName )
75                 svgTemplateText = archive.getFileText(archive.getTemplatesPath('canvas_template.svg'))
76                 output = cStringIO.StringIO()
77                 lines = archive.getTextLines( svgTemplateText )
78                 firstWordTable = {}
79                 firstWordTable['height="999px"'] = '            height="%spx"' % int( round( boxHeight ) )
80                 firstWordTable['<!--replaceLineWith_coloredLines-->'] = self.getCanvasLinesOutput()
81                 firstWordTable['replaceLineWithTitle'] = archive.getSummarizedFileName( self.fileName )
82                 firstWordTable['width="999px"'] = '             width="%spx"' % int( round( boxWidth ) )
83                 for line in lines:
84                         parseLineReplace( firstWordTable, line, output )
85                 archive.writeFileText( svgFileName, output.getvalue() )
86                 fileExtension = self.fileExtension.value
87                 svgViewer = self.svgViewer.value
88                 if svgViewer == '':
89                         return
90                 if svgViewer == 'webbrowser':
91                         settings.openWebPage( svgFileName )
92                         return
93                 svgFilePath = '"' + os.path.normpath( svgFileName ) + '"' # " to send in file name with spaces
94                 shellCommand = svgViewer
95                 print('')
96                 if fileExtension == '':
97                         shellCommand += ' ' + svgFilePath
98                         print('Sending the shell command:')
99                         print(shellCommand)
100                         commandResult = os.system(shellCommand)
101                         if commandResult != 0:
102                                 print('It may be that the system could not find the %s program.' % svgViewer )
103                                 print('If so, try installing the %s program or look for another svg viewer, like Netscape which can be found at:' % svgViewer )
104                                 print('http://www.netscape.org/')
105                         return
106                 shellCommand += ' ' + archive.getFilePathWithUnderscoredBasename( svgFilePath, '.' + fileExtension + '"')
107                 print('Sending the shell command:')
108                 print(shellCommand)
109                 commandResult = os.system(shellCommand)
110                 if commandResult != 0:
111                         print('The %s program could not convert the svg to the %s file format.' % ( svgViewer, fileExtension ) )
112                         print('Try installing the %s program or look for another one, like Image Magick which can be found at:' % svgViewer )
113                         print('http://www.imagemagick.org/script/index.php')
114
115         def getCanvasLinesOutput(self):
116                 "Add the canvas line to the output."
117                 canvasLinesOutput = cStringIO.StringIO()
118                 objectIDNumbers = self.canvas.find_all()
119                 for objectIDNumber in objectIDNumbers:
120                         if self.canvas.type( objectIDNumber ) == 'line':
121                                 self.addCanvasLineToOutput( canvasLinesOutput, objectIDNumber )
122                 return canvasLinesOutput.getvalue()
123
124         def setCanvasFileNameSuffix( self, canvas, fileName, suffix ):
125                 "Set the canvas and initialize the execute title."
126                 self.canvas = canvas
127                 self.executeTitle = 'Convert to Scalable Vector Graphics'
128                 self.fileName = fileName
129                 self.suffix = suffix + '.svg'
130
131
132 def main():
133         "Display the file or directory dialog."
134         settings.startMainLoopFromConstructor(getNewRepository())
135
136 if __name__ == "__main__":
137         main()