/* * Jalview - A Sequence Alignment Editor and Viewer (Version 2.8.2b1) * Copyright (C) 2014 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.controller; import java.awt.Color; import java.util.BitSet; import java.util.List; import jalview.api.AlignViewControllerGuiI; import jalview.api.AlignViewControllerI; import jalview.api.AlignViewportI; import jalview.api.AlignmentViewPanel; import jalview.datamodel.AlignmentI; import jalview.datamodel.AnnotatedCollectionI; import jalview.datamodel.ColumnSelection; import jalview.datamodel.SequenceCollectionI; import jalview.datamodel.SequenceFeature; import jalview.datamodel.SequenceGroup; import jalview.datamodel.SequenceI; import jalview.util.MessageManager; public class AlignViewController implements AlignViewControllerI { AlignViewportI viewport = null; AlignmentViewPanel alignPanel = null; /** * the GUI container that is handling interactions with the user */ private AlignViewControllerGuiI avcg; @Override protected void finalize() throws Throwable { viewport = null; alignPanel = null; avcg = null; }; public AlignViewController(AlignViewControllerGuiI alignFrame, AlignViewportI viewport, AlignmentViewPanel alignPanel) { this.avcg = alignFrame; this.viewport = viewport; this.alignPanel = alignPanel; } @Override public void setViewportAndAlignmentPanel(AlignViewportI viewport, AlignmentViewPanel alignPanel) { this.alignPanel = alignPanel; this.viewport = viewport; } @Override public boolean makeGroupsFromSelection() { if (viewport.getSelectionGroup() != null) { SequenceGroup[] gps = jalview.analysis.Grouping.makeGroupsFrom( viewport.getSequenceSelection(), viewport.getAlignmentView(true).getSequenceStrings( viewport.getGapCharacter()), viewport.getAlignment() .getGroups()); viewport.getAlignment().deleteAllGroups(); viewport.clearSequenceColours(); viewport.setSelectionGroup(null); // set view properties for each group for (int g = 0; g < gps.length; g++) { // gps[g].setShowunconserved(viewport.getShowUnconserved()); gps[g].setshowSequenceLogo(viewport.isShowSequenceLogo()); viewport.getAlignment().addGroup(gps[g]); Color col = new Color((int) (Math.random() * 255), (int) (Math.random() * 255), (int) (Math.random() * 255)); col = col.brighter(); for (SequenceI sq : gps[g].getSequences(null)) viewport.setSequenceColour(sq, col); } return true; } return false; } @Override public boolean createGroup() { SequenceGroup sg = viewport.getSelectionGroup(); if (sg != null) { viewport.getAlignment().addGroup(sg); return true; } return false; } @Override public boolean unGroup() { SequenceGroup sg = viewport.getSelectionGroup(); if (sg != null) { viewport.getAlignment().deleteGroup(sg); return true; } return false; } @Override public boolean deleteGroups() { if (viewport.getAlignment().getGroups() != null && viewport.getAlignment().getGroups().size() > 0) { viewport.getAlignment().deleteAllGroups(); viewport.clearSequenceColours(); viewport.setSelectionGroup(null); return true; } return false; } @Override public boolean markColumnsContainingFeatures(boolean invert, boolean extendCurrent, boolean toggle, String featureType) { // JBPNote this routine could also mark rows, not just columns. // need a decent query structure to allow all types of feature searches BitSet bs = new BitSet(); int alw, alStart; SequenceCollectionI sqcol = (viewport.getSelectionGroup() == null ? viewport .getAlignment() : viewport.getSelectionGroup()); alStart = sqcol.getStartRes(); alw = sqcol.getEndRes() + 1; List seqs = sqcol.getSequences(); int nseq = 0; for (SequenceI sq : seqs) { int tfeat = 0; if (sq != null) { SequenceI dsq = sq.getDatasetSequence(); while (dsq.getDatasetSequence() != null) { dsq = dsq.getDatasetSequence(); } ; SequenceFeature[] sf = dsq.getSequenceFeatures(); if (sf != null) { int ist = sq.findIndex(sq.getStart()); int iend = sq.findIndex(sq.getEnd()); if (iend < alStart || ist > alw) { // sequence not in region continue; } for (SequenceFeature sfpos : sf) { // future functionalty - featureType == null means mark columns // containing all displayed features if (sfpos != null && (featureType.equals(sfpos.getType()))) { tfeat++; // optimisation - could consider 'spos,apos' like cursor argument // - findIndex wastes time by starting from first character and // counting int i = sq.findIndex(sfpos.getBegin()); int j = sq.findIndex(sfpos.getEnd()); if (j < alStart || i > alw) { // feature is outside selected region continue; } if (i < alStart) { i = alStart; } if (i < ist) { i = ist; } if (j > alw) { j = alw; } for (; i <= j; i++) { bs.set(i - 1); } } } } if (tfeat > 0) { nseq++; } } } ColumnSelection cs = viewport.getColumnSelection(); if (bs.cardinality() > 0 || invert) { if (cs == null) { cs = new ColumnSelection(); } else { if (!extendCurrent) { cs.clear(); } } if (invert) { // invert only in the currently selected sequence region for (int i = bs.nextClearBit(alStart), ibs = bs.nextSetBit(alStart); i >= alStart && i < (alw);) { if (ibs < 0 || i < ibs) { if (toggle && cs.contains(i)) { cs.removeElement(i++); } else { cs.addElement(i++); } } else { i = bs.nextClearBit(ibs); ibs = bs.nextSetBit(i); } } } else { for (int i = bs.nextSetBit(alStart); i >= alStart; i = bs .nextSetBit(i + 1)) { if (toggle && cs.contains(i)) { cs.removeElement(i); } else { cs.addElement(i); } } } viewport.setColumnSelection(cs); alignPanel.paintAlignment(true); avcg.setStatus(MessageManager.formatMessage("label.view_controller_toggled_marked", new String[]{ (toggle ? MessageManager.getString("label.toggled") : MessageManager.getString("label.marked")), (invert ? (Integer.valueOf((alw - alStart) - bs.cardinality()).toString()):(Integer.valueOf(bs.cardinality()).toString())), featureType, Integer.valueOf(nseq).toString() })); return true; } else { avcg.setStatus(MessageManager.formatMessage("label.no_feature_of_type_found", new String[]{featureType})); if (!extendCurrent && cs != null) { cs.clear(); alignPanel.paintAlignment(true); } return false; } } }