package com.le.formseditor.model;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.nio.charset.Charset;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.attribute.FileTime;
import java.util.ArrayList;
import java.util.prefs.Preferences;
import javax.swing.JComponent;
import javax.swing.JFileChooser;
import javax.swing.JOptionPane;
import com.le.formseditor.gui.FormsFrame;
import com.le.formseditor.gui.MyElement;
/**
* Model for handling the file-operations
*
* @author Simon Wirth
*
*/
public class FileModel {
/** the path-object pointing to the list-file */
private static Path path;
/** a list holding all strings from the list-file */
private ArrayList<String> list;
/** for caching purposes */
private FileTime lastModified;
/** a file chooser */
public static JFileChooser fc = new JFileChooser();
/** preferences */
private static Preferences prefs;
/** holding the last error message */
public static String errorMsg = "none";
/** holding the name of the latest used i.e. loaded/saved file*/
public static String fileName = " - new File";
/** the last opened/saved file */
private static File lastFile = null;
/**
* the model-constructor.
*/
public FileModel() {
File file = null;
prefs = Preferences.userRoot().node("FormsEditor");
String listFile = prefs.get("listFile", null);
boolean askForFile = false;
if(listFile == null)
askForFile = true;
else
file = new File(listFile);
if(file == null || !file.exists())
askForFile = true;
if(askForFile) {
JOptionPane.showMessageDialog(null,
"Since this is the first start you have to choose a List-File first.",
"Choose List-File", JOptionPane.INFORMATION_MESSAGE);
boolean success = changeListFile();
if(!success) {
JOptionPane
.showMessageDialog(
null,
"You canceled the selection-dialog.\nThe Forms-Editor will be closed now.",
"Closing Forms-Editor", JOptionPane.WARNING_MESSAGE);
System.exit(0);
}
} else {
path = file.toPath();
}
}
/**
* method for reading in the file
*
* @return true if the file was successfully read,<br>
* flase otherwise.
*/
public boolean readFile() {
try {
list = (ArrayList<String>) Files.readAllLines(path,
Charset.forName("US-ASCII"));
lastModified = Files.getLastModifiedTime(path);
} catch (IOException e) {
errorMsg = e.getMessage();
return false;
}
return true;
}
/**
* getter for the value-list
*
* @param type the list-type
* @return a list of values from the list-file
*/
//TODO use type
public ArrayList<String> getList(Type type) {
if (list == null)
readFile();
try{
if (!(lastModified.equals(Files.getLastModifiedTime(path)))) {
readFile();
} }
catch (IOException e) {
errorMsg = e.getMessage();
return null;
}
return list;
}
/**
* getter for the value-list as array
*
* @param type the list-type
* @return the value-list as array
*/
public String[] getArray(Type type) {
ArrayList<String> list = getList(type);
return list.toArray(new String[list.size()]);
}
/**
* method for changing the list-file
*
* @return if it was successful
*/
public static boolean changeListFile() {
File file;
int returnVal = fc.showOpenDialog(null);
if (returnVal == JFileChooser.APPROVE_OPTION) {
file = fc.getSelectedFile();
} else {
errorMsg = "Selection aborted!";
return false;
}
if (!file.exists()) {
errorMsg = "File" + file.getAbsolutePath() + " doesn't exist!";
// System.err.println("File" + file.getAbsolutePath() + " doesn't exist!");
return false;
} else if (!file.canRead()) {
errorMsg = "Can't read file" + file.getAbsolutePath();
// System.err.println("Can't read file" + file.getAbsolutePath());
return false;
}
path = file.toPath();
prefs.put("listFile", file.getAbsolutePath());
return true;
}
/**
* method for writing the existing form to a file
*
* @param components the components in the form
* @param sizes the size of the components
* @param formName the name of the form
* @param quicksave if the last used filename should be used again
* @return if writing was successful
*/
public static boolean writeFormToFile(JComponent[][] components, int[][][] sizes, String formName, boolean quicksave) {
if(formName == null || formName.length() == 0) {
errorMsg = "Dialog for form name aborted!";
return false;
} else
formName = formName.toUpperCase();
File f;
if(quicksave && lastFile != null){
f = lastFile;
} else {
int returnVal = fc.showSaveDialog(FormsFrame.getInstance());
if (returnVal == JFileChooser.APPROVE_OPTION) {
f = fc.getSelectedFile();
} else {
errorMsg = "Selection aborted!";
return false;
}
}
return writeFormToFile(components, sizes, formName, f);
}
/**
* method for writing the existing form to a file
*
* @param components the components in the form
* @param sizes the size of the components
* @param file the file
* @return if writing was successful
*/
private static boolean writeFormToFile(JComponent[][] components, int[][][] sizes, String formName, File f) {
try {
BufferedWriter bf = new BufferedWriter(new FileWriter(f));
ArrayList<String> tags = new ArrayList<String>();
String line = "";
bf.write("NAME=" + formName + ";TYPE=FORM;");
bf.newLine();
bf.write("LAYOUT=");
bf.newLine();
bf.write("+--------------------------------------------------------------------------------+,");
bf.newLine();
for (int i = 0; i < components.length; i++) {
line = "|";
for (int j = 0; j < components[i].length; j++) {
if (components[i][j] != null && components[i][j] instanceof MyElement) {
// for debugging
// System.out.println("found => row: " + i + " col: " + j
// + " comp: " + components[i][j].toString());
MyElement element = ((MyElement) components[i][j]);
tags.add(components[i][j].toString() + ",ROW(" + i + "),COL(" + j +");" );
String text = element.getType().equals(Type.TEXT) ? element.getText() : element.getTag();
line += text;
if (text.length() < sizes[i][j][0]) {
for (int k = text.length(); k < sizes[i][j][0]; k++) {
line += " ";
}
}
j += sizes[i][j][0] - 1;
}
else {
line += " ";
}
}
line += "|,";
bf.write(line);
bf.newLine();
}
bf.write("+--------------------------------------------------------------------------------+;");
bf.newLine();
bf.newLine();
bf.write("Tags:");
bf.newLine();
for (String tag : tags) {
bf.write(tag);
bf.newLine();
}
// ---
bf.flush();
bf.close();
System.out.println("--- Saving to File " + f.getAbsolutePath()
+ " completed. Components found: " + tags.size() + " ---");
fileName = " - " + f.getName();
lastFile = f;
return true;
} catch (IOException e) {
errorMsg = e.getMessage();
return false;
}
}
/**
* method for load a form from a file
* @return if reading was successful
*/
public static boolean loadFormFromFile(FormsModel mm) {
File f;
int returnVal = fc.showOpenDialog(FormsFrame.getInstance());
if (returnVal == JFileChooser.APPROVE_OPTION) {
f = fc.getSelectedFile();
} else {
errorMsg = "Selection aborted!";
return false;
}
try {
ArrayList<String> lines = (ArrayList<String>) Files.readAllLines( f.toPath(), Charset.forName("US-ASCII"));
boolean farEnough = false;
int count = 0;
for (String line : lines) {
if (farEnough) {
// parse a line to a component and insert it
boolean success = mm.insertNewComponent(line);
if (success)
count++;
else
break;
}
if (line.startsWith("Tags:")) {
farEnough = true;
mm.clearForm();
}
}
System.out.println("--- Reading from File " + f.getAbsolutePath()
+ " completed. Components inserted: " + count + " ---");
fileName = " - " + f.getName();
lastFile = f;
return true;
} catch (IOException e) {
errorMsg = e.getMessage();
return false;
}
}
/**
* reset for new File
*/
public static void newFile() {
fileName = " - new File";
lastFile = null;
}
}