2
2
3
3
import javafx .geometry .Bounds ;
4
4
import javafx .scene .Group ;
5
+ import javafx .scene .control .TextField ;
6
+ import javafx .scene .layout .AnchorPane ;
5
7
import javafx .scene .paint .Color ;
8
+ import javafx .scene .text .Text ;
6
9
import programminglife .model .Dummy ;
7
10
import programminglife .model .GenomeGraph ;
8
11
import programminglife .model .Segment ;
11
14
import programminglife .model .drawing .SubGraph ;
12
15
import programminglife .utility .Console ;
13
16
17
+ import java .util .Arrays ;
14
18
import java .util .Collection ;
15
19
import java .util .LinkedList ;
16
20
@@ -28,16 +32,19 @@ public class GraphController {
28
32
private double locationCenterX ;
29
33
private LinkedList <DrawableNode > oldMinMaxList = new LinkedList <>();
30
34
private SubGraph subGraph ;
35
+ private AnchorPane anchorGraphInfo ;
31
36
private LinkedList <DrawableNode > oldGenomeList = new LinkedList <>();
32
37
33
38
/**
34
39
* Initialize controller object.
35
40
* @param graph The genome graph to control
36
41
* @param grpDrawArea The {@link Group} to draw in
42
+ * @param anchorGraphInfo the {@link AnchorPane} were to show the info of a node or edge.
37
43
*/
38
- public GraphController (GenomeGraph graph , Group grpDrawArea ) {
44
+ public GraphController (GenomeGraph graph , Group grpDrawArea , AnchorPane anchorGraphInfo ) {
39
45
this .graph = graph ;
40
46
this .grpDrawArea = grpDrawArea ;
47
+ this .anchorGraphInfo = anchorGraphInfo ;
41
48
}
42
49
43
50
/**
@@ -172,11 +179,25 @@ private void highlightDummyNode(DrawableNode node, Color color) {
172
179
*/
173
180
private void drawEdge (DrawableNode parent , DrawableNode child ) {
174
181
DrawableEdge edge = new DrawableEdge (parent , child );
182
+ // If either parent or child are dummy nodes make on click use the link in that dummy.
183
+ if (parent .getNode () instanceof Dummy ) {
184
+ edge .setOnMouseClicked (event -> {
185
+ Console .println (parent .getNode ().getLink (null ).toString ());
186
+ });
187
+ } else if (child .getNode () instanceof Dummy ) {
188
+ edge .setOnMouseClicked (event -> {
189
+ Console .println (child .getNode ().getLink (null ).toString ());
190
+ });
191
+ } else {
192
+ edge .setOnMouseClicked (event -> Console .println (edge .toString ()));
193
+ }
175
194
edge .setOnMouseClicked (event -> {
176
- Console .println (edge .toString ());
177
- Console .println ("Genomes: " + graph .getGenomeNames (edge .getGenomes ()));
195
+ if (event .isShiftDown ()) {
196
+ showInfoEdge (edge , 250 );
197
+ } else {
198
+ showInfoEdge (edge , 10 );
199
+ }
178
200
});
179
-
180
201
edge .colorize (graph );
181
202
edge .setStartLocation (edge .getStart ().getRightBorderCenter ());
182
203
edge .setEndLocation (edge .getEnd ().getLeftBorderCenter ());
@@ -197,11 +218,14 @@ public void drawNode(DrawableNode drawableNode) {
197
218
});
198
219
} else {
199
220
Dummy node = (Dummy ) drawableNode .getNode ();
200
- drawableNode .setOnMouseClicked (event -> {
201
- Console .println (node .getLink (null ).toString ());
202
- Console .println ("Genomes: " + graph .getGenomeNames (node .getGenomes ()));
203
- });
204
221
}
222
+ drawableNode .setOnMouseClicked (event -> {
223
+ if (event .isShiftDown ()) {
224
+ showInfoNode (drawableNode , 250 );
225
+ } else {
226
+ showInfoNode (drawableNode , 10 );
227
+ }
228
+ });
205
229
drawableNode .colorize (graph );
206
230
this .grpDrawArea .getChildren ().add (drawableNode );
207
231
}
@@ -255,7 +279,99 @@ public void centerOnNodeId(int nodeId) {
255
279
256
280
grpDrawArea .setTranslateX (locationCenterX );
257
281
grpDrawArea .setTranslateY (locationCenterY );
282
+ }
283
+
284
+ /**
285
+ * Method to show the information of an edge.
286
+ * @param edge DrawableEdge the edge which has been clicked on.
287
+ * @param x int the x location of the TextField.
288
+ */
289
+ private void showInfoEdge (DrawableEdge edge , int x ) {
290
+ anchorGraphInfo .getChildren ().removeIf (node1 -> node1 .getLayoutX () == x );
291
+
292
+ Text idText = new Text ("Genomes: " ); idText .setLayoutX (x ); idText .setLayoutY (65 );
293
+ Text parentsText = new Text ("Parent: " ); parentsText .setLayoutX (x ); parentsText .setLayoutY (115 );
294
+ Text childrenText = new Text ("Child: " ); childrenText .setLayoutX (x ); childrenText .setLayoutY (165 );
295
+
296
+ TextField id = getTextField ("Genomes: " , x , 70 , graph .getGenomeNames (edge .getLink ().getGenomes ()).toString ());
297
+ TextField parent = getTextField ("Parent Node: " , x , 120 , edge .getStart ().getNode ().getIdentifier () + "" );
298
+ TextField child = getTextField ("Child Node: " , x , 170 , edge .getEnd ().getNode ().getIdentifier () + "" );
258
299
300
+ anchorGraphInfo .getChildren ().addAll (idText , parentsText , childrenText , id , parent , child );
301
+ }
302
+
303
+ /**
304
+ * Method to show the information of a node.
305
+ * @param node DrawableNode the node which has been clicked on.
306
+ * @param x int the x location of the TextField.
307
+ */
308
+ private void showInfoNode (DrawableNode node , int x ) {
309
+ Text idText = new Text ("ID: " ); idText .setLayoutX (x ); idText .setLayoutY (65 );
310
+ Text parentText = new Text ("Parents: " ); parentText .setLayoutX (x ); parentText .setLayoutY (115 );
311
+ Text childText = new Text ("Children: " ); childText .setLayoutX (x ); childText .setLayoutY (165 );
312
+ Text inEdgeText = new Text ("Incoming Edges: " ); inEdgeText .setLayoutX (x ); inEdgeText .setLayoutY (215 );
313
+ Text outEdgeText = new Text ("Outgoing Edges: " ); outEdgeText .setLayoutX (x ); outEdgeText .setLayoutY (265 );
314
+ Text genomeText = new Text ("Genomes: " ); genomeText .setLayoutX (x ); genomeText .setLayoutY (315 );
315
+ Text seqLengthText = new Text ("Sequence Length: " ); seqLengthText .setLayoutX (x ); seqLengthText .setLayoutY (365 );
316
+ Text seqText = new Text ("Sequence: " ); seqText .setLayoutX (x ); seqText .setLayoutY (415 );
317
+
318
+ anchorGraphInfo .getChildren ().removeIf (node1 -> node1 .getLayoutX () == x );
319
+
320
+ TextField id = getTextField ("ID: " , x , 70 , node .getNode ().getIdentifier () + "" );
321
+
322
+ StringBuilder parentSB = new StringBuilder ();
323
+ node .getNode ().getParents ().forEach (o -> parentSB .append (o .getIdentifier ()).append (", " ));
324
+ TextField parents ;
325
+ if (parentSB .length () > 2 ) {
326
+ parentSB .setLength (parentSB .length () - 2 );
327
+ parents = getTextField ("Parents: " , x , 120 , parentSB .toString ());
328
+ } else {
329
+ parentSB .replace (0 , parentSB .length (), "This node has no parent(s)" );
330
+ parents = getTextField ("Parents: " , x , 120 , parentSB .toString ());
331
+ }
332
+
333
+ StringBuilder childSB = new StringBuilder ();
334
+ node .getNode ().getChildren ().forEach (o -> childSB .append (o .getIdentifier ()).append (", " ));
335
+ TextField children ;
336
+ if (childSB .length () > 2 ) {
337
+ childSB .setLength (childSB .length () - 2 );
338
+ children = getTextField ("Children: " , x , 170 , childSB .toString ());
339
+ } else {
340
+ childSB .replace (0 , childSB .length (), "This node has no child(ren)" );
341
+ children = getTextField ("Children: " , x , 170 , childSB .toString ());
342
+ }
343
+
344
+ TextField inEdges = getTextField ("Incoming Edges: " , x , 220 , node .getNode ().getParentEdges ().size () + "" );
345
+ TextField outEdges = getTextField ("Outgoing Edges: " , x , 270 , node .getNode ().getChildEdges ().size () + "" );
346
+ TextField genome = getTextField ("Genome: " , x , 320 , graph .getGenomeNames (node .getNode ().getGenomes ()).toString ());
347
+ TextField seqLength = getTextField ("Sequence Length: " , x , 370 , node .getNode ().getSequence ().length () + "" );
348
+ TextField seq = getTextField (x + " Sequence: " , x , 420 , node .getNode ().getSequence ());
349
+
350
+ anchorGraphInfo .getChildren ().addAll (idText , parentText , childText , inEdgeText ,
351
+ outEdgeText , genomeText , seqLengthText , seqText );
352
+ anchorGraphInfo .getChildren ().addAll (id , parents , children , inEdges , outEdges , genome , seqLength , seq );
353
+ }
354
+
355
+ /**
356
+ * Returns a textField to be used by the edge and node information show panel.
357
+ * @param id String the id of the textField.
358
+ * @param x int the x coordinate of the textField inside the anchorPane.
359
+ * @param y int the y coordinate of the textField inside the anchorPane.
360
+ * @param text String the text to be shown by the textField.
361
+ * @return TextField the created textField.
362
+ */
363
+ private TextField getTextField (String id , int x , int y , String text ) {
364
+ TextField textField = new TextField ();
365
+ textField .setId (id );
366
+ textField .setText (text );
367
+ textField .setLayoutX (x );
368
+ textField .setLayoutY (y );
369
+ textField .setEditable (false );
370
+ textField .setStyle ("-fx-text-box-border: transparent;-fx-background-color: none; -fx-background-insets: 0;"
371
+ + " -fx-padding: 1 3 1 3; -fx-focus-color: transparent; -fx-faint-focus-color: transparent;" );
372
+ textField .setPrefSize (220 , 25 );
373
+
374
+ return textField ;
259
375
}
260
376
261
377
/**
0 commit comments