/* * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$) * Copyright (C) $$Year-Rel$$ The Jalview Authors * * This file is part of Jalview. * * Jalview is free software: you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation, either version 3 * of the License, or (at your option) any later version. * * Jalview is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty * of MERCHANTABILITY or FITNESS FOR A PARTICULAR * PURPOSE. See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Jalview. If not, see . * The Jalview Authors are detailed in the 'AUTHORS' file. */ package jalview.viewmodel; import jalview.datamodel.ColumnSelection; import jalview.datamodel.HiddenSequences; import java.awt.Graphics; public class OverviewDimensions { // Default width and height values private static final int DEFAULT_GRAPH_HEIGHT = 20; private static final int MAX_WIDTH = 400; private static final int MIN_WIDTH = 120; private static final int MIN_SEQ_HEIGHT = 40; private static final int MAX_SEQ_HEIGHT = 300; // width of the overview panel private int width; // height of sequences part of the overview panel private int sequencesHeight; // height of the graphs part of the overview panel private int graphHeight = DEFAULT_GRAPH_HEIGHT; // dimensions of box outlining current extent of view in alignment panel // location of left side of box private int boxX = -1; // location of bottom of box private int boxY = -1; // width of box private int boxWidth = -1; // height of box private int boxHeight = -1; // scroll position in viewport corresponding to boxX private int scrollCol = -1; // scroll position in viewport corresponding to boxY private int scrollRow = -1; /** * Create an OverviewDimensions object * * @param ranges * positional properties of the viewport * @param showAnnotationPanel * true if the annotation panel is to be shown, false otherwise */ public OverviewDimensions(ViewportRanges ranges, boolean showAnnotationPanel) { // scale the initial size of overviewpanel to shape of alignment float initialScale = (float) ranges.getAbsoluteAlignmentWidth() / (float) ranges.getAbsoluteAlignmentHeight(); if (!showAnnotationPanel) { graphHeight = 0; } if (ranges.getAbsoluteAlignmentWidth() > ranges .getAbsoluteAlignmentHeight()) { // wider width = MAX_WIDTH; sequencesHeight = Math.round(MAX_WIDTH / initialScale); if (sequencesHeight < MIN_SEQ_HEIGHT) { sequencesHeight = MIN_SEQ_HEIGHT; } } else { // taller width = Math.round(MAX_WIDTH * initialScale); sequencesHeight = MAX_SEQ_HEIGHT; if (width < MIN_WIDTH) { width = MIN_WIDTH; } } } /** * Check box dimensions and scroll positions and correct if necessary * * @param mousex * x position in overview panel * @param mousey * y position in overview panel * @param hiddenSeqs * hidden sequences * @param hiddenCols * hidden columns * @param ranges * viewport position properties */ public void updateViewportFromMouse(int mousex, int mousey, HiddenSequences hiddenSeqs, ColumnSelection hiddenCols, ViewportRanges ranges) { int x = mousex; int y = mousey; int alwidth = ranges.getAbsoluteAlignmentWidth(); int alheight = ranges.getAbsoluteAlignmentHeight(); if (x < 0) { x = 0; } if (y < 0) { y = 0; } // // Convert x value to residue position // // need to determine where scrollCol should be, given x // to do this also need to know width of viewport, and some hidden column // correction // convert x to residues - this is an absolute position int xAsRes = Math.round((float) x * alwidth / width); // get viewport width in residues int vpwidth = ranges.getEndRes() - ranges.getStartRes() + 1; // get where x should be when accounting for hidden cols // if x is in a hidden col region, shift to left - but we still need // absolute position // so convert back after getting visible region position int visXAsRes = hiddenCols.findColumnPosition(xAsRes); // check in case we went off the edge of the alignment int visAlignWidth = hiddenCols.findColumnPosition(alwidth - 1); if (visXAsRes + vpwidth - 1 > visAlignWidth) { // went past the end of the alignment, adjust backwards // if last position was before the end of the alignment, need to update if ((scrollCol + vpwidth - 1) < visAlignWidth) { visXAsRes = hiddenCols.findColumnPosition(hiddenCols .subtractVisibleColumns(vpwidth - 1, alwidth - 1)); } else { visXAsRes = scrollCol; } } // // Convert y value to sequence position // // convert y to residues int yAsSeq = Math.round((float) y * alheight / sequencesHeight); // get viewport height in sequences // add 1 because height includes both endSeq and startSeq int vpheight = ranges.getEndSeq() - ranges.getStartSeq() + 1; // get where y should be when accounting for hidden rows // if y is in a hidden row region, shift up - but we still need absolute // position, // so convert back after getting visible region position yAsSeq = hiddenSeqs.adjustForHiddenSeqs(hiddenSeqs .findIndexWithoutHiddenSeqs(yAsSeq)); // check in case we went off the edge of the alignment int visAlignHeight = hiddenSeqs.findIndexWithoutHiddenSeqs(alheight); int visYAsRes = hiddenSeqs.findIndexWithoutHiddenSeqs(yAsSeq); if (visYAsRes + vpheight - 1 > visAlignHeight) { // went past the end of the alignment, adjust backwards if ((scrollRow + vpheight - 1) < visAlignHeight) { visYAsRes = hiddenSeqs.findIndexWithoutHiddenSeqs(hiddenSeqs .subtractVisibleRows(vpheight - 1, alheight - 1)); } else { visYAsRes = scrollRow; } } // update scroll values scrollCol = visXAsRes; scrollRow = visYAsRes; } /** * Update the overview panel box when the associated alignment panel is * changed * * @param hiddenSeqs * hidden sequences * @param hiddenCols * hidden columns * @param ranges * viewport position properties */ public void setBoxPosition(HiddenSequences hiddenSeqs, ColumnSelection hiddenCols, ViewportRanges ranges) { int alwidth = ranges.getAbsoluteAlignmentWidth(); int alheight = ranges.getAbsoluteAlignmentHeight(); // work with absolute values of startRes and endRes int startRes = hiddenCols.adjustForHiddenColumns(ranges.getStartRes()); int endRes = hiddenCols.adjustForHiddenColumns(ranges.getEndRes()); // work with absolute values of startSeq and endSeq int startSeq = hiddenSeqs.adjustForHiddenSeqs(ranges.getStartSeq()); int endSeq = hiddenSeqs.adjustForHiddenSeqs(ranges.getEndSeq()); // boxX, boxY is the x,y location equivalent to startRes, startSeq boxX = Math.round((float) startRes * width / alwidth); boxY = Math.round((float) startSeq * sequencesHeight / alheight); // boxWidth is the width in residues translated to pixels // since the box includes both the start and end residues, add 1 to the // difference boxWidth = Math .round((float) (endRes - startRes + 1) * width / alwidth); // boxHeight is the height in sequences translated to pixels boxHeight = Math.round((float) (endSeq - startSeq + 1) * sequencesHeight / alheight); } /** * Draw the overview panel's viewport box on a graphics object * * @param g * the graphics object to draw on */ public void drawBox(Graphics g) { g.drawRect(boxX, boxY, boxWidth, boxHeight); g.drawRect(boxX + 1, boxY + 1, boxWidth - 2, boxHeight - 2); } public int getScrollCol() { return scrollCol; } public int getScrollRow() { return scrollRow; } // TODO should be removed, when unit test has mock Graphics object available // to check boxX/boxY public int getBoxX() { return boxX; } // TODO should be removed, when unit test has mock Graphics object available // to check boxX/boxY public int getBoxY() { return boxY; } // TODO should be removed, when unit test has mock Graphics object available public int getBoxWidth() { return boxWidth; } // TODO should be removed, when unit test has mock Graphics object available public int getBoxHeight() { return boxHeight; } public void setWidth(int w) { width = w; } public void setHeight(int h) { sequencesHeight = h - graphHeight; } public int getWidth() { return width; } public int getHeight() { return sequencesHeight + graphHeight; } public int getSequencesHeight() { return sequencesHeight; } public int getGraphHeight() { return graphHeight; } }