package ui.view;

import javax.swing.JSplitPane;
import javax.swing.JScrollPane;
import javax.swing.JPanel;

import java.util.ArrayList;
import java.util.Hashtable;
import java.util.Random;

import javax.swing.GroupLayout;
import javax.swing.GroupLayout.Alignment;
import javax.swing.JLabel;
import javax.swing.LayoutStyle.ComponentPlacement;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;
import javax.swing.event.TreeSelectionEvent;
import javax.swing.event.TreeSelectionListener;
import javax.swing.tree.DefaultMutableTreeNode;
import javax.swing.tree.DefaultTreeModel;
import javax.swing.tree.MutableTreeNode;
import javax.swing.tree.TreeNode;

import DataSets.GraphDataSet;
import DataSets.PropertyDataSet;
import classes.AbstractCpsObject;
import classes.CpsUpperNode;
import classes.HolonObject;
import classes.HolonSwitch;
import classes.TrackedDataSet;
import interfaces.GraphListener;
import ui.controller.Control;

import javax.swing.JTextField;
import javax.swing.JComboBox;
import javax.swing.JButton;
import javax.swing.JTree;
import java.awt.Color;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;

import javax.swing.border.CompoundBorder;
import javax.swing.border.LineBorder;
import javax.swing.JPopupMenu;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import javax.swing.JMenuItem;
import javax.swing.BorderFactory;
import javax.swing.Box;
import javax.swing.BoxLayout;
import java.awt.FlowLayout;
import java.awt.BorderLayout;

public class splitPane extends JSplitPane implements GraphListener {
	// Property Integers
	public static final int CONS_OBJ_INT = 0;
	public static final int PROD_OBJ_INT = 1;
	public static final int ACTIVE_ELEMENTS_INT = 2;
	public static final int SW_ACTIVE_INT = 3;
	public static final int PROD_HOLON_INT = 4;
	public static final int CONS_HOLON_INT = 5;
	public static final int SUPPLIED_INT = 6;
	public static final int NOT_SUPPLIED_INT = 7;
	public static final int PART_SUPPLIED_INT = 8;
	public static final int GRID_PROD_INT = 9;
	public static final int GRID_CONS_INT = 10;
	public static final int NR_SUBNETS_INT = 11;
	
	// Property Strings
	public static final String TOT_PROD_HOLON = "total Holon Production";
	public static final String TOT_CONS_HOLON = "total Holon Consumption";
	public static final String SUPPLIED_OBJ = "Percentage of supplied Objects";
	public static final String NOT_SUPPLIED_OBJ = "Percentage of not supplied Objects";
	public static final String PART_SUPPLIED_OBJ = "Percentage of partially supplied Objects";
	public static final String NR_SUBNETS = "number of Subnets";
	
	public static final String TOT_PROD_OBJ = "total Production";
	public static final String TOT_CONS_OBJ = "total Consumption";
	public static final String NR_ACTIVE_ELEMENTS = "active Elements";
	
	public static final String SW_ACTIVE = "active";
	
	public static final String TOT_PROD_GRID = "total Grid Production";
	public static final String TOT_CONS_GRID = "total Grid Consumption";
	
	// editable textfields
	private JTextField graphNrTxtField;
	private JTextField redField;
	private JTextField greenField;
	private JTextField blueField;
	
	// Tree Properties
	private JTree objectTree;
	private DefaultTreeModel treeModel;
	private DefaultMutableTreeNode objectsNode;
	private DefaultMutableTreeNode mainGrid;
	private DefaultMutableTreeNode switchesNode;
	private DefaultMutableTreeNode gridsNode;
	
	private Hashtable<String, GraphDataSet> objectHashtable;
	private Hashtable<String, StatisticGraphPanel> graphHashtable;
	private Hashtable<String, PropertyDataSet> holonHashtable;
	private Hashtable<String, Integer> propValTable;
	private JPanel colorPanel;
	
	//contains information about a selected property
	private PropertyDataSet currentProperty = new PropertyDataSet();
	private JComboBox colorComboBox;
	private Control controller;
	private JPanel graphPanel;

	JLabel showObjectlbl;
	JLabel showPropertylbl;

	public splitPane(Control cont) {
		this.controller = cont;
		objectHashtable = new Hashtable<String, GraphDataSet>();
		graphHashtable = new Hashtable<String, StatisticGraphPanel>();
		
		holonHashtable = new Hashtable<String, PropertyDataSet>();
		holonHashtable.put(TOT_PROD_HOLON, new PropertyDataSet());
		holonHashtable.put(TOT_CONS_HOLON, new PropertyDataSet());
		holonHashtable.put(SUPPLIED_OBJ, new PropertyDataSet());
		holonHashtable.put(NOT_SUPPLIED_OBJ, new PropertyDataSet());
		holonHashtable.put(PART_SUPPLIED_OBJ, new PropertyDataSet());
		holonHashtable.put(NR_SUBNETS, new PropertyDataSet());
		
		//propValTable associates the Strings to the numbers
		propValTable = new Hashtable<String, Integer>();
		propValTable.put(TOT_PROD_OBJ, PROD_OBJ_INT);
		propValTable.put(TOT_CONS_OBJ, CONS_OBJ_INT);
		propValTable.put(NR_ACTIVE_ELEMENTS, ACTIVE_ELEMENTS_INT);
		propValTable.put(SW_ACTIVE, SW_ACTIVE_INT);
		propValTable.put(TOT_PROD_HOLON, PROD_HOLON_INT);
		propValTable.put(TOT_CONS_HOLON, CONS_HOLON_INT);
		propValTable.put(SUPPLIED_OBJ, SUPPLIED_INT);
		propValTable.put(NOT_SUPPLIED_OBJ, NOT_SUPPLIED_INT);
		propValTable.put(PART_SUPPLIED_OBJ, PART_SUPPLIED_INT);
		propValTable.put(TOT_PROD_GRID, GRID_PROD_INT);
		propValTable.put(TOT_CONS_GRID, GRID_CONS_INT);
		propValTable.put(NR_SUBNETS, NR_SUBNETS_INT);

		JScrollPane dataPane = new JScrollPane();
		setLeftComponent(dataPane);
		JPanel panel = new JPanel();
		dataPane.setViewportView(panel);

		JScrollPane treeScrollPane = new JScrollPane();
		
		
		//================= LABLES ON THE LEFT SIDE =================//
		
		JLabel lblObject = new JLabel("Object(s):");

		showObjectlbl = new JLabel("...");

		JLabel lblProperty = new JLabel("Property:");

		showPropertylbl = new JLabel("...");

		JLabel lblGraph = new JLabel("Graph:");

		JLabel lblColor = new JLabel("Color:");
		
		//================= LABLES END ===============================//
		
		
		//================= COLOR COMBOBOX ===========================//
		
		colorComboBox = new JComboBox();
		colorComboBox.addItem("");
		colorComboBox.addItem("Red");
		colorComboBox.addItem("Blue");
		colorComboBox.addItem("Green");
		colorComboBox.addItem("Yellow");
		colorComboBox.addItem("Orange");
		colorComboBox.addItem("Cyan");
		colorComboBox.addItem("Magenta");
		colorComboBox.addItem("Pink");
		colorComboBox.addItem("Gray");
		colorComboBox.addItem("Random");
		colorComboBox.addItemListener(new ItemListener() {

			@Override
			public void itemStateChanged(ItemEvent e) {
				String colorName = (String) colorComboBox.getSelectedItem();
				Color tmpColor = Color.WHITE;
				switch (colorName) {
				case "":
					tmpColor = currentProperty.getColor();
					break;
				case "Red":
					tmpColor = Color.RED;
					colorChanged(tmpColor);
					break;
				case "Blue":
					tmpColor = Color.BLUE;
					colorChanged(tmpColor);
					break;
				case "Green":
					tmpColor = Color.GREEN;
					colorChanged(tmpColor);
					break;
				case "Yellow":
					tmpColor = Color.YELLOW;
					colorChanged(tmpColor);
					break;
				case "Orange":
					tmpColor = Color.ORANGE;
					colorChanged(tmpColor);
					break;
				case "Cyan":
					tmpColor = Color.CYAN;
					colorChanged(tmpColor);
					break;
				case "Magenta":
					tmpColor = Color.MAGENTA;
					colorChanged(tmpColor);
					break;
				case "Pink":
					tmpColor = Color.PINK;
					colorChanged(tmpColor);
					break;
				case "Gray":
					tmpColor = Color.GRAY;
					colorChanged(tmpColor);
					break;
				case "Random":
					Random rdm = new Random();
					tmpColor = new Color(rdm.nextInt(255), rdm.nextInt(255), rdm.nextInt(255));
				}
				redField.setText(Integer.toString(tmpColor.getRed()));
				greenField.setText(Integer.toString(tmpColor.getGreen()));
				blueField.setText(Integer.toString(tmpColor.getBlue()));
			}

		});
		
		// ==================== COLORBOX END ==========================//

		// ====================GRAPH NR TEXTFIELD======================//
		graphNrTxtField = new JTextField();
		graphNrTxtField.setColumns(10);
		graphNrTxtField.getDocument().addDocumentListener(new DocumentListener() {
			/*
			 * if textField for Red changes, changes will applied in the
			 * DataStructure "currentProperty" if Value is legit
			 */
			@Override
			public void insertUpdate(DocumentEvent e) {
				if (currentProperty != null) {
					currentProperty.setGraph(graphNrTxtField.getText());
				}
			}

			@Override
			public void removeUpdate(DocumentEvent e) {
				if (currentProperty != null) {
					currentProperty.setGraph(graphNrTxtField.getText());
				}
			}

			@Override
			public void changedUpdate(DocumentEvent e) {

			}
		});

		// ====================GRAPH NR TEXTFIELD END==================//

		// ====================RED TEXTFIELD===========================//
		redField = new JTextField();
		redField.setColumns(10);
		redField.getDocument().addDocumentListener(new DocumentListener() {
			/*
			 * if textField for Red changes, changes will applied in the
			 * DataStructure "currentProperty" if Value is legit
			 */
			@Override
			public void insertUpdate(DocumentEvent e) {
				int tmp = -1;
				try {
					tmp = Integer.parseInt(redField.getText());
				} catch (NumberFormatException e1) {

				}
				if (tmp > -1 && tmp <= 255) {
					if (currentProperty != null) {
						Color oldColor = currentProperty.getColor();
						Color color = new Color(tmp, oldColor.getGreen(), oldColor.getBlue());
						currentProperty.setColor(color);
						colorChanged(color);
					}
				}
			}

			@Override
			public void removeUpdate(DocumentEvent e) {
				int tmp = -1;
				try {
					tmp = Integer.parseInt(redField.getText());
				} catch (NumberFormatException e1) {

				}
				if (tmp > -1 && tmp <= 255) {
					if (currentProperty != null) {
						Color oldColor = currentProperty.getColor();
						Color color = new Color(tmp, oldColor.getGreen(), oldColor.getBlue());
						currentProperty.setColor(color);
						colorChanged(color);
					}
				}
			}

			@Override
			public void changedUpdate(DocumentEvent e) {

			}
		});
		// ======================RED TEXTFIELD END==========================//

		// ======================GREEN TEXTFIELD============================//
		greenField = new JTextField();
		greenField.setColumns(10);
		greenField.getDocument().addDocumentListener(new DocumentListener() {
			/*
			 * if textField for Red changes, changes will applied in the
			 * DataStructure "currentProperty" if Value is legit
			 */
			@Override
			public void insertUpdate(DocumentEvent e) {
				int tmp = -1;
				try {
					tmp = Integer.parseInt(greenField.getText());
				} catch (NumberFormatException e1) {

				}
				if (tmp > -1 && tmp <= 255) {
					if (currentProperty != null) {
						Color oldColor = currentProperty.getColor();
						Color color = new Color(oldColor.getRed(), tmp, oldColor.getBlue());
						currentProperty.setColor(color);
						colorChanged(color);
					}
				}
			}

			@Override
			public void removeUpdate(DocumentEvent e) {
				int tmp = -1;
				try {
					tmp = Integer.parseInt(greenField.getText());
				} catch (NumberFormatException e1) {

				}
				if (tmp > -1 && tmp <= 255) {
					if (currentProperty != null) {
						Color oldColor = currentProperty.getColor();
						Color color = new Color(oldColor.getRed(), tmp, oldColor.getBlue());
						currentProperty.setColor(color);
						colorChanged(color);
					}
				}
			}

			@Override
			public void changedUpdate(DocumentEvent e) {

			}
		});
		// ======================GREEN TEXTFIELD END========================//

		// ======================BLUE TEXTFIELD=============================//
		blueField = new JTextField();
		blueField.setColumns(10);
		blueField.getDocument().addDocumentListener(new DocumentListener() {
			/*
			 * if textField for Red changes, changes will applied in the
			 * DataStructure "currentProperty" if Value is legit
			 */
			@Override
			public void insertUpdate(DocumentEvent e) {
				int tmp = -1;
				try {
					tmp = Integer.parseInt(blueField.getText());
				} catch (NumberFormatException e1) {

				}
				if (tmp > -1 && tmp <= 255) {
					if (currentProperty != null) {
						Color oldColor = currentProperty.getColor();
						Color color = new Color(oldColor.getRed(), oldColor.getGreen(), tmp);
						currentProperty.setColor(color);
						colorChanged(color);
					}
				}
			}

			@Override
			public void removeUpdate(DocumentEvent e) {
				int tmp = -1;
				try {
					tmp = Integer.parseInt(blueField.getText());
				} catch (NumberFormatException e1) {

				}
				if (tmp > -1 && tmp <= 255) {
					if (currentProperty != null) {
						Color oldColor = currentProperty.getColor();
						Color color = new Color(oldColor.getRed(), oldColor.getGreen(), tmp);
						currentProperty.setColor(color);
						colorChanged(color);
					}
				}
			}

			@Override
			public void changedUpdate(DocumentEvent e) {

			}
		});
		// ======================BLUE TEXTFIELD END=========================//

		JLabel lblR = new JLabel("R:");

		JLabel lblG = new JLabel("G:");

		JLabel lblB = new JLabel("B:");
		
		
		//======================== ADD BUTTON =============================//

		JButton btnAdd = new JButton("Add");
		btnAdd.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode) objectTree
						.getLastSelectedPathComponent();
				if (selectedNode == null) {
					return;
				} else {
					if (selectedNode.getLevel() == 3 || (selectedNode.getLevel() == 2 && selectedNode.getParent().toString().equals("Main Grid") )) {
						StatisticGraphPanel tmp = null;
						if (graphNrTxtField.getText().length() > 0) {
							if (!graphHashtable.containsKey(graphNrTxtField.getText())
									&& graphNrTxtField.getText().length() > 0) {
								tmp = new StatisticGraphPanel(controller.getModel(), controller,
										graphNrTxtField.getText(), graphHashtable);
								//tmp.setPreferredSize(new Dimension(280, 150));
								//tmp.setMaximumSize(new Dimension(1000, 1000));
								// tmp.setMinimumSize(new Dimension(100, 45));
								tmp.setBorder(new LineBorder(new Color(0, 0, 0), 1));
								graphPanel.add(tmp);
								graphPanel.add(Box.createRigidArea(new Dimension(50, 50)));
								graphPanel.revalidate();
								graphPanel.updateUI();
								graphHashtable.put(graphNrTxtField.getText(), tmp);
							}
							String object = ((DefaultMutableTreeNode) selectedNode.getParent()).toString();
							String property = selectedNode.toString();
							AbstractCpsObject absCps = null;
							if(!object.equals("Main Grid")){
							GraphDataSet dataSet = objectHashtable.get(object);
							absCps = dataSet.getObject();
							}
							TrackedDataSet tds = new TrackedDataSet(absCps, propValTable.get(property),
									currentProperty.getColor());
							graphHashtable.get(graphNrTxtField.getText()).addObjec(tds);
						}
					}
				}
			}
		});
		
		//============================== ADD BUTTON END ==============================//

		colorPanel = new JPanel();
		colorPanel.setBorder(new LineBorder(new Color(0, 0, 0)));
		colorPanel.setBackground(Color.WHITE);
		
		
		//================== LAYOUT FOR COMPONENTS ON THE LEFT SIDE ==================//
		
		GroupLayout gl_panel = new GroupLayout(panel);
		gl_panel.setHorizontalGroup(gl_panel.createParallelGroup(Alignment.LEADING)
				.addGroup(gl_panel.createSequentialGroup().addContainerGap().addGroup(gl_panel
						.createParallelGroup(Alignment.TRAILING, false).addComponent(treeScrollPane,
								Alignment.LEADING)
						.addGroup(Alignment.LEADING,
								gl_panel.createSequentialGroup()
										.addGroup(gl_panel.createParallelGroup(Alignment.LEADING).addComponent(lblGraph)
												.addComponent(lblObject).addComponent(lblProperty)
												.addComponent(lblColor)
												.addGroup(gl_panel.createSequentialGroup().addComponent(lblR)
														.addPreferredGap(ComponentPlacement.RELATED).addGroup(gl_panel
																.createParallelGroup(Alignment.LEADING, false)
																.addComponent(colorPanel, GroupLayout.DEFAULT_SIZE,
																		GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
																.addComponent(redField, GroupLayout.DEFAULT_SIZE, 37,
																		Short.MAX_VALUE))))
										.addPreferredGap(ComponentPlacement.RELATED)
										.addGroup(gl_panel.createParallelGroup(Alignment.LEADING, false)
												.addComponent(showObjectlbl, GroupLayout.DEFAULT_SIZE,
														GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
												.addComponent(showPropertylbl, GroupLayout.DEFAULT_SIZE,
														GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
												.addComponent(colorComboBox, 0, GroupLayout.DEFAULT_SIZE,
														Short.MAX_VALUE)
												.addComponent(graphNrTxtField)
												.addGroup(gl_panel.createSequentialGroup().addGroup(gl_panel
														.createParallelGroup(Alignment.TRAILING).addComponent(btnAdd)
														.addGroup(gl_panel.createSequentialGroup().addComponent(lblG)
																.addPreferredGap(ComponentPlacement.RELATED)
																.addComponent(greenField, GroupLayout.PREFERRED_SIZE,
																		37, GroupLayout.PREFERRED_SIZE)))
														.addPreferredGap(ComponentPlacement.RELATED).addComponent(lblB)
														.addPreferredGap(ComponentPlacement.RELATED)
														.addComponent(blueField, GroupLayout.PREFERRED_SIZE, 37,
																GroupLayout.PREFERRED_SIZE)))))
						.addGap(32)));
		gl_panel.setVerticalGroup(
				gl_panel.createParallelGroup(Alignment.LEADING)
						.addGroup(gl_panel.createSequentialGroup().addContainerGap()
								.addComponent(treeScrollPane, GroupLayout.PREFERRED_SIZE, 174,
										GroupLayout.PREFERRED_SIZE)
								.addPreferredGap(ComponentPlacement.RELATED)
								.addGroup(gl_panel.createParallelGroup(Alignment.BASELINE)
										.addComponent(lblObject, GroupLayout.PREFERRED_SIZE, 14,
												GroupLayout.PREFERRED_SIZE)
										.addComponent(showObjectlbl))
								.addPreferredGap(ComponentPlacement.RELATED)
								.addGroup(gl_panel.createParallelGroup(Alignment.BASELINE).addComponent(lblProperty)
										.addComponent(showPropertylbl))
								.addPreferredGap(ComponentPlacement.RELATED)
								.addGroup(gl_panel.createParallelGroup(Alignment.BASELINE).addComponent(lblGraph)
										.addComponent(graphNrTxtField, GroupLayout.PREFERRED_SIZE,
												GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
								.addPreferredGap(ComponentPlacement.RELATED)
								.addGroup(gl_panel.createParallelGroup(Alignment.BASELINE).addComponent(lblColor)
										.addComponent(colorComboBox, GroupLayout.PREFERRED_SIZE,
												GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
								.addGap(18)
								.addGroup(gl_panel.createParallelGroup(Alignment.BASELINE).addComponent(lblR)
										.addComponent(redField, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE,
												GroupLayout.PREFERRED_SIZE)
										.addComponent(lblG)
										.addComponent(greenField, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE,
												GroupLayout.PREFERRED_SIZE)
										.addComponent(lblB).addComponent(blueField, GroupLayout.PREFERRED_SIZE,
												GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE))
								.addPreferredGap(ComponentPlacement.RELATED)
								.addComponent(colorPanel, GroupLayout.PREFERRED_SIZE, 33, GroupLayout.PREFERRED_SIZE)
								.addPreferredGap(ComponentPlacement.RELATED).addComponent(btnAdd)
								.addContainerGap(35, Short.MAX_VALUE)));
		
		//======================== LAYOUT END ================================//
		
		
		//======================== TREE STRUCTURE=============================//
		
		objectTree = new JTree();
		treeModel = (DefaultTreeModel) objectTree.getModel();
		DefaultMutableTreeNode root = new DefaultMutableTreeNode("Statistics");
		mainGrid = new DefaultMutableTreeNode("Main Grid");
		mainGrid.add(new DefaultMutableTreeNode(TOT_PROD_HOLON));
		mainGrid.add(new DefaultMutableTreeNode(TOT_CONS_HOLON));
		mainGrid.add(new DefaultMutableTreeNode(SUPPLIED_OBJ));
		mainGrid.add(new DefaultMutableTreeNode(NOT_SUPPLIED_OBJ));
		mainGrid.add(new DefaultMutableTreeNode(PART_SUPPLIED_OBJ));
		mainGrid.add(new DefaultMutableTreeNode(NR_SUBNETS));

		objectsNode = new DefaultMutableTreeNode("Objects");
		objectsNode.add(new DefaultMutableTreeNode("empty"));
		
		switchesNode = new DefaultMutableTreeNode("Switches");
		switchesNode.add(new DefaultMutableTreeNode("empty"));
		
		gridsNode = new DefaultMutableTreeNode("Groups");
		gridsNode.add(new DefaultMutableTreeNode("empty"));
		
		treeModel.setRoot(root);
		root.add(mainGrid);
		root.add(objectsNode);
		root.add(switchesNode);
		root.add(gridsNode);
		objectTree.setModel(treeModel);

		treeScrollPane.setViewportView(objectTree);

		JPopupMenu popupMenu = new JPopupMenu();
		addPopup(objectTree, popupMenu);

		JMenuItem mntmUntrack = new JMenuItem("Untrack");
		mntmUntrack.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode) objectTree
						.getLastSelectedPathComponent();
				if (selectedNode.getLevel() == 2 && !selectedNode.getParent().toString().equals("whole Holon")) {
					String object = selectedNode.toString();
					controller.removeTrackingObj(objectHashtable.get(object).getObject());
				}
			}
		});
		popupMenu.add(mntmUntrack);

		objectTree.addTreeSelectionListener(new TreeSelectionListener() {

			@Override
			public void valueChanged(TreeSelectionEvent e) {
				resetFields();
				showObjectlbl.setText("...");
				showPropertylbl.setText("...");
				DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode) objectTree
						.getLastSelectedPathComponent();
				if (selectedNode == null) {
					return;
				} else {
					if (selectedNode.getLevel() == 0) {
						disableFields();
					}
					if (selectedNode.getLevel() == 1) {
						disableFields();
						currentProperty = null;
						graphNrTxtField.setText("");
						showObjectlbl.setText(selectedNode.toString());
					}
					if (selectedNode.getLevel() == 2) {
						if (((DefaultMutableTreeNode) selectedNode.getParent()).toString().equals("Main Grid")) {
							enableFields();
							String object = selectedNode.getParent().toString();
							String property = selectedNode.toString();
							currentProperty = holonHashtable.get(property);
							Color color = currentProperty.getColor();
							
							redField.setText(Integer.toString(color.getRed()));
							greenField.setText(Integer.toString(color.getGreen()));
							blueField.setText(Integer.toString(color.getBlue()));
							
							showPropertylbl.setText(property);
							showObjectlbl.setText(object);
							graphNrTxtField.setText(currentProperty.getAssignedGraph());
							colorPanel.setBackground(color);
						} else {
							disableFields();
							currentProperty = null;
							graphNrTxtField.setText("");
							showObjectlbl.setText(selectedNode.toString());
						}
					}
					if (selectedNode.getLevel() == 3) {
						enableFields();
						String object = ((DefaultMutableTreeNode) selectedNode.getParent()).toString();
						String property = selectedNode.toString();
						currentProperty = objectHashtable.get(object).getPropertytTable().get(property);
						Color color = currentProperty.getColor();
						redField.setText(Integer.toString(color.getRed()));
						greenField.setText(Integer.toString(color.getGreen()));
						blueField.setText(Integer.toString(color.getBlue()));

						showObjectlbl.setText(object);
						showPropertylbl.setText(property);
						graphNrTxtField.setText(currentProperty.getAssignedGraph());
						colorPanel.setBackground(color);
					}
				}
			}

		});
		
		//========================= TREE STRUCTURE END ============================//
		
		
		panel.setLayout(gl_panel);

		JScrollPane graphScrollPane = new JScrollPane();
		setRightComponent(graphScrollPane);

		graphPanel = new JPanel();
		graphPanel.setLayout(new BoxLayout(graphPanel, BoxLayout.Y_AXIS));
		graphPanel.revalidate();
		graphPanel.updateUI();
		graphScrollPane.setViewportView(graphPanel);
		repaintTree();
	}
	
	//=============================== END CONSTRUCTOR ==============================//

	
	//=============================== METHODS ======================================//
	@Override
	public void repaintTree() {
		treeModel.reload();
	}

	@Override
	public void addTrackedObject(ArrayList<AbstractCpsObject> hlList) {
		objectsNode.removeAllChildren();
		switchesNode.removeAllChildren();
		gridsNode.removeAllChildren();
		objectHashtable.clear();
		if (hlList.size() > 0 && hlList != null) {
			for (AbstractCpsObject abs : hlList) {
				String name = abs.getName() + " " + abs.getID();
				DefaultMutableTreeNode tmp = new DefaultMutableTreeNode(name);
				Hashtable<String, PropertyDataSet> tmpHash = new Hashtable<String, PropertyDataSet>();

				//HolonObjects
				if(abs instanceof HolonObject){
					tmp.add(new DefaultMutableTreeNode(TOT_PROD_OBJ));
					tmp.add(new DefaultMutableTreeNode(TOT_CONS_OBJ));
					tmp.add(new DefaultMutableTreeNode(NR_ACTIVE_ELEMENTS));
					tmpHash.put(TOT_PROD_OBJ, new PropertyDataSet());
					tmpHash.put(TOT_CONS_OBJ, new PropertyDataSet());
					tmpHash.put(NR_ACTIVE_ELEMENTS, new PropertyDataSet());
					objectsNode.add(tmp);
				}
				
				//HolonSwitches
				if(abs instanceof HolonSwitch){
					tmp.add(new DefaultMutableTreeNode(SW_ACTIVE));
					tmpHash.put(SW_ACTIVE, new PropertyDataSet());
					switchesNode.add(tmp);
				}
				
				//NodesOfNodes
				if(abs instanceof CpsUpperNode){
					tmp.add(new DefaultMutableTreeNode(TOT_PROD_GRID));
					tmp.add(new DefaultMutableTreeNode(TOT_CONS_GRID));
					tmpHash.put(TOT_PROD_GRID, new PropertyDataSet());
					tmpHash.put(TOT_CONS_GRID, new PropertyDataSet());
					gridsNode.add(tmp);
				}
				
				GraphDataSet gS = new GraphDataSet(abs, tmpHash);
				objectHashtable.put(name, gS);
			}
		}
		if(objectsNode.getChildCount() == 0){
			objectsNode.add(new DefaultMutableTreeNode("empty"));
		}
		if(switchesNode.getChildCount() == 0){
			switchesNode.add(new DefaultMutableTreeNode("empty"));
		}
		if(gridsNode.getChildCount() == 0){
			gridsNode.add(new DefaultMutableTreeNode("empty"));
		}

	}

	public void colorChanged(Color color) {
		colorPanel.setBackground(color);
	}

	public void resetFields() {
		colorPanel.setBackground(Color.WHITE);
		redField.setText("");
		greenField.setText("");
		blueField.setText("");
		colorComboBox.setSelectedIndex(0);
	}

	public void disableFields() {
		redField.setEnabled(false);
		greenField.setEnabled(false);
		blueField.setEnabled(false);
		graphNrTxtField.setEnabled(false);
		colorComboBox.setEnabled(false);
		colorPanel.setBackground(Color.LIGHT_GRAY);
	}

	public void enableFields() {
		redField.setEnabled(true);
		greenField.setEnabled(true);
		blueField.setEnabled(true);
		graphNrTxtField.setEnabled(true);
		colorComboBox.setEnabled(true);
		colorPanel.setBackground(Color.WHITE);
	}

	public void repaintGraphs() {
		for (StatisticGraphPanel sg : graphHashtable.values()) {
			sg.repaint();
		}
	}

	private static void addPopup(Component component, final JPopupMenu popup) {
		component.addMouseListener(new MouseAdapter() {
			public void mousePressed(MouseEvent e) {
				if (e.isPopupTrigger()) {
					showMenu(e);
				}
			}

			public void mouseReleased(MouseEvent e) {
				if (e.isPopupTrigger()) {
					showMenu(e);
				}
			}

			private void showMenu(MouseEvent e) {
				popup.show(e.getComponent(), e.getX(), e.getY());
			}
		});
	}
}
