mirror of https://github.com/rusefi/RomRaider.git
369 lines
16 KiB
Java
369 lines
16 KiB
Java
/*
|
|
* RomRaider Open-Source Tuning, Logging and Reflashing
|
|
* Copyright (C) 2006-2022 RomRaider.com
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation; either version 2 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License along
|
|
* with this program; if not, write to the Free Software Foundation, Inc.,
|
|
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
|
*/
|
|
|
|
package com.romraider.swing;
|
|
|
|
import java.awt.*;
|
|
import java.awt.event.ActionEvent;
|
|
import java.awt.event.ActionListener;
|
|
import java.io.File;
|
|
import java.io.FileInputStream;
|
|
import java.io.FileNotFoundException;
|
|
import java.io.IOException;
|
|
import java.text.MessageFormat;
|
|
import java.util.Properties;
|
|
import java.util.ResourceBundle;
|
|
import java.util.Scanner;
|
|
import java.util.Vector;
|
|
|
|
import javax.swing.*;
|
|
|
|
import com.romraider.Settings;
|
|
import com.romraider.editor.ecu.ECUEditorManager;
|
|
import com.romraider.util.ResourceUtil;
|
|
import com.romraider.util.SettingsManager;
|
|
import com.romraider.xml.ConversionLayer.ConversionLayer;
|
|
import com.romraider.xml.ConversionLayer.ConversionLayerFactory;
|
|
|
|
public class DefinitionManager extends javax.swing.JFrame implements ActionListener {
|
|
|
|
private static final long serialVersionUID = -3920843496218196737L;
|
|
private static final ResourceBundle rb = new ResourceUtil().getBundle(
|
|
DefinitionManager.class.getName());
|
|
public static int MOVE_UP = 0;
|
|
public static int MOVE_DOWN = 1;
|
|
|
|
Vector<String> fileNames;
|
|
|
|
public DefinitionManager() {
|
|
this.setIconImage(ECUEditorManager.getECUEditor().getIconImage());
|
|
initComponents();
|
|
initSettings();
|
|
|
|
definitionList.setFont(new Font("Tahoma", Font.PLAIN, 11));
|
|
definitionList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
|
|
|
|
btnCancel.addActionListener(this);
|
|
btnSave.addActionListener(this);
|
|
btnAddDefinition.addActionListener(this);
|
|
btnRemoveDefinition.addActionListener(this);
|
|
btnMoveUp.addActionListener(this);
|
|
btnMoveDown.addActionListener(this);
|
|
btnApply.addActionListener(this);
|
|
btnUndo.addActionListener(this);
|
|
}
|
|
|
|
private void initSettings() {
|
|
// add definitions to list
|
|
Vector<File> definitionFiles = SettingsManager.getSettings().getEcuDefinitionFiles();
|
|
fileNames = new Vector<String>();
|
|
|
|
for (int i = 0; i < definitionFiles.size(); i++) {
|
|
fileNames.add(definitionFiles.get(i).getAbsolutePath());
|
|
}
|
|
|
|
updateListModel();
|
|
}
|
|
|
|
// <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents
|
|
private void initComponents() {
|
|
jScrollPane1 = new javax.swing.JScrollPane();
|
|
definitionList = new javax.swing.JList();
|
|
defLabel = new javax.swing.JLabel();
|
|
btnMoveUp = new javax.swing.JButton();
|
|
btnMoveDown = new javax.swing.JButton();
|
|
btnAddDefinition = new javax.swing.JButton();
|
|
btnRemoveDefinition = new javax.swing.JButton();
|
|
btnSave = new javax.swing.JButton();
|
|
btnCancel = new javax.swing.JButton();
|
|
btnApply = new javax.swing.JButton();
|
|
btnUndo = new javax.swing.JButton();
|
|
|
|
setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);
|
|
setTitle(rb.getString("TITLE"));
|
|
jScrollPane1.setViewportView(definitionList);
|
|
|
|
defLabel.setText(rb.getString("FILEPRIORITY"));
|
|
|
|
btnMoveUp.setText(rb.getString("MOVEUP"));
|
|
|
|
btnMoveDown.setText(rb.getString("MOVEDOWN"));
|
|
|
|
btnAddDefinition.setText(rb.getString("ADD"));
|
|
|
|
btnRemoveDefinition.setText(rb.getString("REMOVE"));
|
|
|
|
btnSave.setText(rb.getString("SAVE"));
|
|
|
|
btnCancel.setText(rb.getString("CANCEL"));
|
|
|
|
btnApply.setText(rb.getString("APPLY"));
|
|
|
|
btnUndo.setText(rb.getString("UNDO"));
|
|
|
|
GroupLayout layout = new GroupLayout(getContentPane());
|
|
getContentPane().setLayout(layout);
|
|
layout.setHorizontalGroup(
|
|
layout.createParallelGroup(GroupLayout.Alignment.LEADING)
|
|
.addGroup(layout.createSequentialGroup()
|
|
.addContainerGap()
|
|
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.LEADING)
|
|
.addComponent(jScrollPane1, GroupLayout.DEFAULT_SIZE, 448, Short.MAX_VALUE)
|
|
.addGroup(GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
|
|
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.TRAILING)
|
|
.addGroup(layout.createSequentialGroup()
|
|
.addComponent(btnSave)
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
|
|
.addComponent(btnApply)
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
|
|
.addComponent(btnUndo)
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
|
|
.addComponent(btnCancel))
|
|
.addGroup(layout.createSequentialGroup()
|
|
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.LEADING)
|
|
.addComponent(defLabel)
|
|
.addGroup(layout.createSequentialGroup()
|
|
.addComponent(btnMoveDown)
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
|
|
.addComponent(btnMoveUp)))
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED, 80, Short.MAX_VALUE)
|
|
.addComponent(btnAddDefinition)))
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
|
|
.addComponent(btnRemoveDefinition)))
|
|
.addContainerGap())
|
|
);
|
|
|
|
layout.linkSize(SwingConstants.HORIZONTAL, new Component[]{btnAddDefinition, btnMoveDown, btnMoveUp, btnRemoveDefinition});
|
|
|
|
layout.setVerticalGroup(
|
|
layout.createParallelGroup(GroupLayout.Alignment.LEADING)
|
|
.addGroup(layout.createSequentialGroup()
|
|
.addContainerGap()
|
|
.addComponent(defLabel)
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
|
|
.addComponent(jScrollPane1, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
|
|
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.BASELINE)
|
|
.addComponent(btnMoveUp)
|
|
.addComponent(btnMoveDown)
|
|
.addComponent(btnRemoveDefinition, GroupLayout.PREFERRED_SIZE, 23, GroupLayout.PREFERRED_SIZE)
|
|
.addComponent(btnAddDefinition))
|
|
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
|
|
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.BASELINE)
|
|
.addComponent(btnSave)
|
|
.addComponent(btnApply)
|
|
.addComponent(btnUndo)
|
|
.addComponent(btnCancel))
|
|
.addContainerGap(GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
|
|
);
|
|
pack();
|
|
}// </editor-fold>//GEN-END:initComponents
|
|
|
|
@Override
|
|
public void actionPerformed(ActionEvent e) {
|
|
if (e.getSource() == btnCancel) {
|
|
dispose();
|
|
|
|
} else if (e.getSource() == btnSave) {
|
|
saveSettings();
|
|
dispose();
|
|
|
|
} else if (e.getSource() == btnApply) {
|
|
saveSettings();
|
|
|
|
} else if (e.getSource() == btnMoveUp) {
|
|
moveSelection(MOVE_UP);
|
|
|
|
} else if (e.getSource() == btnMoveDown) {
|
|
moveSelection(MOVE_DOWN);
|
|
|
|
} else if (e.getSource() == btnAddDefinition) {
|
|
addFile();
|
|
|
|
} else if (e.getSource() == btnRemoveDefinition) {
|
|
removeSelection();
|
|
|
|
} else if (e.getSource() == btnUndo) {
|
|
initSettings();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
public void saveSettings() {
|
|
Vector<File> output = new Vector<File>();
|
|
|
|
// create file vector
|
|
for (int i = 0; i < fileNames.size(); i++) {
|
|
output.add(new File(fileNames.get(i)));
|
|
}
|
|
|
|
// save
|
|
SettingsManager.getSettings().setEcuDefinitionFiles(output);
|
|
}
|
|
|
|
public void addFile() {
|
|
final Settings settings = SettingsManager.getSettings();
|
|
final JFileChooser fc = new JFileChooser(settings.getLastDefinitionDir());
|
|
fc.setMultiSelectionEnabled(true);
|
|
fc.setFileFilter(new DefinitionFilter());
|
|
|
|
if (fc.showOpenDialog(this) == JFileChooser.APPROVE_OPTION) {
|
|
for (File f : fc.getSelectedFiles()) {
|
|
boolean alreadyAdded = false;
|
|
|
|
//Check if it already exists in the list
|
|
for (String path : fileNames) {
|
|
if (path.equalsIgnoreCase(f.getAbsolutePath())) {
|
|
alreadyAdded = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (!alreadyAdded) {
|
|
//If its a file that needs to be converted sometimes a warning
|
|
//should be displayed to the user
|
|
if (ConversionLayerFactory.requiresConversionLayer(f)) {
|
|
ConversionLayer layer = ConversionLayerFactory.getConversionLayerForFile(f);
|
|
|
|
if (layer.getDefinitionPickerInfo() != null) {
|
|
JOptionPane.showMessageDialog(null, layer.getDefinitionPickerInfo(),
|
|
rb.getString("CONVERSIONTITLE"), JOptionPane.WARNING_MESSAGE);
|
|
}
|
|
}
|
|
}
|
|
else {
|
|
continue;
|
|
}
|
|
|
|
// Try to determine if the selected file is valid, refuse to
|
|
// add invalid types.
|
|
// File types and search sequences are loaded from a properties file.
|
|
final Properties props = loadSequences();
|
|
if (props.size() > 0) {
|
|
String fileType = "RomRaider";
|
|
boolean breakSearch = false;
|
|
try {
|
|
final Scanner scan = new Scanner(f);
|
|
// Scan the file looking for invalid string sequences,
|
|
// the value of a properties file key.
|
|
while(scan.hasNext()) {
|
|
breakSearch = false;
|
|
final String line = scan.nextLine().toLowerCase().toString();
|
|
for (Object key : props.keySet()) {
|
|
if (line.contains(props.getProperty((String) key))) {
|
|
fileType = (String) key;
|
|
breakSearch = true;
|
|
break;
|
|
}
|
|
}
|
|
if (breakSearch) break;
|
|
}
|
|
scan.close();
|
|
|
|
} catch (FileNotFoundException e) {
|
|
// Since the user selected it, it should be found.
|
|
e.printStackTrace();
|
|
}
|
|
if (!fileType.equalsIgnoreCase("RomRaider")) {
|
|
JOptionPane.showMessageDialog(this, MessageFormat.format(
|
|
rb.getString("INVALIDMSG"), fileType, f.getName()),
|
|
rb.getString("INVALIDFILE"),
|
|
JOptionPane.WARNING_MESSAGE);
|
|
continue;
|
|
}
|
|
}
|
|
fileNames.add(f.getAbsolutePath());
|
|
|
|
settings.setLastDefinitionDir(f.getParentFile());
|
|
}
|
|
|
|
updateListModel();
|
|
}
|
|
}
|
|
|
|
public void moveSelection(int direction) {
|
|
int selectedIndex = definitionList.getSelectedIndex();
|
|
String fileName = fileNames.get(selectedIndex);
|
|
|
|
if (direction == MOVE_UP && selectedIndex > 0) {
|
|
fileNames.remove(selectedIndex);
|
|
fileNames.add(--selectedIndex, fileName);
|
|
|
|
} else if (direction == MOVE_DOWN && selectedIndex < definitionList.getModel().getSize()) {
|
|
fileNames.remove(selectedIndex);
|
|
fileNames.add(++selectedIndex, fileName);
|
|
|
|
}
|
|
updateListModel();
|
|
definitionList.setSelectedIndex(selectedIndex);
|
|
}
|
|
|
|
public void removeSelection() {
|
|
int index = definitionList.getSelectedIndex();
|
|
if (index < 0) return;
|
|
fileNames.remove(index);
|
|
updateListModel();
|
|
|
|
}
|
|
|
|
public void updateListModel() {
|
|
definitionList.setListData(fileNames);
|
|
}
|
|
|
|
// Variables declaration - do not modify//GEN-BEGIN:variables
|
|
private javax.swing.JButton btnAddDefinition;
|
|
private javax.swing.JButton btnApply;
|
|
private javax.swing.JButton btnCancel;
|
|
private javax.swing.JButton btnMoveDown;
|
|
private javax.swing.JButton btnMoveUp;
|
|
private javax.swing.JButton btnRemoveDefinition;
|
|
private javax.swing.JButton btnSave;
|
|
private javax.swing.JButton btnUndo;
|
|
private javax.swing.JLabel defLabel;
|
|
private javax.swing.JList definitionList;
|
|
private javax.swing.JScrollPane jScrollPane1;
|
|
// End of variables declaration//GEN-END:variables
|
|
|
|
/**
|
|
* Load String search sequences from a user customized properties file.
|
|
* The file will populate a search list if it is present.
|
|
* String search Sequences in the file are in type=sequence sets.
|
|
* @exception FileNotFoundException if the directory or file is not present
|
|
* @exception IOException if there's some kind of IO error
|
|
*/
|
|
private Properties loadSequences() {
|
|
final Properties sequences = new Properties();
|
|
try {
|
|
final FileInputStream propFile = new FileInputStream("./customize/nameSequences.properties");
|
|
sequences.load(propFile);
|
|
propFile.close();
|
|
} catch (FileNotFoundException e) {
|
|
JOptionPane.showMessageDialog(null, e.getLocalizedMessage(),
|
|
"FileNotFoundException",
|
|
JOptionPane.ERROR_MESSAGE);
|
|
} catch (IOException e) {
|
|
JOptionPane.showMessageDialog(null, e.getLocalizedMessage(),
|
|
"IOException",
|
|
JOptionPane.ERROR_MESSAGE);
|
|
}
|
|
return sequences;
|
|
}
|
|
}
|