From 489d3f9f6c5b4f9a98901c065c0df6e0440e5638 Mon Sep 17 00:00:00 2001
From: Philipp Spohr <spohr.philipp@web.de>
Date: Wed, 30 Aug 2017 20:56:00 +0200
Subject: [PATCH] Some refactoring // cleanup

---
 .../de/hhu/ba/yoshikoWrapper/CyActivator.java |   2 +
 .../yoshikoWrapper/core/GraphicsLoader.java   |  22 +++
 .../core/NetChangeListener.java               |  10 +-
 .../ba/yoshikoWrapper/gui/ColumnMapper.java   |  66 +++++---
 .../ba/yoshikoWrapper/gui/EditCostPanel.java  |  23 ++-
 .../gui/EnableWhenSelectedListener.java       |  30 ++++
 .../hhu/ba/yoshikoWrapper/gui/MainPanel.java  | 149 ++++++++++--------
 .../gui/OperationModePanel.java               |  98 ++++++++++++
 .../gui/SolutionNumberChooser.java            |   8 +-
 .../yoshikoWrapper/gui/TimeLimitSetter.java   |   1 +
 .../ba/yoshikoWrapper/gui/YoshikoHeader.java  |  24 +++
 src/main/resources/YoshikoStrings.properties  |   9 +-
 .../resources/graphics/YoshikoAlphaLogo.png   | Bin 0 -> 6862 bytes
 .../resources/graphics/YoshikoAlphaText.png   | Bin 0 -> 7125 bytes
 src/main/resources/graphics/package-info.java |   1 +
 15 files changed, 343 insertions(+), 100 deletions(-)
 create mode 100644 src/main/java/de/hhu/ba/yoshikoWrapper/core/GraphicsLoader.java
 create mode 100644 src/main/java/de/hhu/ba/yoshikoWrapper/gui/EnableWhenSelectedListener.java
 create mode 100644 src/main/java/de/hhu/ba/yoshikoWrapper/gui/OperationModePanel.java
 create mode 100644 src/main/java/de/hhu/ba/yoshikoWrapper/gui/YoshikoHeader.java
 create mode 100644 src/main/resources/graphics/YoshikoAlphaLogo.png
 create mode 100644 src/main/resources/graphics/YoshikoAlphaText.png
 create mode 100644 src/main/resources/graphics/package-info.java

diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/CyActivator.java b/src/main/java/de/hhu/ba/yoshikoWrapper/CyActivator.java
index e663ccd..1f4f60e 100644
--- a/src/main/java/de/hhu/ba/yoshikoWrapper/CyActivator.java
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/CyActivator.java
@@ -3,6 +3,7 @@ package de.hhu.ba.yoshikoWrapper;
 import java.util.Properties;
 
 import org.cytoscape.application.CyApplicationManager;
+import org.cytoscape.application.events.SetCurrentNetworkListener;
 import org.cytoscape.application.swing.CySwingApplication;
 import org.cytoscape.application.swing.CytoPanelComponent;
 import org.cytoscape.model.CyNetworkFactory;
@@ -88,6 +89,7 @@ public class CyActivator extends AbstractCyActivator {
 		registerService(context,netChangeListener, ColumnCreatedListener.class, new Properties());
 		registerService(context,netChangeListener, ColumnDeletedListener.class, new Properties());
 		registerService(context,netChangeListener, SessionLoadedListener.class, new Properties());
+		registerService(context,netChangeListener, SetCurrentNetworkListener.class, new Properties());
 
 	}
 
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/core/GraphicsLoader.java b/src/main/java/de/hhu/ba/yoshikoWrapper/core/GraphicsLoader.java
new file mode 100644
index 0000000..77ba436
--- /dev/null
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/core/GraphicsLoader.java
@@ -0,0 +1,22 @@
+package de.hhu.ba.yoshikoWrapper.core;
+
+import javax.swing.ImageIcon;
+
+public class GraphicsLoader {
+	private static ImageIcon yoshikoLogo;
+	private static ImageIcon yoshikoText;
+	
+	public static ImageIcon getLogo() {
+		if (yoshikoLogo == null) {
+			yoshikoLogo = new ImageIcon("/resources/graphics/YoshikoAlphaLogo.png");
+		}
+		return yoshikoLogo;
+	}
+	
+	public static ImageIcon getText() {
+		if (yoshikoLogo == null) {
+			yoshikoLogo = new ImageIcon("/graphics/YoshikoAlphaText.png");
+		}
+		return yoshikoText;
+	}
+}
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/core/NetChangeListener.java b/src/main/java/de/hhu/ba/yoshikoWrapper/core/NetChangeListener.java
index cfb4620..49da3d0 100644
--- a/src/main/java/de/hhu/ba/yoshikoWrapper/core/NetChangeListener.java
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/core/NetChangeListener.java
@@ -1,5 +1,7 @@
 package de.hhu.ba.yoshikoWrapper.core;
 
+import org.cytoscape.application.events.SetCurrentNetworkEvent;
+import org.cytoscape.application.events.SetCurrentNetworkListener;
 import org.cytoscape.model.events.AddedEdgesEvent;
 import org.cytoscape.model.events.AddedEdgesListener;
 import org.cytoscape.model.events.ColumnCreatedEvent;
@@ -22,7 +24,8 @@ AddedEdgesListener,
 RemovedEdgesListener,
 ColumnCreatedListener,
 ColumnDeletedListener,
-SessionLoadedListener
+SessionLoadedListener,
+SetCurrentNetworkListener
 {
 	private ColumnMapper columnMapper;
 	
@@ -60,4 +63,9 @@ SessionLoadedListener
 		columnMapper.updateValues();
 	}
 
+	@Override
+	public void handleEvent(SetCurrentNetworkEvent e) {
+		columnMapper.updateValues();
+	}
+
 }
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/ColumnMapper.java b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/ColumnMapper.java
index f87c739..7d1c83b 100644
--- a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/ColumnMapper.java
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/ColumnMapper.java
@@ -1,10 +1,9 @@
 package de.hhu.ba.yoshikoWrapper.gui;
 
 
-import java.awt.event.ActionEvent;
-import java.awt.event.ActionListener;
+import java.awt.FlowLayout;
+
 import javax.swing.BoxLayout;
-import javax.swing.JButton;
 import javax.swing.JCheckBox;
 import javax.swing.JComboBox;
 
@@ -18,43 +17,64 @@ public class ColumnMapper extends ComfortPanel{
 	
 
 	//Swing components
-	private JComboBox<CyColumn> editingCostMapper;
-	private JComboBox<CyColumn> permanentMapper;
-	private JComboBox<CyColumn> forbiddenMapper;
+	private final JComboBox<CyColumn> editingCostMapper;
+	private final JComboBox<CyColumn> permanentMapper;
+	private final JComboBox<CyColumn> forbiddenMapper;
 		
-	private JCheckBox useMappingCost;
-	private JCheckBox useMappingPerm;
-	private JCheckBox useMappingForb;
-	
-	private JButton updateColumns;
+	private final JCheckBox useMappingCost;
+	private final JCheckBox useMappingPerm;
+	private final JCheckBox useMappingForb;
 	
+	private final ComfortPanel costGroup;
+	private final ComfortPanel permGroup;
+	private final ComfortPanel forbGroup;
+		
 	public ColumnMapper() {
 		this.setLayout(new BoxLayout(this,BoxLayout.Y_AXIS));
 
 		//SWING COMPONENTS
+		
+		//Combo-Boxes that map to the CyColumns
 		editingCostMapper = new JComboBox<CyColumn>();
 		permanentMapper = new JComboBox<CyColumn>();
 		forbiddenMapper = new JComboBox<CyColumn>();
+		
+		//Should only be enabled if the option is checked
+		editingCostMapper.setEnabled(false);
+		permanentMapper.setEnabled(false);
+		forbiddenMapper.setEnabled(false);
 
 		useMappingCost = new JCheckBox("Map modification costs");
 		useMappingPerm = new JCheckBox("Map edges as permanent");
 		useMappingForb = new JCheckBox("Map edges as forbidden");
 		
-		updateColumns = new JButton("Update Columns!");
+		useMappingCost.addActionListener(
+			new EnableWhenSelectedListener(useMappingCost, editingCostMapper)
+		);
+		useMappingPerm.addActionListener(
+			new EnableWhenSelectedListener(useMappingPerm, permanentMapper)
+			);
+		useMappingForb.addActionListener(
+			new EnableWhenSelectedListener(useMappingForb, forbiddenMapper)
+		);
 		
-		this.addAll(useMappingCost,editingCostMapper,useMappingPerm,permanentMapper,useMappingForb,forbiddenMapper,updateColumns);
-		//Initial call to get table values
-		updateValues();
-		//Add a focus listener to update values
-		updateColumns.addActionListener(new ActionListener() {
+		costGroup = new ComfortPanel();
+		permGroup = new ComfortPanel();
+		forbGroup = new ComfortPanel();
+		
+		costGroup.setLayout(new FlowLayout());
+		permGroup.setLayout(new FlowLayout());
+		forbGroup.setLayout(new FlowLayout());
 
-			@Override
-			public void actionPerformed(ActionEvent e) {
-				updateValues(); //shitty temporary solution
-			}
-			
-		});
+		costGroup.addAll(useMappingCost,editingCostMapper);
+		permGroup.addAll(useMappingPerm,permanentMapper);
+		forbGroup.addAll(useMappingForb,forbiddenMapper);
 
+		
+		this.addAll(costGroup,permGroup,forbGroup);
+		
+		//Initial call to get table values
+		updateValues();
 
 	}
 	
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/EditCostPanel.java b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/EditCostPanel.java
index aa6d26d..e8b6192 100644
--- a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/EditCostPanel.java
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/EditCostPanel.java
@@ -1,19 +1,26 @@
 package de.hhu.ba.yoshikoWrapper.gui;
 
+import java.awt.FlowLayout;
+
 import javax.swing.BorderFactory;
 import javax.swing.BoxLayout;
 import javax.swing.JLabel;
+import javax.swing.border.Border;
 import javax.swing.border.EtchedBorder;
 
 import org.cytoscape.model.CyColumn;
 
+import de.hhu.ba.yoshikoWrapper.core.LocalizationManager;
+
 @SuppressWarnings("serial") //Will never be serialized
 public class EditCostPanel extends ComfortPanel {
 	
 	//SWING COMPONENTS
 	private ColumnMapper columnMapper;
+	
 	private DoubleInputField  icField;
 	private DoubleInputField dcField;
+	
 	private JLabel icLabel;
 	private JLabel dcLabel;
 	
@@ -25,23 +32,33 @@ public class EditCostPanel extends ComfortPanel {
 		this.setLayout(new BoxLayout(this,BoxLayout.Y_AXIS));
 		//Initialize components
 		columnMapper = new ColumnMapper();
+		
 		icField = new DoubleInputField(Double.NEGATIVE_INFINITY,0);
 		dcField = new DoubleInputField(0,Double.POSITIVE_INFINITY);
+		
 		icField.setText("-1.0");
+		icField.setToolTipText(LocalizationManager.get("icTooltip"));
 		dcField.setText("1.0");
-		icLabel = new JLabel("Insertion Cost:");
-		dcLabel = new JLabel("Deletion Cost:");
+		
+		icLabel = new JLabel(LocalizationManager.get("defaultInsertion"));
+		dcLabel = new JLabel(LocalizationManager.get("defaultDeletion"));
 		//Group the labels with their text fields
 		groupIC = new ComfortPanel();
 		groupDC = new ComfortPanel();
 		
+		groupIC.setLayout(new FlowLayout());
+		groupDC.setLayout(new FlowLayout());
+
 		groupIC.addAll(icLabel,icField);
 		groupDC.addAll(dcLabel,dcField);
 		
 		this.addAll(columnMapper,groupIC,groupDC);
 		
 		//Decoration/Visual
-		this.setBorder(BorderFactory.createEtchedBorder(EtchedBorder.LOWERED));
+		Border border = BorderFactory.createEtchedBorder(EtchedBorder.LOWERED);
+		border = BorderFactory.createTitledBorder(border,LocalizationManager.get("editingCostPanel"));
+
+		this.setBorder(border);
 	}
 	
 	//SETTER / GETTER
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/EnableWhenSelectedListener.java b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/EnableWhenSelectedListener.java
new file mode 100644
index 0000000..1caa526
--- /dev/null
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/EnableWhenSelectedListener.java
@@ -0,0 +1,30 @@
+package de.hhu.ba.yoshikoWrapper.gui;
+
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+
+import javax.swing.JCheckBox;
+import javax.swing.JComponent;
+
+
+public class EnableWhenSelectedListener implements ActionListener {
+	
+	private final JComponent component;
+	private final JCheckBox checkBox;
+
+	public EnableWhenSelectedListener(JCheckBox cb, JComponent c) {
+		this.component = c;
+		this.checkBox = cb;
+	}
+
+	@Override
+	public void actionPerformed(ActionEvent e) {
+		if (checkBox.isSelected()) {
+			component.setEnabled(true);
+		}
+		else {
+			component.setEnabled(false);
+		}
+	}
+
+}
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/MainPanel.java b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/MainPanel.java
index 059fca6..a328edf 100644
--- a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/MainPanel.java
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/MainPanel.java
@@ -1,16 +1,18 @@
 package de.hhu.ba.yoshikoWrapper.gui;
 
 import java.awt.Component;
+import java.awt.FlowLayout;
 import java.awt.event.ActionEvent;
 import java.awt.event.ActionListener;
+import java.util.ArrayList;
+import java.util.Arrays;
 
-import javax.swing.BoxLayout;
-import javax.swing.ButtonGroup;
 import javax.swing.Icon;
 import javax.swing.JButton;
 import javax.swing.JCheckBox;
+import javax.swing.JComponent;
+import javax.swing.JLabel;
 import javax.swing.JOptionPane;
-import javax.swing.JRadioButton;
 
 import org.cytoscape.application.swing.CytoPanelComponent;
 import org.cytoscape.application.swing.CytoPanelName;
@@ -19,6 +21,7 @@ import org.cytoscape.work.TaskIterator;
 
 import de.hhu.ba.yoshikoWrapper.core.AlgorithmTask;
 import de.hhu.ba.yoshikoWrapper.core.CyCore;
+import de.hhu.ba.yoshikoWrapper.core.GraphicsLoader;
 import de.hhu.ba.yoshikoWrapper.core.LocalizationManager;
 import de.hhu.ba.yoshikoWrapper.core.YoshikoLoader;
 
@@ -30,80 +33,100 @@ import de.hhu.ba.yoshikoWrapper.core.YoshikoLoader;
 public class MainPanel extends ComfortPanel implements CytoPanelComponent {
 
 	//SWING COMPONENTS
+	
+	private final YoshikoHeader header;
+	
+	/**
+	 * Swing is a bit special sometimes, so a panel is used to wrap the lang-switcher.
+	 * This prevents stretching of the component
+	 */
+	private final ComfortPanel langSwitcherWrapper;
 	private final LanguageSwitcher langSwitcher;
 	
 	private final LibraryPanel libraryPanel;
 
 	private final EditCostPanel ecPanel;
 	
-	private final ButtonGroup heuristicGroup;
-	private final JRadioButton useHeuristic;
-	private final JRadioButton useILP;
-	
-	private final TimeLimitSetter timeLimitSetter;
 	
 	private final ReductionRulesChooser reductionRulesChooser;
+
+	private final OperationModePanel opModePanel;
 	
-	private final JCheckBox useTriangleCutsBox;
-	private final JCheckBox usePartitionCutsBox;
+	private final JCheckBox showAdvancedOptions;
 	
 
-	private final SolutionNumberChooser solutionNumberChooser;
+	private final ArrayList<JComponent> advancedOptions;
 
 	/**
 	 * Main constructor, creates a new Panel and initializes subcomponents
-	 * @param solPanel 
 	 */
-	public MainPanel( ) {
+	public MainPanel() {
 				
 		//SWING INIT
-		this.setLayout(new BoxLayout(this,BoxLayout.PAGE_AXIS));
+		this.setLayout(new FlowLayout());
 		
 		//Initialize Swing components
+		header = new YoshikoHeader();
+		
+		langSwitcherWrapper = new ComfortPanel();
 		langSwitcher = new LanguageSwitcher();
+		langSwitcherWrapper.addAll(new JLabel(LocalizationManager.get("switchLanguage")),langSwitcher);
+		langSwitcherWrapper.setLayout(new FlowLayout());
+		
 		libraryPanel = new LibraryPanel();
 		
 		ecPanel = new EditCostPanel();
 		
-		heuristicGroup = new ButtonGroup();
-		useILP = new JRadioButton("Use Integer Linear Programming");
-		useILP.setSelected(true);
-
-		useHeuristic = new JRadioButton("Use Heuristic");
-		heuristicGroup.add(useILP);
-		heuristicGroup.add(useHeuristic);
-		
-		solutionNumberChooser = new SolutionNumberChooser();
+		opModePanel = new OperationModePanel();
 		
 		reductionRulesChooser = new ReductionRulesChooser();
 		
-		timeLimitSetter = new TimeLimitSetter();
-				
-		useTriangleCutsBox = new JCheckBox("Use Triangle Cuts");
-		usePartitionCutsBox = new JCheckBox("Use Partition Cuts");
-
 		JButton runButton = new JButton("RUN");
 		runButton.addActionListener(buttonListener);
-		//Link time limit option to ILP
-		useILP.addActionListener(ilpHeuristicSwitch);
-		useHeuristic.addActionListener(ilpHeuristicSwitch);
+
+		
+		showAdvancedOptions = new JCheckBox(LocalizationManager.get("showAdvanced"));
+		showAdvancedOptions.addActionListener(toggleAdvancedOptionsListener);
 
 		this.addAll(
-				langSwitcher,
+				header,
+				langSwitcherWrapper,
+				showAdvancedOptions,
 				libraryPanel,
 				ecPanel,
-				useILP,
-				useHeuristic,
-				timeLimitSetter,
 				reductionRulesChooser,
-				useTriangleCutsBox,
-				usePartitionCutsBox,
-				solutionNumberChooser,
+				opModePanel,
 				runButton
 				);
 		
+		advancedOptions = new ArrayList<JComponent>();
+		//Manage all advanced components separately to enable toggling
+		advancedOptions.addAll(
+				Arrays.asList(
+						opModePanel,
+						reductionRulesChooser
+						)
+		);
+		
+		showAdvancedOptions(false);
+
 		this.setVisible(true);
 	}
+	
+	private ActionListener toggleAdvancedOptionsListener = new ActionListener() {
+
+		@Override
+		public void actionPerformed(ActionEvent e) {
+			showAdvancedOptions(showAdvancedOptions.isSelected());
+		}
+		
+	};
+	
+	private void showAdvancedOptions(boolean show) {
+		for (JComponent j : advancedOptions) {
+			j.setVisible(show);
+		}
+	}
 
 	/**
 	 * ButtonListener for the "Run" Button
@@ -116,7 +139,7 @@ public class MainPanel extends ComfortPanel implements CytoPanelComponent {
 			if (YoshikoLoader.isLibraryLoaded()){
 				AbstractTask yoshiko = new AlgorithmTask(
 					CyCore.cy.getCurrentNetwork(),
-					timeLimitSetter.getTimeLimit(), 
+					opModePanel.getTimeLimit(),
 					ecPanel.getWeightColumn(),
 					ecPanel.getPermanentColumn(),
 					ecPanel.getForbiddenColumn(),
@@ -124,41 +147,25 @@ public class MainPanel extends ComfortPanel implements CytoPanelComponent {
 					ecPanel.getDefaultDeletionCost(),
 					reductionRulesChooser.getBitMask(),
 					reductionRulesChooser.getMultFactor(),
-					useTriangleCutsBox.isSelected(),
-					usePartitionCutsBox.isSelected(), 
-					useHeuristic.isSelected(), 
-					solutionNumberChooser.getSolCount()
+					opModePanel.useTriangleCuts(),
+					opModePanel.usePartitionCuts(), 
+					opModePanel.useHeuristic(),
+					opModePanel.getSolCount()
 				);
 				CyCore.dialogTaskManager.execute(new TaskIterator(1,yoshiko));
 			}
 			else {
-				JOptionPane.showMessageDialog(
-						
-						null,
-						LocalizationManager.get("noLibTitle"),
-						LocalizationManager.get("noLibMessage"),
-						JOptionPane.ERROR_MESSAGE
-						);
+				JOptionPane.showMessageDialog(	
+					null,
+					LocalizationManager.get("noLibTitle"),
+					LocalizationManager.get("noLibMessage"),
+					JOptionPane.ERROR_MESSAGE
+				);
 			}
 		}
 	};
 	
-	ActionListener ilpHeuristicSwitch = new ActionListener() {
-		@Override
-		public void actionPerformed(ActionEvent e) {
-			if (useILP.isSelected()) {
-				timeLimitSetter.setEnabled(true);
-			}
-			else {
-				timeLimitSetter.setEnabled(false);
-			}
-		}	
-	};
-	
-	public ColumnMapper getColumnMapper() {
-		return ecPanel.getColumnMapper();
-	}
-	
+
 	
 	//GETTER / SETTER
 
@@ -178,11 +185,13 @@ public class MainPanel extends ComfortPanel implements CytoPanelComponent {
 		//TODO: Be creative I guess
 		return "Yoshiko";
 	}
-
-
+	
+	public ColumnMapper getColumnMapper() {
+		return ecPanel.getColumnMapper();
+	}
+	
 	public Icon getIcon() {
-		//TODO: 
-		return null;
+		return GraphicsLoader.getLogo();
 	}
 
 
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/OperationModePanel.java b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/OperationModePanel.java
new file mode 100644
index 0000000..133db24
--- /dev/null
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/OperationModePanel.java
@@ -0,0 +1,98 @@
+package de.hhu.ba.yoshikoWrapper.gui;
+
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+
+import javax.swing.BorderFactory;
+import javax.swing.BoxLayout;
+import javax.swing.ButtonGroup;
+import javax.swing.JCheckBox;
+import javax.swing.JRadioButton;
+import javax.swing.border.Border;
+import javax.swing.border.EtchedBorder;
+
+import de.hhu.ba.yoshikoWrapper.core.LocalizationManager;
+
+@SuppressWarnings("serial")
+public class OperationModePanel extends ComfortPanel{
+	private final JRadioButton useHeuristic;
+	private final JRadioButton useILP;
+	private final TimeLimitSetter timeLimitSetter;
+	private final SolutionNumberChooser solutionNumberChooser;
+	private final JCheckBox useTriangleCutsBox;
+	private final JCheckBox usePartitionCutsBox;
+	
+	private final ButtonGroup heuristicGroup;
+
+	public OperationModePanel() {
+		
+		this.setLayout(new BoxLayout(this,BoxLayout.Y_AXIS));
+		
+		heuristicGroup = new ButtonGroup();
+		useILP = new JRadioButton("Use Integer Linear Programming");
+		useILP.setSelected(true);
+
+		useHeuristic = new JRadioButton("Use Heuristic");
+		heuristicGroup.add(useILP);
+		heuristicGroup.add(useHeuristic);
+		
+		solutionNumberChooser = new SolutionNumberChooser();
+		
+
+		timeLimitSetter = new TimeLimitSetter();
+				
+		useTriangleCutsBox = new JCheckBox("Use Triangle Cuts");
+		usePartitionCutsBox = new JCheckBox("Use Partition Cuts");
+		
+		//Link time limit option to ILP
+		useILP.addActionListener(ilpHeuristicSwitch);
+		useHeuristic.addActionListener(ilpHeuristicSwitch);
+		
+
+		this.addAll(useILP,useHeuristic,solutionNumberChooser,timeLimitSetter,useTriangleCutsBox,usePartitionCutsBox);
+		
+		Border border = BorderFactory.createEtchedBorder(EtchedBorder.LOWERED);
+		border = BorderFactory.createTitledBorder(border,LocalizationManager.get("operationMode"));
+		this.setBorder(border);
+	}
+	
+	ActionListener ilpHeuristicSwitch = new ActionListener() {
+		@Override
+		public void actionPerformed(ActionEvent e) {
+			if (useILP.isSelected()) {
+				timeLimitSetter.setEnabled(true);
+				useTriangleCutsBox.setEnabled(true);
+				usePartitionCutsBox.setEnabled(true);
+				solutionNumberChooser.setEnabled(true);
+			}
+			else {
+				timeLimitSetter.setEnabled(false);
+				useTriangleCutsBox.setEnabled(false);
+				usePartitionCutsBox.setEnabled(false);
+				solutionNumberChooser.setEnabled(false);
+			}
+		}	
+	};
+	
+	//SETTER GETTER
+
+	public int getTimeLimit() {
+		return timeLimitSetter.getTimeLimit();
+	}
+
+	public boolean useTriangleCuts() {
+		return useTriangleCutsBox.isSelected();
+	}
+
+	public boolean usePartitionCuts() {
+		return usePartitionCutsBox.isSelected();
+	}
+
+	public boolean useHeuristic() {
+		return useHeuristic.isSelected();
+	}
+
+	public int getSolCount() {
+		return solutionNumberChooser.getSolCount();
+	}
+}
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/SolutionNumberChooser.java b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/SolutionNumberChooser.java
index dc90480..c75006a 100644
--- a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/SolutionNumberChooser.java
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/SolutionNumberChooser.java
@@ -16,8 +16,12 @@ public class SolutionNumberChooser extends ComfortPanel {
 		numSolutionsSetter = new JSpinner();
 		numSolutionsSetter.setModel(new SpinnerNumberModel(1,1,Integer.MAX_VALUE,1));
 		label = new JLabel(LocalizationManager.get("nrSolutions"));
-		this.addAll(label, numSolutionsSetter);
-		 
+		this.addAll(label, numSolutionsSetter);	 
+	}
+	
+	@Override
+	public void setEnabled(boolean enabled) {
+		numSolutionsSetter.setEnabled(enabled);
 	}
 
 	public int getSolCount() {
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/TimeLimitSetter.java b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/TimeLimitSetter.java
index 993afbb..abb2ea2 100644
--- a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/TimeLimitSetter.java
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/TimeLimitSetter.java
@@ -32,6 +32,7 @@ public class TimeLimitSetter extends ComfortPanel{
 		this.addAll(checkBox,numberField);
 	}
 	
+	@Override
 	public void setEnabled(boolean enabled) {
 		if (enabled) {
 			this.checkBox.setEnabled(enabled);
diff --git a/src/main/java/de/hhu/ba/yoshikoWrapper/gui/YoshikoHeader.java b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/YoshikoHeader.java
new file mode 100644
index 0000000..220ddcf
--- /dev/null
+++ b/src/main/java/de/hhu/ba/yoshikoWrapper/gui/YoshikoHeader.java
@@ -0,0 +1,24 @@
+package de.hhu.ba.yoshikoWrapper.gui;
+
+
+import javax.swing.BoxLayout;
+import javax.swing.JLabel;
+
+import de.hhu.ba.yoshikoWrapper.core.GraphicsLoader;
+
+@SuppressWarnings("serial")
+public class YoshikoHeader extends ComfortPanel {
+	
+	private JLabel logo;
+	private JLabel text;
+	
+	public YoshikoHeader() {
+		this.setLayout(new BoxLayout(this,BoxLayout.X_AXIS));
+
+		logo = new JLabel(GraphicsLoader.getLogo());
+		text = new JLabel(GraphicsLoader.getText());
+
+		this.addAll(logo,text);
+		
+	}
+}
diff --git a/src/main/resources/YoshikoStrings.properties b/src/main/resources/YoshikoStrings.properties
index d443a6a..bf621de 100644
--- a/src/main/resources/YoshikoStrings.properties
+++ b/src/main/resources/YoshikoStrings.properties
@@ -21,4 +21,11 @@ nrSolutions = Number of Solutions:
 redRuleChooserTitle = Reduction Rules
 discardSolution = Discard
 createMetaGraph = Create Meta-Graph
-metaGraph = Meta Graph
\ No newline at end of file
+metaGraph = Meta Graph
+showAdvanced = Show advanced options
+editingCostPanel = Editing Costs
+defaultInsertion = Default insertion cost:
+defaultDeletion = Default deletion cost:
+switchLanguage = Plugin language:
+icTooltip = This value is used to determine what the algorithm pays when inserting an edge. Existing mappings overwrite this value. A higher value means that the algorithm is less likely to insert edges in order to generate a cluster.
+operationMode = Operation Mode
\ No newline at end of file
diff --git a/src/main/resources/graphics/YoshikoAlphaLogo.png b/src/main/resources/graphics/YoshikoAlphaLogo.png
new file mode 100644
index 0000000000000000000000000000000000000000..526809e194d1b5ba94fe2c78c0f0d884d409d30d
GIT binary patch
literal 6862
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

literal 0
HcmV?d00001

diff --git a/src/main/resources/graphics/YoshikoAlphaText.png b/src/main/resources/graphics/YoshikoAlphaText.png
new file mode 100644
index 0000000000000000000000000000000000000000..eafac8c6726b9433584f17cc41eb11290e4cf5a0
GIT binary patch
literal 7125
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

literal 0
HcmV?d00001

diff --git a/src/main/resources/graphics/package-info.java b/src/main/resources/graphics/package-info.java
new file mode 100644
index 0000000..0a04afd
--- /dev/null
+++ b/src/main/resources/graphics/package-info.java
@@ -0,0 +1 @@
+package graphics;
\ No newline at end of file
-- 
GitLab