1 package jalview.renderer;
3 import java.util.Iterator;
5 import jalview.datamodel.ColumnSelection;
6 import jalview.datamodel.ContactListI;
7 import jalview.datamodel.HiddenColumns;
8 import jalview.renderer.ContactGeometry.contactInterval;
11 * encapsulate logic for mapping between positions in a ContactList and their
12 * rendered representation in a given number of pixels.
17 public class ContactGeometry
20 final ContactListI contacts;
22 final int pixels_step;
24 final double contacts_per_pixel;
26 final int contact_height;
28 final int graphHeight;
30 public ContactGeometry(final ContactListI contacts, int graphHeight)
32 this.contacts=contacts;
33 this.graphHeight = graphHeight;
34 contact_height = contacts.getContactHeight();
35 // fractional number of contacts covering each pixel
36 contacts_per_pixel = (graphHeight < 1) ? contact_height
37 : ((double) contact_height) / ((double) graphHeight);
39 if (contacts_per_pixel >= 1)
41 // many contacts rendered per pixel
46 // pixel height for each contact
47 pixels_step = (int) Math
48 .ceil(((double) graphHeight) / (double) contact_height);
52 public class contactInterval
54 public contactInterval(int cStart, int cEnd, int pStart, int pEnd)
62 // range on contact list
63 public final int cStart;
65 public final int cEnd;
68 public final int pStart;
70 public final int pEnd;
75 * @param columnSelection
77 * @param visibleOnly - when true, only test intersection of visible columns given matrix range
78 * @return true if the range on the matrix specified by ci intersects with selected columns in the ContactListI's reference frame.
81 boolean intersects(contactInterval ci,ColumnSelection columnSelection, HiddenColumns hiddenColumns, boolean visibleOnly) {
82 boolean rowsel = false;
83 final int[] mappedRange = contacts.getMappedPositionsFor(ci.cStart, ci.cEnd);
84 if (mappedRange==null)
88 boolean containsHidden=false;
89 if (visibleOnly && hiddenColumns!=null && hiddenColumns.hasHiddenColumns())
91 // TODO: turn into function on hiddenColumns and create test !!
92 Iterator<int[]> viscont = hiddenColumns
93 .getVisContigsIterator(mappedRange[0], mappedRange[1], false);
94 containsHidden = !viscont.hasNext();
97 for (int[] interval=viscont.next();viscont.hasNext();
98 rowsel |= columnSelection.intersects(interval[0],interval[1]))
104 // if containsHidden is true mappedRange is not visible
107 rowsel = columnSelection.intersects(mappedRange[0], mappedRange[1]);
120 public contactInterval mapFor(int pStart, int pEnd)
122 int cStart = (int) Math.floor(pStart * contacts_per_pixel);
123 contactInterval ci = new contactInterval(cStart,
124 (int) Math.min(contact_height,
126 cStart + (pEnd - pStart) * contacts_per_pixel)),
133 * return the cell containing given pixel
136 * @return range for pCEntre
138 public contactInterval mapFor(int pCentre)
140 int pStart = Math.max(pCentre - pixels_step, 0);
141 int pEnd = Math.min(pStart + pixels_step, graphHeight);
142 int cStart = (int) Math.floor(pStart * contacts_per_pixel);
143 contactInterval ci = new contactInterval(cStart,
144 (int) Math.min(contact_height,
145 Math.ceil(cStart + (pixels_step) * contacts_per_pixel)),
151 public Iterator<contactInterval> iterateOverContactIntervals(
154 // NOT YET IMPLEMENTED
156 // int cstart = 0, cend;
159 // eht = y2 - graphHeight; ht >= eht; ht -= pixels_step)
161 // cstart = (int) Math.floor(((double) y2 - ht) * contacts_per_pixel);
162 // cend = (int) Math.min(contact_height,
163 // Math.ceil(cstart + contacts_per_pixel * pixels_step));
165 // return new Iterator<contactIntervals>() {
168 // public boolean hasNext()
170 // // TODO Auto-generated method stub
175 // public contactIntervals next()
177 // // TODO Auto-generated method stub