package com.it.loratek.sski.model;
import java.awt.BorderLayout;
import java.awt.Button;
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.geom.Point2D;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.imageio.ImageIO;
import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.BorderFactory;
import javax.swing.BoxLayout;
import javax.swing.Icon;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JColorChooser;
import javax.swing.JDialog;
import javax.swing.JFileChooser;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JRadioButton;
import javax.swing.JScrollPane;
import javax.swing.JSplitPane;
import javax.swing.JTabbedPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.JToolBar;
import javax.swing.UIManager;
import javax.swing.border.LineBorder;
import javax.swing.table.AbstractTableModel;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.JTableHeader;
import javax.swing.table.TableCellRenderer;
import javax.xml.parsers.ParserConfigurationException;
import org.jfree.chart.ChartPanel;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.plot.CategoryPlot;
import org.jfree.chart.renderer.category.BarRenderer;
import org.jfree.data.category.CategoryDataset;
import org.jfree.data.category.DefaultCategoryDataset;
import org.jfree.data.xy.XYDataset;
import org.xml.sax.SAXException;
import com.it.loratek.sski.controller.DataSetCreator;
import com.it.loratek.sski.controller.InputParser;
import com.it.loratek.sski.model.graph.DensityChartCreator;
import com.it.loratek.sski.model.graph.DirectionChartCreator;
import com.it.loratek.sski.model.graph.ProvenienzaChartCreator;
import com.it.loratek.sski.model.graph.SpeedMaxChartCreator;
import com.it.loratek.sski.model.graph.SpeedPercentChartCreator;
import com.it.loratek.sski.parser.Skier;
import com.it.loratek.sski.parser.SkierSaxParser;
import com.it.loratek.sski.parser.TimeToken;
import com.it.loratek.sski.view.ClickPolygon;
import com.it.loratek.sski.view.TableButton;
import com.it.loratek.sski.view.panels.EditorPanel;
import com.it.loratek.sski.view.panels.StatPanel;
import com.itextpdf.awt.DefaultFontMapper;
import com.itextpdf.text.Document;
import com.itextpdf.text.pdf.PdfContentByte;
import com.itextpdf.text.pdf.PdfTemplate;
import com.itextpdf.text.pdf.PdfWriter;
import com.lowagie.text.Image;
@SuppressWarnings("serial")
public abstract class AbstractFrame extends JFrame {
/**
*
*/
protected static final long serialVersionUID = -120650113677607513L;
protected static final String GRAPH_CONTAINER_NAME = "graphScroll";
protected static final String EDIT_CONTAINER_NAME = "editContainer";
protected static final String ERRORE_MSG = "Errore..";
private static final Color internColor = new Color(251, 247, 128);
protected Map<Integer, Skier> skiersMap;
protected SkierSaxParser parser;
protected boolean XML_PARSED = false;
protected boolean FILE_OPENED = false;
protected Button up = new Button("+");;
protected Button down = new Button("-");
protected Button upX = new Button("+");;
protected Button downX = new Button("-");
protected Button upY = new Button("+");;
protected Button downY = new Button("-");
protected MyToolBar editToolbar;
protected JTextField ticknesTxt = new JTextField(4);
protected JTextField xTraslTxt = new JTextField(4);
protected JTextField yTraslTxt = new JTextField(4);
/* panels */
protected JSplitPane mainSplitPane;
protected JSplitPane leftPanel;
protected EditorPanel editPanel;
protected JTabbedPane rightTabPanel;
protected JTabbedPane leftTabPanel;
protected JPanel opPanel;
protected MatchingsPanel matchPanel;
protected StatPanel statPanel;
protected TimePanel timePanel;
protected JScrollPane graphScoll;
protected OutputPanel outputPanel;
/* container panels */
protected JPanel editContainer;
protected JPanel graphContainer;
protected JTable matchTable;
protected JTable timeTable;
protected JCheckBox modeSelectionChk;
protected List<MatchData> matchList;
protected List<MatchData> graphMatchList;
protected boolean DIREZIONI_CONFERMATE = false;
private boolean SELECTION_ENABLED = false;
protected int MATCH_ID = 0;
protected int MODE = 1;
private boolean OUTPUT_GENERATO = false;
public AbstractFrame() {
super("SecurSki Manager");
}
private ArrayList<Integer> enters;
private ArrayList<Integer> exits;
private static final String SORRY = "Errore";
class ClearDirectionsAction extends AbstractAction {
public ClearDirectionsAction() {
super("Azzera direzioni");
}
@Override
public void actionPerformed(ActionEvent e) {
for(ClickPolygon pol : editPanel.getPolygonList()){
pol.setEnter(false);
pol.setExit(false);
pol.setOn(false);
pol.setActive(false);
pol.setColor(internColor);
enters = new ArrayList<Integer>();
exits = new ArrayList<Integer>();
editPanel.repaint();
DIREZIONI_CONFERMATE = false;
}
}
}
class ConfirmDirectionsAction extends AbstractAction {
public ConfirmDirectionsAction() {
super("Conferma direzioni");
}
@Override
public void actionPerformed(ActionEvent e) {
if (!XML_PARSED) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"XML non parsato.", SORRY, JOptionPane.ERROR_MESSAGE);
return;
}
enters = new ArrayList<Integer>();
exits = new ArrayList<Integer>();
for (ClickPolygon pol : editPanel.getPolygonList()) {
if (pol.isEnter())
enters.add(pol.getPolID());
else if (pol.isExit())
exits.add(pol.getPolID());
}
if (enters.size() < 1) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"Selezionare almeno un'entrata", SORRY,
JOptionPane.ERROR_MESSAGE);
return;
}
if (exits.size() < 1) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"Selezionare almeno un'uscita", SORRY,
JOptionPane.ERROR_MESSAGE);
return;
}
DIREZIONI_CONFERMATE = true;
}
}
protected class DrawSingleSkierTrackAction extends AbstractAction {
public DrawSingleSkierTrackAction() {
super("Traiettoria singolo");
}
public void actionPerformed(ActionEvent e) {
if (XML_PARSED) {
int id = 0;
String idString = JOptionPane
.showInputDialog("Inserire numero ID");
if (!"".equals(idString) && idString != null) {
try {
id = Integer.parseInt(idString);
} catch (NumberFormatException ex) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"Numero errato.", SORRY,
JOptionPane.ERROR_MESSAGE);
}
if (!skiersMap.keySet().contains(id)) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"Nessun dato per ID: " + id, SORRY,
JOptionPane.ERROR_MESSAGE);
} else {
editPanel.drawSingleTrack(null, id, null);
editPanel.setTRACKS(true);
}
} else
JOptionPane.showMessageDialog(AbstractFrame.this,
"Inserire l'ID!", ERRORE_MSG,
JOptionPane.ERROR_MESSAGE);
} else
JOptionPane.showMessageDialog(AbstractFrame.this,
"XML non parsato.", ERRORE_MSG,
JOptionPane.ERROR_MESSAGE);
}
}
public class ImagePanel extends JPanel {
private BufferedImage image;
public ImagePanel(String file, String file2) {
try {
image = ImageIO.read(new File(file));
} catch (IOException ex) {
}
}
@Override
public void paintComponent(Graphics g) {
g.drawImage(image, 0, 0, null);
}
}
protected class OpenFileAction extends AbstractAction {
public OpenFileAction() {
super("Apri..");
}
public void actionPerformed(ActionEvent e) {
leftTabPanel.setEnabled(true);
JFileChooser filechooser = new JFileChooser();
// TODO scommentare
if (filechooser.showOpenDialog(AbstractFrame.this) != JFileChooser.APPROVE_OPTION) {
return;
}
String path = filechooser.getSelectedFile().getAbsolutePath();
InputParser parser = new InputParser();
parser.parse(path);
if (!parser.isOk()) {
JOptionPane.showMessageDialog(
AbstractFrame.this,
"Errore nel parsing del file di input. "
+ parser.getMessage(), ERRORE_MSG,
JOptionPane.ERROR_MESSAGE);
return;
}
editPanel.setNp(parser.getN());
editPanel.setXp(parser.getX());
editPanel.setYp(parser.getY());
editPanel.setPreferredSize(new Dimension(1200, 800));
editPanel.setSize(new Dimension(1200, 800));
XML_PARSED = false;
FILE_OPENED = true;
editPanel.init();
revalidate();
pack();
}
}
protected class ParseXMLAction extends AbstractAction {
public ParseXMLAction() {
super("Parsa XML");
}
public void actionPerformed(ActionEvent e) {
if (FILE_OPENED) {
JFileChooser filechooser = new JFileChooser();
// TODO:scommentare
if (filechooser.showOpenDialog(AbstractFrame.this) != JFileChooser.APPROVE_OPTION) {
return;
}
// anche qui
String path = filechooser.getSelectedFile().getAbsolutePath();
String dist = JOptionPane
.showInputDialog("Inserire distanza minima [40 default]");
int d = 0;
if (dist != null && !"".equals(dist))
d = Integer.parseInt(dist);
parser = new SkierSaxParser(path, d);
try {
skiersMap = parser.getData();
// skiersList = parser.getDataList();
} catch (SAXException e1) {
JOptionPane.showMessageDialog(AbstractFrame.this,
e1.getMessage());
e1.printStackTrace();
return;
} catch (IOException e1) {
JOptionPane.showMessageDialog(AbstractFrame.this,
e1.getMessage());
e1.printStackTrace();
return;
} catch (ParserConfigurationException e1) {
JOptionPane.showMessageDialog(AbstractFrame.this,
e1.getMessage());
e1.printStackTrace();
return;
}
editPanel
.setSkiersList(new ArrayList<Skier>(skiersMap.values()));
JOptionPane.showMessageDialog(AbstractFrame.this,
"Eleborazione terminata.");
statPanel.setSkiersNumber(String.valueOf(skiersMap.size()));
XML_PARSED = true;
editPanel.setMap((HashMap<Integer, Skier>) skiersMap);
timePanel.updateTab(parser.getTimeTokenListList());
timePanel.setTableVisible();
} else
JOptionPane.showMessageDialog(AbstractFrame.this,
"Nessun file aperto.", ERRORE_MSG,
JOptionPane.ERROR_MESSAGE);
}
}
protected class DrawPointAction extends AbstractAction {
public DrawPointAction() {
super("Tutti i punti");
}
public void actionPerformed(ActionEvent e) {
if (XML_PARSED)
editPanel.drawAllPoints(null);
else
JOptionPane.showMessageDialog(AbstractFrame.this,
"XML non parsato.", ERRORE_MSG,
JOptionPane.ERROR_MESSAGE);
}
}
protected class DrawTracks extends AbstractAction {
public DrawTracks() {
super("Tutte le traiettorie");
}
public void actionPerformed(ActionEvent e) {
if (XML_PARSED)
editPanel.drawAllTracks(null);
else
JOptionPane.showMessageDialog(AbstractFrame.this,
"XML non parsato.", SORRY, JOptionPane.ERROR_MESSAGE);
}
}
protected class ClearAction extends AbstractAction {
public ClearAction() {
super("Cancella");
}
public void actionPerformed(ActionEvent e) {
if (FILE_OPENED) {
editPanel.clear();
}
}
}
protected class SelectEntranceAction extends AbstractAction {
public SelectEntranceAction() {
super("Select Entrance");
}
public void actionPerformed(ActionEvent e) {
editPanel.setSelectColor(Color.GREEN);
}
}
protected class SelectExitAction extends AbstractAction {
public SelectExitAction() {
super("Select Exit");
}
public void actionPerformed(ActionEvent e) {
editPanel.setSelectColor(Color.RED);
}
}
protected class QuitAction extends AbstractAction {
public QuitAction() {
super("Esci");
}
public void actionPerformed(ActionEvent e) {
int response = JOptionPane.showConfirmDialog(AbstractFrame.this,
"Chiudere?");
if (response == JOptionPane.YES_OPTION)
System.exit(0);
}
}
protected class DrawStartPoints extends AbstractAction {
Color color;
public DrawStartPoints() {
super("Tutti i punti di entrata");
}
public void actionPerformed(ActionEvent e) {
if (!XML_PARSED) {
JOptionPane
.showMessageDialog(AbstractFrame.this,
"XML non parsato.", "Errore",
JOptionPane.ERROR_MESSAGE);
return;
}
editPanel.drawStart(null);
}
}
protected class DrawEndPoints extends AbstractAction {
Color color;
public DrawEndPoints() {
super("Tutti i punti di uscita");
}
public void actionPerformed(ActionEvent e) {
if (!XML_PARSED) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"XML non parsato.", ERRORE_MSG,
JOptionPane.ERROR_MESSAGE);
return;
}
editPanel.drawEnd(null);
}
}
protected static class ColorIcon implements Icon {
Color color;
public ColorIcon(Color color) {
this.color = color;
}
public int getIconHeight() {
return 16;
}
public int getIconWidth() {
return 16;
}
public void paintIcon(Component c, Graphics g, int x, int y) {
g.setColor(color);
g.fillRect(x, y, 16, 16);
}
}
protected class Match extends AbstractAction {
public void actionPerformed(ActionEvent e) {
JDialog dialog = new JDialog(AbstractFrame.this);
dialog.setSize(new Dimension(400, 300));
dialog.setLayout(new FlowLayout(3));
JToolBar tool = new JToolBar(JToolBar.HORIZONTAL);
tool.add(new ChooseColor());
dialog.add(tool);
dialog.setVisible(true);
}
class ChooseColor extends AbstractAction {
ChooseColor() {
super("Scegli colore");
}
@Override
public void actionPerformed(ActionEvent e) {
Color c = JColorChooser.showDialog(AbstractFrame.this,
"Scegli colore", Color.BLACK);
if (c != null)
editPanel.setSelectColor(c);
}
}
}
protected class ChooseColor extends AbstractAction {
ChooseColor() {
super("Choose color");
}
@Override
public void actionPerformed(ActionEvent e) {
Color c = JColorChooser.showDialog(AbstractFrame.this,
"Scegli colore", Color.BLACK);
if (c != null)
editPanel.setSelectColor(c);
}
}
protected class TimePanel extends JPanel {
TimeTableModel model;
public void updateTab(ArrayList<TimeToken> list) {
model = new TimeTableModel(list);
int row = 0;
for (TimeToken q : list) {
for (int i = 0; i < 3; i++) {
model.setValueAt(q.getOrd(), row, 0);
model.setValueAt(q.getSkiers(), row, 1);
model.setValueAt(q.getMedSpeed(), row, 2);
}
row++;
}
timeTable.setModel(model);
// model.fireTableDataChanged();
}
JScrollPane pane;
public TimePanel() {
String data[][] = {};
String col[] = { "Settore di 5'", "Sciatori", "Velocit� media" };
DefaultTableModel temp = new DefaultTableModel(data, col);
timeTable = new JTable(temp);
JTableHeader header = timeTable.getTableHeader();
header.setBackground(Color.yellow);
setLayout(new BorderLayout());
pane = new JScrollPane(timeTable);
/* loratek logo panel */
}
public void setTableVisible() {
add(pane);
}
protected class TimeTableModel extends AbstractTableModel {
private List<TimeToken> list;
public TimeTableModel(List<TimeToken> list) {
this.list = list;
// setValueAt("numero", 0, 0);
// setValueAt("sciatori", 0, 1);
// setValueAt("velocit� media", 0, 2);
}
public int getColumnCount() {
return 3;
}
public int getRowCount() {
return list.size();
}
public String getColumnName(int col) {
if (col == 0)
return "Settore di 5'";
if (col == 1)
return "Sciatori";
if (col == 2)
return "Velocit� media";
return null;
}
public Object getValueAt(int row, int col) {
if (col == 0)
return list.get(row).getOrd() + 1;
if (col == 1)
return list.get(row).getSkiers();
if (col == 2)
return list.get(row).getMedSpeed();
return null;
}
public Class getColumnClass(int c) {
return getValueAt(0, c).getClass();
}
public void setValueAt(Object value, int row, int col) {
if (col == 0)
list.get(row).setOrd((Integer) value);
if (col == 1)
list.get(row).setSkiers((Integer) value);
if (col == 2)
list.get(row).setMedSpeed((Integer) value);
fireTableCellUpdated(row, col);
}
}
}
protected class MyToolBar extends JToolBar {
private BufferedImage image;
public MyToolBar() {
try {
image = ImageIO.read(new File("images/Logo_Securski2.png"));
} catch (IOException ex) {
}
}
@Override
public void paintComponent(Graphics g) {
super.paintComponents(g);
g.drawImage(image, getParent().getWidth() - 150, -8, null);
}
}
private void generatePDF(String filepath) {
com.itextpdf.text.Rectangle r = new com.itextpdf.text.Rectangle(0, 0,
graphContainer.getWidth(), graphContainer.getHeight());
Document document = new Document(r);
try {
PdfWriter writer;
writer = PdfWriter.getInstance(document, new FileOutputStream(
filepath));
document.open();
PdfContentByte cb = writer.getDirectContent();
PdfTemplate tp = cb.createTemplate(graphContainer.getWidth(),
graphContainer.getHeight());
Graphics2D g2d = tp.createGraphics(graphContainer.getWidth(),
graphContainer.getHeight(), new DefaultFontMapper());
graphContainer.addNotify();
graphContainer.validate();
graphContainer.paint(g2d);
g2d.dispose();
cb.addTemplate(tp, 0, 0);
} catch (Exception e) {
e.printStackTrace();
}
document.close();
}
protected class OutputPanel extends JPanel {
public OutputPanel() {
setLayout(new BorderLayout());
setPreferredSize(new Dimension(400, 400));
setSize(new Dimension(400, 400));
add(new ButtonsPanel(), BorderLayout.NORTH);
setName("outputPanel");
}
class SelectLabelPanel extends JPanel {
public SelectLabelPanel() {
setBackground(Color.WHITE);
setLayout(new FlowLayout());
JLabel label = new JLabel("Selezionare :");
label.setBackground(Color.WHITE);
add(label);
}
}
class RadioAreaPanel extends JPanel {
private JRadioButton radioEntrate;
private JRadioButton radioUscite;
private JLabel labEntr;
private JLabel labExt;
public RadioAreaPanel() {
setBackground(Color.WHITE);
setLayout(new BoxLayout(this, BoxLayout.Y_AXIS));
add(new RadioLabelEnter());
add(new RadioLabelExit());
}
class SelectEntrateAction extends AbstractAction {
@Override
public void actionPerformed(ActionEvent e) {
SELECTION_ENABLED = true;
radioUscite.setSelected(false);
labExt.setForeground(Color.BLACK);
labEntr.setForeground(Color.GREEN);
editPanel.setSelectColor(Color.GREEN);
editPanel.setEnter(true);
editPanel.setExit(false);
}
}
class SelectUsciteAction extends AbstractAction {
@Override
public void actionPerformed(ActionEvent e) {
SELECTION_ENABLED = true;
radioEntrate.setSelected(false);
labEntr.setForeground(Color.BLACK);
labExt.setForeground(Color.RED);
editPanel.setSelectColor(Color.RED);
editPanel.setExit(true);
editPanel.setEnter(false);
}
}
class RadioLabelEnter extends JPanel {
public RadioLabelEnter() {
setBackground(Color.WHITE);
setLayout(new FlowLayout(FlowLayout.LEFT));
radioEntrate = new JRadioButton(new SelectEntrateAction());
radioEntrate.setBackground(Color.WHITE);
add(radioEntrate);
labEntr = new JLabel("Entrate");
labEntr.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
SELECTION_ENABLED = true;
radioEntrate.setSelected(true);
radioUscite.setSelected(false);
labExt.setForeground(Color.BLACK);
labEntr.setForeground(Color.GREEN);
editPanel.setSelectColor(Color.GREEN);
editPanel.setEnter(true);
editPanel.setExit(false);
super.mouseClicked(e);
}
});
add(labEntr);
}
}
class RadioLabelExit extends JPanel {
public RadioLabelExit() {
setBackground(Color.WHITE);
setLayout(new FlowLayout(FlowLayout.LEFT));
radioUscite = new JRadioButton(new SelectUsciteAction());
radioUscite.setBackground(Color.WHITE);
add(radioUscite);
labExt = new JLabel("Uscite");
labExt.addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
SELECTION_ENABLED = true;
radioUscite.setSelected(true);
radioEntrate.setSelected(false);
labEntr.setForeground(Color.BLACK);
labExt.setForeground(Color.RED);
editPanel.setSelectColor(Color.RED);
editPanel.setExit(true);
editPanel.setEnter(false);
}
});
add(labExt);
}
}
}
// pannello pulsantiera match panel
public class ButtonsPanel extends JPanel {
public ButtonsPanel() {
setBackground(Color.WHITE);
setLayout(new BoxLayout(this, BoxLayout.Y_AXIS));
// setPreferredSize(new Dimension(200, 100));
JPanel p1 = new JPanel();
p1.setSize(200, 50);
p1.setBackground(Color.WHITE);
JPanel p3 = new JPanel();
p3.setLayout(new FlowLayout(FlowLayout.RIGHT));
p3.add(new JButton(new GenerateOutputAction()));
p3.add(new JButton(new GeneratePDFAction()));
JPanel p4 = new JPanel();
p4.setLayout(new FlowLayout(FlowLayout.LEFT));
p4.add(new JButton(new ClearDirectionsAction()));
p4.add(new JButton(new ConfirmDirectionsAction()));
JPanel space = new JPanel();
space.setBackground(Color.WHITE);
JPanel p5 = new JPanel();
p5.setLayout(new FlowLayout(FlowLayout.LEFT));
p5.add(new SelectLabelPanel());
p5.add(new RadioAreaPanel());
p1.setBackground(Color.WHITE);
p3.setBackground(Color.WHITE);
p4.setBackground(Color.WHITE);
p5.setBackground(Color.WHITE);
setBorder(new LineBorder(Color.GRAY));
add(p1);
add(p5);
add(p4);
add(space);
add(p3);
setSize(new Dimension(400, 200));
setPreferredSize(new Dimension(400, 200));
}
class InfoPanel extends JPanel {
public InfoPanel() {
setBackground(Color.WHITE);
setLayout(new BorderLayout());
ImagePanel toolbar = new ImagePanel(
"images/Logo_Securski2.png");
toolbar.setLayout(new FlowLayout(FlowLayout.LEFT));
toolbar.setSize(new Dimension(400, 40));
toolbar.setPreferredSize(new Dimension(400, 40));
toolbar.setLayout(new BoxLayout(toolbar, BoxLayout.X_AXIS));
add(toolbar, BorderLayout.NORTH);
setPreferredSize(new Dimension(400, 300));
setSize(new Dimension(400, 300));
}
public class ImagePanel extends JPanel {
private BufferedImage image;
public ImagePanel(String file) {
try {
image = ImageIO.read(new File(file));
} catch (IOException ex) {
}
}
@Override
public void paintComponent(Graphics g) {
g.drawImage(image, 0, 0, null);
}
}
}
class MyButton extends JButton {
public MyButton(Action action, String tooltip) {
super(action);
setToolTipText(tooltip);
// setPreferredSize(new Dimension(100, 20));
}
}
class GenerateOutputAction extends AbstractAction {
private static final int TOKEN_SIZE = 15000;
// numero di volte che ho stampato
int times = 1;
ChartPanel densityPanel;
ChartPanel speedPercPanel;
ChartPanel speedMaxPanel;
ChartPanel enterDirectionPanel;
ChartPanel exitDirectionPanel;
ArrayList<ChartPanel> listOfMatch;
public GenerateOutputAction() {
super("Genera grafici");
}
public void actionPerformed(ActionEvent e) {
if (!XML_PARSED) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"XML non parsato", SORRY,
JOptionPane.ERROR_MESSAGE);
return;
}
DataSetCreator datasetCreator = new DataSetCreator();
if (DIREZIONI_CONFERMATE) {
ArrayList<Skier> skiersList = editPanel.getSkiersList();
// prepare direction graph data
// per ogni MATCH prendo tutte le radioEntrate e calcolo
// per
// ognuna
// quanti escono dalle radioUscite
HashMap<Integer, ArrayList<Skier>> skierEntranceMap = new HashMap<Integer, ArrayList<Skier>>();
HashMap<Integer, ArrayList<Skier>> skierExitMap = new HashMap<Integer, ArrayList<Skier>>();
ArrayList<DirectionData> directions = new ArrayList<DirectionData>();
for (Integer intein : enters) {
DirectionData dd = new DirectionData(intein);
ArrayList<Skier> temp = new ArrayList<Skier>();
ArrayList<Skier> entrate = new ArrayList<Skier>();
ClickPolygon pEnter = editPanel.getPolygonMap()
.get(intein);
for (Skier s : skiersList) {
Point2D pN = pN(s.getPixmapX().get(0), s
.getPixmapY().get(0));
if (pEnter.contains(pN)) {
entrate.add(s);
temp.add(s);
}
}
skierEntranceMap.put(intein, entrate);
for (Integer inteout : exits) {
ExitDirectionData edd = new ExitDirectionData(
inteout);
ArrayList<Skier> uscite = new ArrayList<Skier>();
ArrayList<Skier> fnl = new ArrayList<Skier>();
ClickPolygon pExit = editPanel.getPolygonMap()
.get(inteout);
// conto per questo poligono quanti skiers
// escono
for (Skier s : skiersList) {
Point2D pN = pN(
s.getPixmapX().get(
s.getPixmapX().size() - 1),
s.getPixmapY().get(
s.getPixmapX().size() - 1));
if (pExit.contains(pN)) {
uscite.add(s);
}
}
// aggiungo ID poligono e numero di skiers che
// sono usciti nella mappa delle radioUscite
skierExitMap.put(inteout, uscite);
for (Skier s : temp) {
Point2D pN = pN(
s.getPixmapX().get(
s.getPixmapX().size() - 1),
s.getPixmapY().get(
s.getPixmapX().size() - 1));
if (pExit.contains(pN)) {
fnl.add(s);
}
}
edd.setListOfTraks(fnl);
dd.getListOfTo().add(edd);
}
directions.add(dd);
}
double f = Double.parseDouble(skiersList
.get(skiersList.size() - 1).getFrame().get(0));
int tokens = ((int) f / 15000) + 1;
/* PROVENIENZA SCIATORI */
// calcolo la lista di matchdata radioEntrate
ArrayList<MatchData> entersMatch = new ArrayList<MatchData>();
for (Integer id : skierEntranceMap.keySet())
entersMatch.add(computeMatchTokens(id, tokens,
skierEntranceMap.get(id), TOKEN_SIZE));
// creo il dataset
String[] labels = new String[enters.size()];
for (int i = 0; i < enters.size(); i++) {
labels[i] = enters.get(i).toString();
}
DefaultCategoryDataset enterDirectionDataset = datasetCreator
.createDirectionDataset(false, new int[] {},
computeReg(entersMatch), labels,
"entrati da ");
// creao il grafico
ProvenienzaChartCreator enterDirectionFactory = new ProvenienzaChartCreator(
enterDirectionDataset, "Provenienza sciatori");
JFreeChart enterDirectionChart = enterDirectionFactory
.createChart();
enterDirectionPanel = new ChartPanel(
enterDirectionChart);
enterDirectionPanel.setBorder(BorderFactory
.createLineBorder(Color.RED));
CategoryPlot cp = enterDirectionChart.getCategoryPlot();
BarRenderer renderer = (BarRenderer) cp.getRenderer();
// for (int c = 0; c < matchList.size(); c++) {
// renderer.setSeriesPaint(c, matchList.get(c)
// .getColor());
// }
enterDirectionPanel.setPreferredSize(new Dimension(400,
300));
enterDirectionPanel.setRangeZoomable(false);
/* DIREZIONI SCIATORI RIPARTITI DA PISTA */
// calcolo la lista di matchdata radioUscite
ArrayList<MatchData> exitsMatch = new ArrayList<MatchData>();
for (Integer id : skierExitMap.keySet())
exitsMatch.add(computeMatchTokens(id, tokens,
skierExitMap.get(id), TOKEN_SIZE));
// creo il dataset
labels = new String[exits.size()];
for (int i = 0; i < exits.size(); i++) {
labels[i] = exits.get(i).toString();
}
DefaultCategoryDataset exitDirectionDataset = datasetCreator
.createDirectionDataset(false,
computeStopped(exitsMatch),
computeReg(exitsMatch), labels,
"verso ");
// creao il grafico
DirectionChartCreator exitDirectionFactory = new DirectionChartCreator(
exitDirectionDataset,
"Direzione sciatori ripartiti da pista");
JFreeChart exitDirectionChart = exitDirectionFactory
.createChart();
exitDirectionPanel = new ChartPanel(exitDirectionChart);
exitDirectionPanel.setPreferredSize(new Dimension(400,
300));
exitDirectionPanel.setRangeZoomable(false);
exitDirectionPanel.setBorder(BorderFactory
.createLineBorder(Color.RED));
/* DIREZIONI SCIATORI PROVENDIENTI DA */
// calcolo la lista di datamatch
ArrayList<DirectionMatchData> directionmatchlist = new ArrayList<DirectionMatchData>();
listOfMatch = new ArrayList<ChartPanel>();
for (DirectionData data : directions) {
DirectionMatchData direction = new DirectionMatchData();
direction.setFrom(data.getFrom());
for (ExitDirectionData extdata : data.getListOfTo()) {
direction.add(computeMatchTokens(
extdata.getTo(), tokens,
extdata.getListOfTraks(), TOKEN_SIZE));
}
directionmatchlist.add(direction);
}
// creo il dataset
for (DirectionMatchData dirmatch : directionmatchlist) {
labels = new String[dirmatch.listOfTo.size()];
for (int i = 0; i < dirmatch.getListOfTo().size(); i++) {
labels[i] = String.valueOf(dirmatch
.getListOfTo().get(i).getId());
}
DefaultCategoryDataset directionDataset = datasetCreator
.createDirectionDataset(false,
computeStopped(dirmatch
.getListOfTo()),
computeReg(dirmatch.getListOfTo()),
labels, "verso ");
// creao il grafico
DirectionChartCreator directionFactory = new DirectionChartCreator(
directionDataset,
"Direzione sciatori proveniente da "
+ dirmatch.getFrom());
JFreeChart directionChart = directionFactory
.createChart();
ChartPanel directionPanel = new ChartPanel(
directionChart);
directionPanel.setBorder(BorderFactory
.createLineBorder(Color.RED));
directionPanel.setPreferredSize(new Dimension(400,
300));
directionPanel.setRangeZoomable(false);
listOfMatch.add(directionPanel);
}
}
CategoryDataset speedPercData = datasetCreator
.createSpeedPercentDataset(false,
new ArrayList<Skier>(skiersMap.values()));
CategoryDataset speedMaxData = datasetCreator
.createMaxSpeedPercentDataset(false,
new ArrayList<Skier>(skiersMap.values()));
new ArrayList<Skier>(skiersMap.values());
XYDataset densityData = datasetCreator
.createDensityDataset(parser.getTimeTokenListList());
SpeedPercentChartCreator percSpeedFactory = new SpeedPercentChartCreator(
speedPercData);
SpeedMaxChartCreator maxSpeedFactory = new SpeedMaxChartCreator(
speedMaxData);
DensityChartCreator densityFactory = new DensityChartCreator(
densityData);
JFreeChart speedPercChart = percSpeedFactory.createChart();
JFreeChart speedMaxChart = maxSpeedFactory.createChart();
JFreeChart densityChart = densityFactory.createChart();
densityPanel = new ChartPanel(densityChart);
speedPercPanel = new ChartPanel(speedPercChart);
speedMaxPanel = new ChartPanel(speedMaxChart);
speedPercPanel.setPreferredSize(new Dimension(400, 300));
speedMaxPanel.setPreferredSize(new Dimension(400, 300));
densityPanel.setPreferredSize(new Dimension(400, 300));
speedPercPanel.setRangeZoomable(false);
speedMaxPanel.setRangeZoomable(false);
densityPanel.setRangeZoomable(false);
graphContainer = new JPanel();
graphContainer.setBackground(Color.WHITE);
graphContainer.setName(GRAPH_CONTAINER_NAME);
graphScoll = new JScrollPane(graphContainer);
graphScoll.setSize(100, 100);
graphContainer.add(new InfoPanel());
speedPercPanel.setBorder(BorderFactory
.createLineBorder(Color.RED));
densityPanel.setBorder(BorderFactory
.createLineBorder(Color.RED));
speedMaxPanel.setBorder(BorderFactory
.createLineBorder(Color.RED));
graphContainer.add(speedPercPanel);
graphContainer.add(densityPanel);
graphContainer.add(speedMaxPanel);
int rows = 2;
if (DIREZIONI_CONFERMATE) {
graphContainer.add(enterDirectionPanel);
graphContainer.add(exitDirectionPanel);
for (ChartPanel panel : listOfMatch) {
graphContainer.add(panel);
}
rows = 4 + (int) (listOfMatch.size() / 2);
}
GridLayout grid = new GridLayout(rows, 2, 10, 15);
grid.preferredLayoutSize(graphScoll);
graphContainer.setLayout(grid);
graphContainer.revalidate();
times++;
rightTabPanel.add("Grafici", graphScoll);
OUTPUT_GENERATO = true;
}
private int[][] computeReg(ArrayList<MatchData> list) {
int[][] reg = new int[list.size()][];
int i = 0;
for (MatchData elem : list) {
reg[i] = new int[elem.getTimeTokenListList().size()];
for (int j = 0; j < parser.getTimeTokenListList()
.size(); j++) {
TimeToken token = elem.getTimeTokenListList()
.get(j);
reg[i][j] = token.getSkiers();
}
i++;
}
return reg;
}
private int[] computeStopped(ArrayList<MatchData> list) {
int[] stopped = new int[parser.getTimeTokenListList()
.size()];
for (int j = 0; j < parser.getTimeTokenListList().size(); j++) {
stopped[j] = parser.getTimeTokenListList().get(j)
.getHasStopped();
}
return stopped;
}
private MatchData computeMatchTokens(int id, int tokens,
List<Skier> skierlist, double tokensize) {
/* creazione dei time token, divisione per 5 minuti */
MatchData dataz = new MatchData(id);
ArrayList<TimeToken> tokenlist = new ArrayList<TimeToken>();
for (int i = 0; i < tokens; i++) {
TimeToken q = new TimeToken();
q.setOrd(i);
tokenlist.add(q);
}
// metto ogni skier nel token giusto leggendo il primo tempo
for (int j = 0; j < skierlist.size(); j++) {
Skier skier = skierlist.get(j);
double fr = Double.parseDouble(skier.getFrame().get(0));
int n = (int) (fr / tokensize);
TimeToken token = tokenlist.get(n);
token.getList().add(skier);
if (skier.hasStopped())
token.increseHasStopped();
}
for (int i = 0; i < tokens; i++) {
tokenlist.get(i).setMedSpeed(
calcMedSpeed(tokenlist.get(i).getList()));
tokenlist.get(i).setSkiers(
tokenlist.get(i).getList().size());
}
dataz.setTimeTokenListList(tokenlist);
return dataz;
}
private Point2D pN(String x, String y) {
return new Point2D.Double(Integer.parseInt(x),
Integer.parseInt(y));
}
private int calcMedSpeed(ArrayList<Skier> list) {
int count = 0;
int sum = 0;
for (Skier s : list) {
sum += s.getMedSpeed();
if (s.getMedSpeed() > 10)
count++;
}
if (count == 0)
return 0;
return sum / count;
}
}
}
class DirectionMatchData {
private int from;
private ArrayList<MatchData> listOfTo;
public DirectionMatchData() {
listOfTo = new ArrayList<MatchData>();
}
public void add(MatchData data) {
listOfTo.add(data);
}
public int getFrom() {
return from;
}
public void setFrom(int from) {
this.from = from;
}
public ArrayList<MatchData> getListOfTo() {
return listOfTo;
}
}
class DirectionData {
public DirectionData(int from) {
this.from = from;
listOfTo = new ArrayList<ExitDirectionData>();
}
private int from;
private ArrayList<ExitDirectionData> listOfTo;
public int getFrom() {
return from;
}
public void setFrom(int from) {
this.from = from;
}
public ArrayList<ExitDirectionData> getListOfTo() {
return listOfTo;
}
public void setListOfTo(ArrayList<ExitDirectionData> listOfTo) {
this.listOfTo = listOfTo;
}
}
class ExitDirectionData {
public ExitDirectionData(int to) {
this.to = to;
listOfTraks = new ArrayList<Skier>();
}
private ArrayList<Skier> listOfTraks;
private int to;
public int getTo() {
return to;
}
public void setTo(int to) {
this.to = to;
}
public ArrayList<Skier> getListOfTraks() {
return listOfTraks;
}
public void setListOfTraks(ArrayList<Skier> listOfTraks) {
this.listOfTraks = listOfTraks;
}
}
class AddEnter extends AbstractAction {
public AddEnter() {
super("Entrate");
}
public void actionPerformed(ActionEvent e) {
editPanel.setSelectColor(Color.GREEN);
editPanel.setEnter(true);
editPanel.setExit(false);
}
}
class AddExit extends AbstractAction {
public AddExit() {
super("Uscite");
}
public void actionPerformed(ActionEvent e) {
editPanel.setSelectColor(Color.RED);
editPanel.setExit(true);
editPanel.setEnter(false);
}
}
class GeneratePDFAction extends AbstractAction {
public GeneratePDFAction() {
super("Genera PDF");
}
@Override
public void actionPerformed(ActionEvent e) {
if (!XML_PARSED) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"XML non parsato.", SORRY,
JOptionPane.ERROR_MESSAGE);
return;
}
if (!OUTPUT_GENERATO) {
JOptionPane.showMessageDialog(AbstractFrame.this,
"Grafici non generati.", SORRY,
JOptionPane.ERROR_MESSAGE);
return;
}
generatePDF("./output/prova.pdf");
}
}
}
// pannello abbinamenti
protected class MatchingsPanel extends JPanel {
private MatchTableModel matchModel;
private static final long serialVersionUID = 1915905791856174042L;
private boolean isInit = false;
private int rowcount = 0;
private JScrollPane pane;
public int getRowcount() {
return rowcount;
}
public void setRowcount(int rowcount) {
this.rowcount = rowcount;
}
public void zeroMatchTab() {
matchList = new ArrayList<MatchData>();
rowcount = 0;
MATCH_ID = 0;
matchModel.refreshTable();
}
public void updateTab(MatchData data) {
rowcount++;
MATCH_ID++;
matchList.add(data);
matchModel.refreshTable();
if (!isInit) {
setTableVisible();
isInit = true;
revalidate();
}
}
private void setTableVisible() {
add(pane, BorderLayout.CENTER);
}
public MatchingsPanel() {
setLayout(new BorderLayout());
setPreferredSize(new Dimension(400, 400));
setSize(new Dimension(400, 400));
setMinimumSize(new Dimension(400, 200));
matchModel = new MatchTableModel();
setName("abbinamenti");
add(new ButtonsPanel(), BorderLayout.NORTH);
String data[][] = {};
String col[] = { "ID", "Colore", "n° totale", "Velocit� media",
"elimina" };
DefaultTableModel temp = new DefaultTableModel(data, col);
matchTable = new JTable(temp);
matchTable.setDefaultRenderer(Color.class, new ColorRenderer(true));
JTableHeader header = matchTable.getTableHeader();
header.setBackground(Color.yellow);
pane = new JScrollPane(matchTable);
matchTable.setModel(matchModel);
}
// pannello pulsantiera match panel
public class ButtonsPanel extends JPanel {
public ButtonsPanel() {
setLayout(new BoxLayout(this, BoxLayout.Y_AXIS));
// setPreferredSize(new Dimension(200, 100));
JPanel p1 = new JPanel();
p1.setSize(200, 50);
p1.setLayout(new FlowLayout(FlowLayout.LEFT));
p1.add(new MyButton(new MatchAction(),
"Aggiungi nuovo abbinamento"));
JPanel p2 = new JPanel();
p2.setLayout(new FlowLayout(FlowLayout.LEFT));
p2.add(new MyButton(new AddEnter(), "Aggiungi entrata"));
p2.add(new MyButton(new AddExit(), "Aggiungi uscita"));
JLabel lTime = new JLabel(" ");
p2.add(lTime);
p2.add(new MyButton(new OKAction(), "Calcola"));
JPanel p3 = new JPanel();
p3.setLayout(new FlowLayout(FlowLayout.RIGHT));
JPanel p4 = new JPanel();
p4.setLayout(new FlowLayout(FlowLayout.LEFT));
MyButton del = new MyButton(new ImageIcon("/images/images.png"));
p4.add(del);
JPanel space = new JPanel();
p1.setBackground(Color.WHITE);
p2.setBackground(Color.WHITE);
p3.setBackground(Color.WHITE);
p4.setBackground(Color.WHITE);
space.setBackground(Color.WHITE);
setBorder(new LineBorder(Color.GRAY));
add(p1);
add(p2);
add(p4);
add(space);
add(p3);
setSize(new Dimension(400, 200));
setPreferredSize(new Dimension(400, 200));
}
class MyButton extends JButton {
public MyButton(Action action, String tooltip) {
super(action);
setToolTipText(tooltip);
// setPreferredSize(new Dimension(100, 20));
}
public MyButton(ImageIcon icon) {
super(icon);
// setPreferredSize(new Dimension(100, 20));
}
}
}
protected class MatchTableModel extends AbstractTableModel {
public MatchTableModel() {
matchList = new ArrayList<MatchData>();
}
public int getColumnCount() {
return 4;
}
public int getRowCount() {
return matchList.size();
}
public String getColumnName(int col) {
if (col == 0)
return "ID";
if (col == 1)
return "Colore";
if (col == 2)
return "Numero totale";
if (col == 3)
return "Velocit� media";
if (col == 4)
return " - ";
return null;
}
public Object getValueAt(int row, int col) {
if (col == 0)
return matchList.get(row).getId();
if (col == 1)
return (Color) matchList.get(row).getColor();
if (col == 2)
return matchList.get(row).getNumberOfToken();
if (col == 3)
return matchList.get(row).getMedSpeed();
if (col == 4) {
return matchList.get(row).getButton();
}
return null;
}
public Class getColumnClass(int c) {
return getValueAt(0, c).getClass();
}
public void setValueAt(Object value, int row, int col) {
if (col == 0)
matchList.get(row).setId((Integer) value);
if (col == 1)
matchList.get(row).setColor((Color) value);
if (col == 2)
matchList.get(row).setNumberOfToken((Integer) value);
if (col == 3)
matchList.get(row).setMedSpeed((Integer) value);
if (col == 4)
matchList.get(row).setButton((TableButton) value);
fireTableCellUpdated(row, col);
}
public void refreshTable() {
for (MatchData d : matchList) {
setValueAt(d.getId(), d.getPosition(), 0);
setValueAt(d.getColor(), d.getPosition(), 1);
setValueAt(d.getNumberOfToken(), d.getPosition(), 2);
setValueAt(d.getMedSpeed(), d.getPosition(), 3);
setValueAt(d.getButton(), d.getPosition(), 4);
}
fireTableDataChanged();
}
public void removeRow(int id) {
ArrayList<MatchData> temp = new ArrayList<MatchData>();
for (MatchData d : matchList) {
if (d.getId() != id)
temp.add(d);
}
matchList = new ArrayList<MatchData>(temp);
if (rowcount > 0)
rowcount--;
refreshTable();
}
}
class ButtonRenderer extends JButton implements TableCellRenderer {
public ButtonRenderer() {
setOpaque(true);
}
public Component getTableCellRendererComponent(JTable table,
Object value, boolean isSelected, boolean hasFocus,
int row, int column) {
if (isSelected) {
setForeground(table.getSelectionForeground());
setBackground(table.getSelectionBackground());
} else {
setForeground(table.getForeground());
setBackground(UIManager.getColor("Button.background"));
}
setText("DELETE");
return this;
}
}
class AddEnter extends AbstractAction {
public AddEnter() {
super("+ Entrata");
}
public void actionPerformed(ActionEvent e) {
editPanel.setSelectColor(Color.GREEN);
editPanel.setEnter(true);
editPanel.setExit(false);
}
}
class AddExit extends AbstractAction {
public AddExit() {
super("+ Uscita");
}
public void actionPerformed(ActionEvent e) {
editPanel.setSelectColor(Color.RED);
editPanel.setExit(true);
editPanel.setEnter(false);
}
}
class MatchAction extends AbstractAction {
public MatchAction() {
super("Nuovo");
}
public void actionPerformed(ActionEvent e) {
if (XML_PARSED)
editPanel.resetMatch();
}
}
class DeleteMatchAction extends AbstractAction {
public DeleteMatchAction() {
super(" ");
}
public void actionPerformed(ActionEvent e) {
matchPanel.zeroMatchTab();
editPanel.clear();
}
}
class OKAction extends AbstractAction {
public OKAction() {
super("OK");
}
// Action delete = new AbstractAction() {
// public void actionPerformed(ActionEvent e) {
// int modelRow = Integer.valueOf(e.getActionCommand());
// matchTable.removeRowSelectionInterval(modelRow, modelRow);
// }
// };
public void actionPerformed(ActionEvent e) {
if (!XML_PARSED)
return;
Color color;
if ((color = JColorChooser.showDialog(getParent(), "",
Color.BLACK)) == null)
return;
editPanel.setNewMatchColor(color);
// creo il nuovo match
MatchData data = new MatchData(rowcount, MATCH_ID);
data.setTotalTokens(parser.getTotalTokens());
// l'edit panel aggiunge le altre info al data
editPanel.computeMatch(data);
matchPanel.updateTab(data);
}
}
}
}