Clover icon

Coverage Report

  1. Project Clover database Thu Aug 13 2020 12:04:21 BST
  2. Package jalview.gui

File SeqPanelTest.java

 

Code metrics

4
423
15
1
905
601
18
0.04
28.2
15
1.2

Classes

Class Line # Actions
SeqPanelTest 56 423 18
0.9457013694.6%
 

Contributing tests

This file is covered by 9 tests. .

Source view

1    /*
2    * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$)
3    * Copyright (C) $$Year-Rel$$ The Jalview Authors
4    *
5    * This file is part of Jalview.
6    *
7    * Jalview is free software: you can redistribute it and/or
8    * modify it under the terms of the GNU General Public License
9    * as published by the Free Software Foundation, either version 3
10    * of the License, or (at your option) any later version.
11    *
12    * Jalview is distributed in the hope that it will be useful, but
13    * WITHOUT ANY WARRANTY; without even the implied warranty
14    * of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15    * PURPOSE. See the GNU General Public License for more details.
16    *
17    * You should have received a copy of the GNU General Public License
18    * along with Jalview. If not, see <http://www.gnu.org/licenses/>.
19    * The Jalview Authors are detailed in the 'AUTHORS' file.
20    */
21    package jalview.gui;
22   
23    import static org.testng.Assert.assertEquals;
24    import static org.testng.Assert.assertNull;
25    import static org.testng.Assert.assertTrue;
26   
27    import jalview.api.AlignViewportI;
28    import jalview.bin.Cache;
29    import jalview.bin.Jalview;
30    import jalview.commands.EditCommand;
31    import jalview.commands.EditCommand.Action;
32    import jalview.commands.EditCommand.Edit;
33    import jalview.datamodel.Alignment;
34    import jalview.datamodel.AlignmentAnnotation;
35    import jalview.datamodel.AlignmentI;
36    import jalview.datamodel.Sequence;
37    import jalview.datamodel.SequenceI;
38    import jalview.gui.SeqPanel.MousePos;
39    import jalview.io.DataSourceType;
40    import jalview.io.FileLoader;
41    import jalview.util.MessageManager;
42    import jalview.viewmodel.ViewportRanges;
43   
44    import java.awt.EventQueue;
45    import java.awt.event.MouseEvent;
46    import java.lang.reflect.InvocationTargetException;
47   
48    import javax.swing.JLabel;
49   
50    import org.testng.annotations.AfterMethod;
51    import org.testng.annotations.BeforeClass;
52    import org.testng.annotations.Test;
53   
54    import junit.extensions.PA;
55   
 
56    public class SeqPanelTest
57    {
58    AlignFrame af;
59   
 
60  1 toggle @BeforeClass(alwaysRun = true)
61    public void setUpJvOptionPane()
62    {
63  1 JvOptionPane.setInteractiveMode(false);
64  1 JvOptionPane.setMockResponse(JvOptionPane.CANCEL_OPTION);
65    }
 
66  1 toggle @Test(groups = "Functional")
67    public void testSetStatusReturnsNearestResiduePosition()
68    {
69  1 SequenceI seq1 = new Sequence("Seq1", "AACDE");
70  1 SequenceI seq2 = new Sequence("Seq2", "AA--E");
71  1 AlignmentI al = new Alignment(new SequenceI[] { seq1, seq2 });
72  1 AlignFrame alignFrame = new AlignFrame(al, al.getWidth(),
73    al.getHeight());
74  1 AlignmentI visAl = alignFrame.getViewport().getAlignment();
75   
76    // Test either side of gap
77  1 assertEquals(
78    alignFrame.alignPanel.getSeqPanel().setStatusMessage(
79    visAl.getSequenceAt(1), 1, 1), 2);
80  1 assertEquals(((JLabel) PA.getValue(alignFrame, "statusBar")).getText(),
81    "Sequence 2 ID: Seq2 Residue: ALA (2)");
82  1 assertEquals(
83    alignFrame.alignPanel.getSeqPanel().setStatusMessage(
84    visAl.getSequenceAt(1), 4, 1), 3);
85  1 assertEquals(((JLabel) PA.getValue(alignFrame, "statusBar")).getText(),
86    "Sequence 2 ID: Seq2 Residue: GLU (3)");
87    // no status message at a gap, returns next residue position to the right
88  1 assertEquals(
89    alignFrame.alignPanel.getSeqPanel().setStatusMessage(
90    visAl.getSequenceAt(1), 2, 1), 3);
91  1 assertEquals(((JLabel) PA.getValue(alignFrame, "statusBar")).getText(),
92    "Sequence 2 ID: Seq2");
93  1 assertEquals(
94    alignFrame.alignPanel.getSeqPanel().setStatusMessage(
95    visAl.getSequenceAt(1), 3, 1), 3);
96  1 assertEquals(((JLabel) PA.getValue(alignFrame, "statusBar")).getText(),
97    "Sequence 2 ID: Seq2");
98    }
99   
 
100  1 toggle @Test(groups = "Functional")
101    public void testAmbiguousAminoAcidGetsStatusMessage()
102    {
103  1 SequenceI seq1 = new Sequence("Seq1", "ABCDE");
104  1 SequenceI seq2 = new Sequence("Seq2", "AB--E");
105  1 AlignmentI al = new Alignment(new SequenceI[] { seq1, seq2 });
106  1 AlignFrame alignFrame = new AlignFrame(al, al.getWidth(),
107    al.getHeight());
108  1 AlignmentI visAl = alignFrame.getViewport().getAlignment();
109   
110  1 assertEquals(
111    alignFrame.alignPanel.getSeqPanel().setStatusMessage(
112    visAl.getSequenceAt(1), 1, 1), 2);
113  1 assertEquals(((JLabel) PA.getValue(alignFrame, "statusBar")).getText(),
114    "Sequence 2 ID: Seq2 Residue: B (2)");
115    }
116   
 
117  1 toggle @Test(groups = "Functional")
118    public void testGetEditStatusMessage()
119    {
120  1 assertNull(SeqPanel.getEditStatusMessage(null));
121   
122  1 EditCommand edit = new EditCommand(); // empty
123  1 assertNull(SeqPanel.getEditStatusMessage(edit));
124   
125  1 SequenceI[] seqs = new SequenceI[] { new Sequence("a", "b") };
126   
127    // 1 gap
128  1 edit.addEdit(edit.new Edit(Action.INSERT_GAP, seqs, 1, 1, '-'));
129  1 String expected = MessageManager.formatMessage("label.insert_gap", "1");
130  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
131   
132    // 3 more gaps makes +4
133  1 edit.addEdit(edit.new Edit(Action.INSERT_GAP, seqs, 1, 3, '-'));
134  1 expected = MessageManager.formatMessage("label.insert_gaps", "4");
135  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
136   
137    // 2 deletes makes + 2
138  1 edit.addEdit(edit.new Edit(Action.DELETE_GAP, seqs, 1, 2, '-'));
139  1 expected = MessageManager.formatMessage("label.insert_gaps", "2");
140  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
141   
142    // 2 more deletes makes 0 - no text
143  1 edit.addEdit(edit.new Edit(Action.DELETE_GAP, seqs, 1, 2, '-'));
144  1 assertNull(SeqPanel.getEditStatusMessage(edit));
145   
146    // 1 more delete makes 1 delete
147  1 edit.addEdit(edit.new Edit(Action.DELETE_GAP, seqs, 1, 1, '-'));
148  1 expected = MessageManager.formatMessage("label.delete_gap", "1");
149  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
150   
151    // 1 more delete makes 2 deletes
152  1 edit.addEdit(edit.new Edit(Action.DELETE_GAP, seqs, 1, 1, '-'));
153  1 expected = MessageManager.formatMessage("label.delete_gaps", "2");
154  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
155    }
156   
157    /**
158    * Tests that simulate 'locked editing', where an inserted gap is balanced by
159    * a gap deletion in the selection group, and vice versa
160    */
 
161  1 toggle @Test(groups = "Functional")
162    public void testGetEditStatusMessage_lockedEditing()
163    {
164  1 EditCommand edit = new EditCommand(); // empty
165  1 SequenceI[] seqs = new SequenceI[] { new Sequence("a", "b") };
166   
167    // 1 gap inserted, balanced by 1 delete
168  1 Edit e1 = edit.new Edit(Action.INSERT_GAP, seqs, 1, 1, '-');
169  1 edit.addEdit(e1);
170  1 Edit e2 = edit.new Edit(Action.DELETE_GAP, seqs, 5, 1, '-');
171  1 e2.setSystemGenerated(true);
172  1 edit.addEdit(e2);
173  1 String expected = MessageManager.formatMessage("label.insert_gap", "1");
174  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
175   
176    // 2 more gaps makes +3
177  1 Edit e3 = edit.new Edit(Action.INSERT_GAP, seqs, 1, 2, '-');
178  1 edit.addEdit(e3);
179  1 Edit e4 = edit.new Edit(Action.DELETE_GAP, seqs, 5, 2, '-');
180  1 e4.setSystemGenerated(true);
181  1 edit.addEdit(e4);
182  1 expected = MessageManager.formatMessage("label.insert_gaps", "3");
183  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
184   
185    // 2 deletes makes + 1
186  1 Edit e5 = edit.new Edit(Action.DELETE_GAP, seqs, 1, 2, '-');
187  1 edit.addEdit(e5);
188  1 Edit e6 = edit.new Edit(Action.INSERT_GAP, seqs, 5, 2, '-');
189  1 e6.setSystemGenerated(true);
190  1 edit.addEdit(e6);
191  1 expected = MessageManager.formatMessage("label.insert_gap", "1");
192  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
193   
194    // 1 more delete makes 0 - no text
195  1 Edit e7 = edit.new Edit(Action.DELETE_GAP, seqs, 1, 1, '-');
196  1 edit.addEdit(e7);
197  1 Edit e8 = edit.new Edit(Action.INSERT_GAP, seqs, 5, 1, '-');
198  1 e8.setSystemGenerated(true);
199  1 edit.addEdit(e8);
200  1 expected = MessageManager.formatMessage("label.insert_gaps", "2");
201  1 assertNull(SeqPanel.getEditStatusMessage(edit));
202   
203    // 1 more delete makes 1 delete
204  1 Edit e9 = edit.new Edit(Action.DELETE_GAP, seqs, 1, 1, '-');
205  1 edit.addEdit(e9);
206  1 Edit e10 = edit.new Edit(Action.INSERT_GAP, seqs, 5, 1, '-');
207  1 e10.setSystemGenerated(true);
208  1 edit.addEdit(e10);
209  1 expected = MessageManager.formatMessage("label.delete_gap", "1");
210  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
211   
212    // 2 more deletes makes 3 deletes
213  1 Edit e11 = edit.new Edit(Action.DELETE_GAP, seqs, 1, 2, '-');
214  1 edit.addEdit(e11);
215  1 Edit e12 = edit.new Edit(Action.INSERT_GAP, seqs, 5, 2, '-');
216  1 e12.setSystemGenerated(true);
217  1 edit.addEdit(e12);
218  1 expected = MessageManager.formatMessage("label.delete_gaps", "3");
219  1 assertEquals(SeqPanel.getEditStatusMessage(edit), expected);
220    }
221   
 
222  0 toggle public void testFindMousePosition_unwrapped()
223    {
224  0 String seqData = ">Seq1\nAACDE\n>Seq2\nAA--E\n";
225  0 AlignFrame alignFrame = new FileLoader().LoadFileWaitTillLoaded(seqData,
226    DataSourceType.PASTE);
227  0 AlignViewportI av = alignFrame.getViewport();
228  0 av.setShowAnnotation(true);
229  0 av.setWrapAlignment(false);
230  0 final int charHeight = av.getCharHeight();
231  0 final int charWidth = av.getCharWidth();
232    // sanity checks:
233  0 assertTrue(charHeight > 0);
234  0 assertTrue(charWidth > 0);
235  0 assertTrue(alignFrame.alignPanel.getSeqPanel().getWidth() > 0);
236   
237  0 SeqPanel testee = alignFrame.alignPanel.getSeqPanel();
238  0 int x = 0;
239  0 int y = 0;
240   
241    /*
242    * mouse at top left of unwrapped panel
243    */
244  0 MouseEvent evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y,
245    0, 0, 0, false, 0);
246  0 MousePos pos = testee.findMousePosition(evt);
247  0 assertEquals(pos.column, 0);
248  0 assertEquals(pos.seqIndex, 0);
249  0 assertEquals(pos.annotationIndex, -1);
250    }
251   
 
252  9 toggle @AfterMethod(alwaysRun = true)
253    public void tearDown()
254    {
255  9 Desktop.instance.closeAll_actionPerformed(null);
256    }
257   
 
258  1 toggle @Test(groups = "Functional")
259    public void testFindMousePosition_wrapped_annotations()
260    {
261  1 Cache.applicationProperties.setProperty("SHOW_ANNOTATIONS", "true");
262  1 Cache.applicationProperties.setProperty("WRAP_ALIGNMENT", "true");
263  1 AlignFrame alignFrame = new FileLoader().LoadFileWaitTillLoaded(
264    "examples/uniref50.fa", DataSourceType.FILE);
265  1 AlignViewportI av = alignFrame.getViewport();
266  1 av.setScaleAboveWrapped(false);
267  1 av.setScaleLeftWrapped(false);
268  1 av.setScaleRightWrapped(false);
269   
270  1 alignFrame.alignPanel.updateLayout();
271   
272  1 final int charHeight = av.getCharHeight();
273  1 final int charWidth = av.getCharWidth();
274  1 final int alignmentHeight = av.getAlignment().getHeight();
275   
276    // sanity checks:
277  1 assertTrue(charHeight > 0);
278  1 assertTrue(charWidth > 0);
279  1 assertTrue(alignFrame.alignPanel.getSeqPanel().getWidth() > 0);
280   
281  1 SeqPanel testee = alignFrame.alignPanel.getSeqPanel();
282  1 int x = 0;
283  1 int y = 0;
284   
285    /*
286    * mouse at top left of wrapped panel; there is a gap of charHeight
287    * above the alignment
288    */
289  1 MouseEvent evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y,
290    0, 0, 0, false, 0);
291  1 MousePos pos = testee.findMousePosition(evt);
292  1 assertEquals(pos.column, 0);
293  1 assertEquals(pos.seqIndex, -1); // above sequences
294  1 assertEquals(pos.annotationIndex, -1);
295   
296    /*
297    * cursor at bottom of gap above
298    */
299  1 y = charHeight - 1;
300  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
301    false, 0);
302  1 pos = testee.findMousePosition(evt);
303  1 assertEquals(pos.seqIndex, -1);
304  1 assertEquals(pos.annotationIndex, -1);
305   
306    /*
307    * cursor over top of first sequence
308    */
309  1 y = charHeight;
310  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
311    false, 0);
312  1 pos = testee.findMousePosition(evt);
313  1 assertEquals(pos.seqIndex, 0);
314  1 assertEquals(pos.annotationIndex, -1);
315   
316    /*
317    * cursor at bottom of first sequence
318    */
319  1 y = 2 * charHeight - 1;
320  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
321    false, 0);
322  1 pos = testee.findMousePosition(evt);
323  1 assertEquals(pos.seqIndex, 0);
324  1 assertEquals(pos.annotationIndex, -1);
325   
326    /*
327    * cursor at top of second sequence
328    */
329  1 y = 2 * charHeight;
330  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
331    false, 0);
332  1 pos = testee.findMousePosition(evt);
333  1 assertEquals(pos.seqIndex, 1);
334  1 assertEquals(pos.annotationIndex, -1);
335   
336    /*
337    * cursor at bottom of second sequence
338    */
339  1 y = 3 * charHeight - 1;
340  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
341    false, 0);
342  1 pos = testee.findMousePosition(evt);
343  1 assertEquals(pos.seqIndex, 1);
344  1 assertEquals(pos.annotationIndex, -1);
345   
346    /*
347    * cursor at bottom of last sequence
348    */
349  1 y = charHeight * (1 + alignmentHeight) - 1;
350  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
351    false, 0);
352  1 pos = testee.findMousePosition(evt);
353  1 assertEquals(pos.seqIndex, alignmentHeight - 1);
354  1 assertEquals(pos.annotationIndex, -1);
355   
356    /*
357    * cursor below sequences, in 3-pixel gap above annotations
358    * method reports index of nearest sequence above
359    */
360  1 y += 1;
361  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
362    false, 0);
363  1 pos = testee.findMousePosition(evt);
364  1 assertEquals(pos.seqIndex, alignmentHeight - 1);
365  1 assertEquals(pos.annotationIndex, -1);
366   
367    /*
368    * cursor still in the gap above annotations, now at the bottom of it
369    */
370  1 y += SeqCanvas.SEQS_ANNOTATION_GAP - 1; // 3-1 = 2
371  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
372    false, 0);
373  1 pos = testee.findMousePosition(evt);
374  1 assertEquals(pos.seqIndex, alignmentHeight - 1);
375  1 assertEquals(pos.annotationIndex, -1);
376   
377  1 AlignmentAnnotation[] annotationRows = av.getAlignment()
378    .getAlignmentAnnotation();
379  5 for (int n = 0; n < annotationRows.length; n++)
380    {
381    /*
382    * cursor at the top of the n'th annotation
383    */
384  4 y += 1;
385  4 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
386    false, 0);
387  4 pos = testee.findMousePosition(evt);
388  4 assertEquals(pos.seqIndex, alignmentHeight - 1);
389  4 assertEquals(pos.annotationIndex, n); // over n'th annotation
390   
391    /*
392    * cursor at the bottom of the n'th annotation
393    */
394  4 y += annotationRows[n].height - 1;
395  4 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
396    false, 0);
397  4 pos = testee.findMousePosition(evt);
398  4 assertEquals(pos.seqIndex, alignmentHeight - 1);
399  4 assertEquals(pos.annotationIndex, n);
400    }
401   
402    /*
403    * cursor in gap between wrapped widths
404    */
405  1 y += 1;
406  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
407    false, 0);
408  1 pos = testee.findMousePosition(evt);
409  1 assertEquals(pos.seqIndex, -1);
410  1 assertEquals(pos.annotationIndex, -1);
411   
412    /*
413    * cursor at bottom of gap between wrapped widths
414    */
415  1 y += charHeight - 1;
416  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
417    false, 0);
418  1 pos = testee.findMousePosition(evt);
419  1 assertEquals(pos.seqIndex, -1);
420  1 assertEquals(pos.annotationIndex, -1);
421   
422    /*
423    * cursor at top of first sequence, second wrapped width
424    */
425  1 y += 1;
426  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
427    false, 0);
428  1 pos = testee.findMousePosition(evt);
429  1 assertEquals(pos.seqIndex, 0);
430  1 assertEquals(pos.annotationIndex, -1);
431    }
432   
 
433  1 toggle @Test(groups = "Functional")
434    public void testFindMousePosition_wrapped_scaleAbove()
435    {
436  1 Cache.applicationProperties.setProperty("SHOW_ANNOTATIONS", "true");
437  1 Cache.applicationProperties.setProperty("WRAP_ALIGNMENT", "true");
438  1 AlignFrame alignFrame = new FileLoader().LoadFileWaitTillLoaded(
439    "examples/uniref50.fa", DataSourceType.FILE);
440  1 AlignViewportI av = alignFrame.getViewport();
441  1 av.setScaleAboveWrapped(true);
442  1 av.setScaleLeftWrapped(false);
443  1 av.setScaleRightWrapped(false);
444  1 alignFrame.alignPanel.updateLayout();
445   
446  1 final int charHeight = av.getCharHeight();
447  1 final int charWidth = av.getCharWidth();
448  1 final int alignmentHeight = av.getAlignment().getHeight();
449   
450    // sanity checks:
451  1 assertTrue(charHeight > 0);
452  1 assertTrue(charWidth > 0);
453  1 assertTrue(alignFrame.alignPanel.getSeqPanel().getWidth() > 0);
454   
455  1 SeqPanel testee = alignFrame.alignPanel.getSeqPanel();
456  1 int x = 0;
457  1 int y = 0;
458   
459    /*
460    * mouse at top left of wrapped panel; there is a gap of charHeight
461    * above the alignment
462    */
463  1 MouseEvent evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y,
464    0, 0, 0, false, 0);
465  1 MousePos pos = testee.findMousePosition(evt);
466  1 assertEquals(pos.column, 0);
467  1 assertEquals(pos.seqIndex, -1); // above sequences
468  1 assertEquals(pos.annotationIndex, -1);
469   
470    /*
471    * cursor at bottom of gap above
472    * two charHeights including scale panel
473    */
474  1 y = 2 * charHeight - 1;
475  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
476    false, 0);
477  1 pos = testee.findMousePosition(evt);
478  1 assertEquals(pos.seqIndex, -1);
479  1 assertEquals(pos.annotationIndex, -1);
480   
481    /*
482    * cursor over top of first sequence
483    */
484  1 y += 1;
485  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
486    false, 0);
487  1 pos = testee.findMousePosition(evt);
488  1 assertEquals(pos.seqIndex, 0);
489  1 assertEquals(pos.annotationIndex, -1);
490   
491    /*
492    * cursor at bottom of first sequence
493    */
494  1 y += charHeight - 1;
495  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
496    false, 0);
497  1 pos = testee.findMousePosition(evt);
498  1 assertEquals(pos.seqIndex, 0);
499  1 assertEquals(pos.annotationIndex, -1);
500   
501    /*
502    * cursor at top of second sequence
503    */
504  1 y += 1;
505  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
506    false, 0);
507  1 pos = testee.findMousePosition(evt);
508  1 assertEquals(pos.seqIndex, 1);
509  1 assertEquals(pos.annotationIndex, -1);
510   
511    /*
512    * cursor at bottom of second sequence
513    */
514  1 y += charHeight - 1;
515  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
516    false, 0);
517  1 pos = testee.findMousePosition(evt);
518  1 assertEquals(pos.seqIndex, 1);
519  1 assertEquals(pos.annotationIndex, -1);
520   
521    /*
522    * cursor at bottom of last sequence
523    * (scale + gap + sequences)
524    */
525  1 y = charHeight * (2 + alignmentHeight) - 1;
526  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
527    false, 0);
528  1 pos = testee.findMousePosition(evt);
529  1 assertEquals(pos.seqIndex, alignmentHeight - 1);
530  1 assertEquals(pos.annotationIndex, -1);
531   
532    /*
533    * cursor below sequences, in 3-pixel gap above annotations
534    */
535  1 y += 1;
536  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
537    false, 0);
538  1 pos = testee.findMousePosition(evt);
539  1 assertEquals(pos.seqIndex, alignmentHeight - 1);
540  1 assertEquals(pos.annotationIndex, -1);
541   
542    /*
543    * cursor still in the gap above annotations, now at the bottom of it
544    * method reports index of nearest sequence above
545    */
546  1 y += SeqCanvas.SEQS_ANNOTATION_GAP - 1; // 3-1 = 2
547  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
548    false, 0);
549  1 pos = testee.findMousePosition(evt);
550  1 assertEquals(pos.seqIndex, alignmentHeight - 1);
551  1 assertEquals(pos.annotationIndex, -1);
552   
553  1 AlignmentAnnotation[] annotationRows = av.getAlignment().getAlignmentAnnotation();
554  5 for (int n = 0; n < annotationRows.length; n++)
555    {
556    /*
557    * cursor at the top of the n'th annotation
558    */
559  4 y += 1;
560  4 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
561    false, 0);
562  4 pos = testee.findMousePosition(evt);
563  4 assertEquals(pos.seqIndex, alignmentHeight - 1);
564  4 assertEquals(pos.annotationIndex, n); // over n'th annotation
565   
566    /*
567    * cursor at the bottom of the n'th annotation
568    */
569  4 y += annotationRows[n].height - 1;
570  4 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
571    false, 0);
572  4 pos = testee.findMousePosition(evt);
573  4 SeqCanvas sc = testee.seqCanvas;
574  4 assertEquals(pos.seqIndex, alignmentHeight - 1,
575    String.format("%s n=%d y=%d %d, %d, %d, %d",
576    annotationRows[n].label, n, y, sc.getWidth(),
577    sc.getHeight(), sc.wrappedRepeatHeightPx,
578    sc.wrappedSpaceAboveAlignment));
579  4 assertEquals(pos.annotationIndex, n);
580    }
581   
582    /*
583    * cursor in gap between wrapped widths
584    */
585  1 y += 1;
586  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
587    false, 0);
588  1 pos = testee.findMousePosition(evt);
589  1 assertEquals(pos.seqIndex, -1);
590  1 assertEquals(pos.annotationIndex, -1);
591   
592    /*
593    * cursor at bottom of gap between wrapped widths
594    */
595  1 y += charHeight - 1;
596  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
597    false, 0);
598  1 pos = testee.findMousePosition(evt);
599  1 assertEquals(pos.seqIndex, -1);
600  1 assertEquals(pos.annotationIndex, -1);
601   
602    /*
603    * cursor at top of scale, second wrapped width
604    */
605  1 y += 1;
606  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
607    false, 0);
608  1 pos = testee.findMousePosition(evt);
609  1 assertEquals(pos.seqIndex, -1);
610  1 assertEquals(pos.annotationIndex, -1);
611   
612    /*
613    * cursor at bottom of scale, second wrapped width
614    */
615  1 y += charHeight - 1;
616  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
617    false, 0);
618  1 pos = testee.findMousePosition(evt);
619  1 assertEquals(pos.seqIndex, -1);
620  1 assertEquals(pos.annotationIndex, -1);
621   
622    /*
623    * cursor at top of first sequence, second wrapped width
624    */
625  1 y += 1;
626  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
627    false, 0);
628  1 pos = testee.findMousePosition(evt);
629  1 assertEquals(pos.seqIndex, 0);
630  1 assertEquals(pos.annotationIndex, -1);
631    }
632   
 
633  1 toggle @Test(groups = "Functional")
634    public void testFindMousePosition_wrapped_noAnnotations()
635    {
636  1 Cache.applicationProperties.setProperty("SHOW_ANNOTATIONS", "false");
637  1 Cache.applicationProperties.setProperty("WRAP_ALIGNMENT", "true");
638  1 AlignFrame alignFrame = new FileLoader().LoadFileWaitTillLoaded(
639    "examples/uniref50.fa", DataSourceType.FILE);
640  1 AlignViewportI av = alignFrame.getViewport();
641  1 av.setScaleAboveWrapped(false);
642  1 av.setScaleLeftWrapped(false);
643  1 av.setScaleRightWrapped(false);
644  1 alignFrame.alignPanel.updateLayout();
645   
646  1 final int charHeight = av.getCharHeight();
647  1 final int charWidth = av.getCharWidth();
648  1 final int alignmentHeight = av.getAlignment().getHeight();
649   
650    // sanity checks:
651  1 assertTrue(charHeight > 0);
652  1 assertTrue(charWidth > 0);
653  1 assertTrue(alignFrame.alignPanel.getSeqPanel().getWidth() > 0);
654   
655  1 SeqPanel testee = alignFrame.alignPanel.getSeqPanel();
656  1 int x = 0;
657  1 int y = 0;
658   
659    /*
660    * mouse at top left of wrapped panel; there is a gap of charHeight
661    * above the alignment
662    */
663  1 MouseEvent evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y,
664    0, 0, 0, false, 0);
665  1 MousePos pos = testee.findMousePosition(evt);
666  1 assertEquals(pos.column, 0);
667  1 assertEquals(pos.seqIndex, -1); // above sequences
668  1 assertEquals(pos.annotationIndex, -1);
669   
670    /*
671    * cursor over top of first sequence
672    */
673  1 y = charHeight;
674  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
675    false, 0);
676  1 pos = testee.findMousePosition(evt);
677  1 assertEquals(pos.seqIndex, 0);
678  1 assertEquals(pos.annotationIndex, -1);
679   
680    /*
681    * cursor at bottom of last sequence
682    */
683  1 y = charHeight * (1 + alignmentHeight) - 1;
684  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
685    false, 0);
686  1 pos = testee.findMousePosition(evt);
687  1 assertEquals(pos.seqIndex, alignmentHeight - 1);
688  1 assertEquals(pos.annotationIndex, -1);
689   
690    /*
691    * cursor below sequences, at top of charHeight gap between widths
692    */
693  1 y += 1;
694  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
695    false, 0);
696  1 pos = testee.findMousePosition(evt);
697  1 assertEquals(pos.seqIndex, -1);
698  1 assertEquals(pos.annotationIndex, -1);
699   
700    /*
701    * cursor below sequences, at top of charHeight gap between widths
702    */
703  1 y += charHeight - 1;
704  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
705    false, 0);
706  1 pos = testee.findMousePosition(evt);
707  1 assertEquals(pos.seqIndex, -1);
708  1 assertEquals(pos.annotationIndex, -1);
709   
710    /*
711    * cursor at the top of the first sequence, second width
712    */
713  1 y += 1;
714  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, y, 0, 0, 0,
715    false, 0);
716  1 pos = testee.findMousePosition(evt);
717  1 assertEquals(pos.seqIndex, 0);
718  1 assertEquals(pos.annotationIndex, -1);
719    }
720   
 
721  1 toggle @Test(groups = "Functional")
722    public void testFindColumn_unwrapped()
723    {
724  1 Cache.applicationProperties.setProperty("WRAP_ALIGNMENT", "false");
725  1 AlignFrame alignFrame = new FileLoader().LoadFileWaitTillLoaded(
726    "examples/uniref50.fa", DataSourceType.FILE);
727  1 SeqPanel testee = alignFrame.alignPanel.getSeqPanel();
728  1 int x = 0;
729  1 final int charWidth = alignFrame.getViewport().getCharWidth();
730  1 assertTrue(charWidth > 0); // sanity check
731  1 ViewportRanges ranges = alignFrame.getViewport().getRanges();
732  1 assertEquals(ranges.getStartRes(), 0);
733   
734    /*
735    * mouse at top left of unwrapped panel
736    */
737  1 MouseEvent evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0,
738    0, 0, 0, false, 0);
739  1 assertEquals(testee.findColumn(evt), 0);
740   
741    /*
742    * not quite one charWidth across
743    */
744  1 x = charWidth-1;
745  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0,
746    0, 0, 0, false, 0);
747  1 assertEquals(testee.findColumn(evt), 0);
748   
749    /*
750    * one charWidth across
751    */
752  1 x = charWidth;
753  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
754    false, 0);
755  1 assertEquals(testee.findColumn(evt), 1);
756   
757    /*
758    * two charWidths across
759    */
760  1 x = 2 * charWidth;
761  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
762    false, 0);
763  1 assertEquals(testee.findColumn(evt), 2);
764   
765    /*
766    * limited to last column of seqcanvas
767    */
768  1 x = 20000;
769  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
770    false, 0);
771  1 SeqCanvas seqCanvas = alignFrame.alignPanel.getSeqPanel().seqCanvas;
772  1 int w = seqCanvas.getWidth();
773    // limited to number of whole columns, base 0,
774    // and to end of visible range
775  1 int expected = w / charWidth;
776  1 expected = Math.min(expected, ranges.getEndRes());
777  1 assertEquals(testee.findColumn(evt), expected);
778   
779    /*
780    * hide columns 5-10 (base 1)
781    */
782  1 alignFrame.getViewport().hideColumns(4, 9);
783  1 x = 5 * charWidth + 2;
784    // x is in 6th visible column, absolute column 12, or 11 base 0
785  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
786    false, 0);
787  1 assertEquals(testee.findColumn(evt), 11);
788    }
789   
 
790  1 toggle @Test(groups = "Functional")
791    public void testFindColumn_wrapped()
792    {
793  1 Cache.applicationProperties.setProperty("WRAP_ALIGNMENT", "true");
794  1 AlignFrame alignFrame = new FileLoader().LoadFileWaitTillLoaded(
795    "examples/uniref50.fa", DataSourceType.FILE);
796  1 AlignViewport av = alignFrame.getViewport();
797  1 av.setScaleAboveWrapped(false);
798  1 av.setScaleLeftWrapped(false);
799  1 av.setScaleRightWrapped(false);
800  1 alignFrame.alignPanel.updateLayout();
801  1 SeqPanel testee = alignFrame.alignPanel.getSeqPanel();
802  1 int x = 0;
803  1 final int charWidth = av.getCharWidth();
804  1 assertTrue(charWidth > 0); // sanity check
805  1 assertEquals(av.getRanges().getStartRes(), 0);
806   
807    /*
808    * mouse at top left of wrapped panel, no West (left) scale
809    */
810  1 MouseEvent evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0,
811    0, 0, 0, false, 0);
812  1 assertEquals(testee.findColumn(evt), 0);
813   
814    /*
815    * not quite one charWidth across
816    */
817  1 x = charWidth-1;
818  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0,
819    0, 0, 0, false, 0);
820  1 assertEquals(testee.findColumn(evt), 0);
821   
822    /*
823    * one charWidth across
824    */
825  1 x = charWidth;
826  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
827    false, 0);
828  1 assertEquals(testee.findColumn(evt), 1);
829   
830    /*
831    * x over scale left (before drawn columns) results in -1
832    */
833  1 av.setScaleLeftWrapped(true);
834  1 alignFrame.alignPanel.updateLayout();
835  1 SeqCanvas seqCanvas = testee.seqCanvas;
836  1 int labelWidth = (int) PA.getValue(seqCanvas, "labelWidthWest");
837  1 assertTrue(labelWidth > 0);
838  1 x = labelWidth - 1;
839  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
840    false, 0);
841  1 assertEquals(testee.findColumn(evt), -1);
842   
843  1 x = labelWidth;
844  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
845    false, 0);
846  1 assertEquals(testee.findColumn(evt), 0);
847   
848    /*
849    * x over right edge of last residue (including scale left)
850    */
851  1 int residuesWide = av.getRanges().getViewportWidth();
852  1 assertTrue(residuesWide > 0);
853  1 x = labelWidth + charWidth * residuesWide - 1;
854  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
855    false, 0);
856  1 assertEquals(testee.findColumn(evt), residuesWide - 1);
857   
858    /*
859    * x over scale right (beyond drawn columns) results in -1
860    */
861  1 av.setScaleRightWrapped(true);
862  1 alignFrame.alignPanel.updateLayout();
863  1 labelWidth = (int) PA.getValue(seqCanvas, "labelWidthEast");
864  1 assertTrue(labelWidth > 0);
865  1 int residuesWide2 = av.getRanges().getViewportWidth();
866  1 assertTrue(residuesWide2 > 0);
867  1 assertTrue(residuesWide2 < residuesWide); // available width reduced
868  1 x += 1; // just over left edge of scale right
869  1 evt = new MouseEvent(testee, MouseEvent.MOUSE_MOVED, 0L, 0, x, 0, 0, 0, 0,
870    false, 0);
871  1 assertEquals(testee.findColumn(evt), -1);
872   
873    // todo add startRes offset, hidden columns
874   
875    }
 
876  1 toggle @BeforeClass(alwaysRun = true)
877    public static void setUpBeforeClass() throws Exception
878    {
879    /*
880    * use read-only test properties file
881    */
882  1 Cache.loadProperties("test/jalview/io/testProps.jvprops");
883  1 Jalview.main(new String[] { "-nonews" });
884    }
885   
886    /**
887    * waits for Swing event dispatch queue to empty
888    */
 
889  0 toggle synchronized void waitForSwing()
890    {
891  0 try
892    {
893  0 EventQueue.invokeAndWait(new Runnable()
894    {
 
895  0 toggle @Override
896    public void run()
897    {
898    }
899    });
900    } catch (InterruptedException | InvocationTargetException e)
901    {
902  0 e.printStackTrace();
903    }
904    }
905    }