Files
2026-06-17 14:00:51 +02:00

134 lines
4.8 KiB
Python

# ExportLogixNG.py -- Export LogixNG definitions
# The details are at https://jmri.org/help/en/html/tools/logixng/ExportLogixNG.shtml
# The LogixNG content in the PanelPro xml data file looks simple but it is internally complex.
# The default is to use automatic system names. The format is xxxx:AUTO:nnnn. The xxxx is one of
# a couple dozen values. The nnnn is a sequential number. Since the system names are only unique
# within a xml data file, copying LogixNG content to another xml data file is impossible.
# The export process changes the system names to be unique. The AUTO keyword is replaced by a user
# supplied keyword. For example using XYZ, the result is that xxxx:AUTO:nnnn becomes xxxx$XYZ:nnnn.
# Notice that the first colon becomes a dollar character.
# The script has three prompts when started.
# 1 -- The input xml data file. If you want to export all of the LogixNG definitions, a current file
# can be used. If only some of the LogixNG definitions are to be exported, then some pre-processing
# is required. Except for the LogixNGs and/or Modules to be exported, the other LogixNGs, Modules,
# Tables and Global Variables need to be deleted. Also, the LogixNG clipboard should be emptied.
# After removing the other items, store the file with a new name. Select this file as the export
# input file.
# 2 -- The output xml data file. This file will be created or over written with no warnings. This
# is a PanelPro data file with the standard header and the LogixNG definitions. There are no other
# tables or panels. This file can be loaded after the normal data file. This results in adding the
# exported LogixNG definitions. This is a one time activity.
# 3 -- The alternate system name keyword.
# # # Warnings # # #
# The references in LogixNG definitions to other tables, such as sensors, turnouts, etc., are not
# changed. These will create errors if there are no matching entries in the normal tables.
# Any messages from the script will be on the JMRI system console.
# Author: Dave Sand, copyright 2024
# Part of the JMRI distribution.
import java
import jmri
from javax.swing import JFileChooser, JOptionPane
from javax.swing.filechooser import FileNameExtensionFilter
from org.slf4j import LoggerFactory
log = LoggerFactory.getLogger("jmri.jmrit.jython.exec.ExportLogixNG")
log.info('Run LogixNG Export v1.0')
inputFileName = None
outputFileName = None
newKeyword = None
header = True
logixNGs = False
lngItems = False
ready = True
lines = []
# Create a file chooser.
fc = JFileChooser(jmri.util.FileUtil.getUserFilesPath())
fc.setFileFilter(FileNameExtensionFilter("PanelPro XML Data File", ["xml"]));
fc.setFileSelectionMode(JFileChooser.FILES_AND_DIRECTORIES)
# Select a XML file to be exported.
fc.setDialogTitle('Select Input XML Data File')
ret = fc.showOpenDialog(None)
if ret == JFileChooser.APPROVE_OPTION:
inputFileName = fc.getSelectedFile().toString()
if ret is None: ready = False
# Select a XML file to be created/replaced.
fc.setDialogTitle('Select Output XML Data File')
ret = fc.showSaveDialog(None)
if ret == JFileChooser.APPROVE_OPTION:
outputFileName = fc.getSelectedFile().toString()
if ret is None: ready = False
# Select the keyword to replace AUTO
newKeyword = JOptionPane.showInputDialog(
None,
'Enter the replacement keyword for AUTO',
'',
JOptionPane.PLAIN_MESSAGE);
if not newKeyword.isalnum():
log.error('"{}" is an invalid keyword'.format(newKeyword))
ready = False
if ready:
# Process each input line and add the retained lines to the 'lines' list.
with open(inputFileName) as infile:
for line in infile:
if header:
lines.append(line)
if '</jmriversion>' in line:
header = False
# Handle LogixNGs list
if not logixNGs:
if '<LogixNGs' in line:
logixNGs = True
if logixNGs:
lines.append(line)
if '</LogixNGs>' in line:
logixNGs = False
continue
# Handle remaining lines
if not lngItems:
if '<LogixNG' in line:
lngItems = True
if lngItems:
lines.append(line)
if '</LogixNG' in line:
lngItems = False
# Write each line from the "lines" list to the output file, finish with the final xml line.
with open(outputFileName, 'w') as outfile:
for line in lines:
outfile.write(line.decode("utf-8", "replace").replace(':AUTO:', '$' + newKeyword + ':').encode("utf-8"))
outfile.write('</layout-config>\n')
log.info('Export completed, AUTO replaced by {}, file {} has been created'.format(newKeyword.encode("ascii", "replace"), outputFileName.encode("ascii", "replace")))
else:
log.warn('Export aborted due to incomplete input')