/* * 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.api.AlignViewportI; 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; private AlignViewportI av; private float scalew = 1f; private float scaleh = 1f; // 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; private int scrollCol = -1; private int scrollRow = -1; public OverviewDimensions(AlignViewportI avi) { this.av = avi; // scale the initial size of overviewpanel to shape of alignment float initialScale = (float) av.getAlignment().getWidth() / (float) av.getAlignment().getHeight(); // TODO: in applet this was getSequenceConsensusHash() // check if it makes any functional difference if (av.getAlignmentConservationAnnotation() == null) { graphHeight = 0; } if (av.getAlignment().getWidth() > av.getAlignment().getHeight()) { // wider width = MAX_WIDTH; sequencesHeight = (int) (MAX_WIDTH / initialScale); if (sequencesHeight < MIN_SEQ_HEIGHT) { sequencesHeight = MIN_SEQ_HEIGHT; } } else { // taller width = (int) (MAX_WIDTH * initialScale); sequencesHeight = MAX_SEQ_HEIGHT; if (width < MIN_WIDTH) { width = MIN_WIDTH; } } } /** * Check box dimensions and scroll positions and correct if necessary */ public void setBoxPositionByMouse(int x, int y) { boxX = x; boxY = y; if (boxY < 0) { boxY = 0; } else if (boxY > (sequencesHeight - boxHeight)) { boxY = sequencesHeight - boxHeight + 1; } if (boxX < 0) { boxX = 0; } else if (boxX > (width - boxWidth)) { if (av.hasHiddenColumns()) { // Try smallest possible box boxWidth = (int) ((av.getEndRes() - av.getStartRes() + 1) * av.getCharWidth() * scalew); } boxX = width - boxWidth; } scrollCol = (int) (boxX / scalew / av.getCharWidth()); scrollRow = (int) (boxY / scaleh / av.getCharHeight()); if (av.hasHiddenColumns()) { if (!av.getColumnSelection().isVisible(scrollCol)) { return; } scrollCol = av.getColumnSelection().findColumnPosition(scrollCol); } if (av.hasHiddenRows()) { scrollRow = av.getAlignment().getHiddenSequences() .findIndexWithoutHiddenSeqs(scrollRow); } } /** * Update the overview panel box when the associated alignment panel is * changed * */ public void setBoxPosition() { updateScales(); int startRes = av.getStartRes(); int endRes = av.getEndRes(); if (av.hasHiddenColumns()) { startRes = av.getColumnSelection().adjustForHiddenColumns(startRes); endRes = av.getColumnSelection().adjustForHiddenColumns(endRes); } int startSeq = av.getStartSeq(); int endSeq = av.getEndSeq(); if (av.hasHiddenRows()) { startSeq = av.getAlignment().getHiddenSequences() .adjustForHiddenSeqs(startSeq); endSeq = av.getAlignment().getHiddenSequences() .adjustForHiddenSeqs(endSeq); } boxX = (int) (startRes * av.getCharWidth() * scalew); boxY = (int) (startSeq * av.getCharHeight() * scaleh); boxWidth = (int) ((endRes - startRes + 1) * av.getCharWidth() * scalew); boxHeight = (int) ((endSeq - startSeq) * av.getCharHeight() * scaleh); } /** * Update width and height scales in terms of the alignment width and height */ public void updateScales() { int alwidth = av.getAlignment().getWidth(); int alheight = av.getAlignment().getHeight() + av.getAlignment().getHiddenSequences().getSize(); int fullsizeWidth = alwidth * av.getCharWidth(); int fullsizeHeight = alheight * av.getCharHeight(); scalew = (float) width / fullsizeWidth; scaleh = (float) sequencesHeight / fullsizeHeight; } /** * 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); } // don't like this, scroll vals are separate from setting code 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; } public int getBoxWidth() { return boxWidth; } public int getBoxHeight() { return boxHeight; } public void setBoxX(int x) { boxX = x; } public void setBoxY(int y) { boxY = y; } 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; } }