I try to create a simple plugin to load a sif file. I took the skeleton simple plugin example and I made a few changes. But the file don’t be loaded. where I’m wrong?
I put the test.sif in the same plugin folder. The xml file is loaded into the menu
#!/usr/bin/env python
import os
import sys
import codecs
def process(filename):
template_filename = os.path.join(os.path.dirname(sys.argv[0]), 'test.sif')
template_f = codecs.open(template_filename, 'r', encoding='utf-8')
template_contents = template_f.readlines()
template_f.close()
# Read the input file
inputfile_f = codecs.open(filename, 'r', encoding='utf-8')
inputfile_contents = inputfile_f.readlines()
inputfile_f.close()
# Now write results to the same file
inputfile_f = open(filename, 'w', encoding='utf-8')
inputfile_f.close()
I don’t see you calling process(sys.argv[1]) after having declared your process function… and it is thus never executed.
Moreover I’d recommend
using xml parsing instead of plain text… that will ensure the proper formatting of the resulting document.
using a logging mechanism, to get feedback on how your plugin behaved if it encounters a problem
Below is code that works for me with these 2 elements, to copy elements of a template into the current synfig file.
#!/usr/bin/env python
import os
import sys
import xml.etree.ElementTree as ET # common Python xml implementation
import logging
def process(filename):
# setup logging
log = os.path.join(os.path.dirname(sys.argv[0]), 'plugin.log')
logging.basicConfig(filename='plugin.log',level=logging.DEBUG)
logging.info('running plugin "test"')
template_filename = os.path.join(os.path.dirname(sys.argv[0]), 'test.sif')
# read template sif file as xml (TODO consider SAX 'parse' instead, for very big xml files)
logging.debug('loading template file %s'%template_filename)
tree = ET.parse(template_filename)
template_canvas = tree.getroot()
# Read the input file
logging.debug('loading current file %s'%filename)
tree = ET.parse(filename)
canvas = tree.getroot()
# copy canvas/defs/* and canvas/layer from template to file
for layer_t in template_canvas.findall("./layer"):
logging.debug('copying layer %s from template to file'%layer_t.get('desc'))
canvas.append(layer_t)
defs_nodes_t = template_canvas.findall("./defs/*")
if defs_nodes_t:
defs = canvas.find("./defs")
if defs is None:
logging.debug('creating node for exported values in file')
defs = ET.Element('defs')
canvas.insert(1,k) # insert <defs /> after <name>.
defs.extend(defs_nodes_t) # append all template defs children to file defs
logging.debug('added %d exported values in file'%len(defs_nodes_t))
# write modified xml tree to the same sif file
tree.write(filename, encoding="UTF-8", xml_declaration=True)
logging.info('call to plugin "test" successfully completed. Synfig will now reload your file.')
#run process() on call
if len(sys.argv) < 2:
sys.exit("Missing synfig filename as argument")
else:
sifin_filename = sys.argv[1]
#make sure the plugin is called on sif, and not sifz
if not (os.path.splitext(sifin_filename)[-2].lower().endswith('.sif') or os.path.splitext(sifin_filename)[-1].lower().endswith('.sif')):
sys.exit("Synfig plug-ins only work on sif file, not sifz.\n\nPlease save your Synfig project (%s) as sif, then try again." % sifin_filename)
process(sifin_filename)
I would add additional arguments to enable a more customized use of the plugin from the command line as well… If interested see the code of plugin to import keyframes from Audacity. You could, a.o., add the template name as a parameter.