package nl.tudelft.dnainator.javafx.widgets;

import javafx.application.Platform;
import javafx.beans.property.DoubleProperty;
import javafx.beans.property.SimpleDoubleProperty;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.Pane;
import javafx.scene.shape.Rectangle;
import nl.tudelft.dnainator.graph.Graph;
import nl.tudelft.dnainator.javafx.drawables.strains.Strain;
import nl.tudelft.dnainator.javafx.views.StrainView;

/**
 * The minimap gives a global overview of the DNA strains in the {@link StrainView}, based on the
 * amount of ranks.
 */
public class Minimap extends Pane {
	private static final String VIEW_STYLE = "view";
	private static final String SPACER_STYLE = "spacer";
	private static final double HEIGHT = 50;
	private static final double SPACER_HEIGHT = 7;
	private Strain strain;
	private Graph graph;
	private StrainView strainView;
	private DoubleProperty widthPerRank = new SimpleDoubleProperty(0, "widthPerRank");

	/**
	 * Instantiates a new {@link Minimap}.
	 * @param strain The {@link Strain} to operate on.
	 * @param graph The {@link Graph} that the {@link Strain} operates on.
	 * @param strainView The {@link StrainView} that contains this minimap.
	 */
	public Minimap(Strain strain, Graph graph, StrainView strainView) {
		this.strain = strain;
		this.graph = graph;
		this.strainView = strainView;
		this.widthPerRank.bind(widthProperty().divide(graph.getMaxRank()));
		setHeight(HEIGHT);

		drawSpacer();
		// Wait for the Strain to update its properties.
		Platform.runLater(this::drawViewport);

		setOnMouseClicked(e -> onMouseClicked(e));
	}

	private void drawSpacer() {
		Rectangle spacer = new Rectangle();
		spacer.getStyleClass().add(SPACER_STYLE);
		spacer.widthProperty().bind(widthPerRank.multiply(graph.getMaxRank()));
		spacer.setHeight(SPACER_HEIGHT);
		spacer.yProperty().bind(
				heightProperty().divide(2).subtract(spacer.heightProperty().divide(2)));
		getChildren().add(spacer);
	}

	private void drawViewport() {
		Rectangle view = new Rectangle();
		view.getStyleClass().add(VIEW_STYLE);
		view.xProperty().bind(strain.minRankProperty().multiply(widthPerRank));
		view.heightProperty().bind(heightProperty());
		view.widthProperty().bind(widthPerRank.multiply(
				strain.maxRankProperty().subtract(strain.minRankProperty())));
		getChildren().add(view);
	}

	private void onMouseClicked(MouseEvent e) {
		int rank = (int) (e.getX() / widthPerRank.get());
		strainView.gotoRank(rank);
	}
}

@@ -435,16 +435,47 @@
 nView;%0A%0A
+import java.util.OptionalInt;%0A%0A
 /**%0A * T
@@ -581,20 +581,25 @@
 ount of 
-rank
+base pair
 s.%0A */%0Ap
@@ -937,20 +937,20 @@
 widthPer
-Rank
+Base
  = new S
@@ -981,20 +981,20 @@
 widthPer
-Rank
+Base
 %22);%0A%0A%09/*
@@ -1399,20 +1399,20 @@
 widthPer
-Rank
+Base
 .bind(wi
@@ -1436,36 +1436,41 @@
 ide(graph.getMax
-Rank
+BasePairs
 ()));%0A%09%09setHeigh
@@ -1780,36 +1780,36 @@
 ().bind(widthPer
-Rank
+Base
 .multiply(graph.
@@ -1814,20 +1814,25 @@
 h.getMax
-Rank
+BasePairs
 ()));%0A%09%09
@@ -2115,17 +2115,22 @@
 %0A%09%09view.
-x
+height
 Property
@@ -2137,16 +2137,37 @@
 ().bind(
+heightProperty());%0A%09%09
 strain.m
@@ -2187,223 +2187,421 @@
 y().
-multiply(widthPerRank));%0A%09%09view.heightProperty().bind(heightProperty());%0A%09%09view.widthProperty().bind(widthPerRank.multiply(%0A%09%09%09%09strain.maxRankProperty().subtract(strain.minRankProperty())));%0A%09%09getChildren().add(view
+addListener((obj, ov, nv) -%3E %7B%0A%09%09%09view.setX(getBasePairs(nv.intValue()) * widthPerBase.get());%0A%09%09%7D);%0A%09%09strain.maxRankProperty().addListener((obj, ov, nv) -%3E %7B%0A%09%09%09view.setWidth(getBasePairs(nv.intValue()) * widthPerBase.get() - view.getX());%0A%09%09%7D);%0A%09%09getChildren().add(view);%0A%09%7D%0A%0A%09private int getBasePairs(int rank) %7B%0A%09%09return graph.getRank(rank).stream()%0A%09%09%09%09.mapToInt(n -%3E n.getBaseDistance())%0A%09%09%09%09.max().orElse(0
 );%0A%09
@@ -2654,20 +2654,20 @@
 %7B%0A%09%09int 
-rank
+base
  = (int)
@@ -2691,18 +2691,64 @@
 hPer
-Rank.get()
+Base.get());%0A%09%09int rank = graph.getRankFromBasePair(base
 );%0A%09

Convert to basepairs instead of ranks