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.ColumnSelection; import jalview.datamodel.SequenceFeature; import jalview.datamodel.SequenceGroup; import jalview.datamodel.SequenceI; 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, 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(); List seqs = viewport.getAlignment().getSequences(); int alw = viewport.getAlignment().getWidth(); 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) { 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 ist = sq.findIndex(sq.getStart()); if (i < ist) { i = ist; } int j = sq.findIndex(sfpos.getEnd()); if (j > alw) { j = alw; } for (; i <= j; i++) { bs.set(i - 1); } } } } if (tfeat > 0) { nseq++; } } } if (bs.cardinality() > 0 || invert) { ColumnSelection cs = viewport.getColumnSelection(); if (cs == null) { cs = new ColumnSelection(); } if (invert) { for (int i = bs.nextClearBit(0), ibs = bs.nextSetBit(0); i >= 0 && i < alw;) { if (ibs < 0 || i < ibs) { cs.addElement(i++); } else { i = bs.nextClearBit(ibs); ibs = bs.nextSetBit(i); } } } else { for (int i = bs.nextSetBit(0); i >= 0; i = bs.nextSetBit(i + 1)) { cs.addElement(i); } } viewport.setColumnSelection(cs); alignPanel.paintAlignment(true); avcg.setStatus("Marked " + (invert ? alw - bs.cardinality() : bs.cardinality()) + " columns containing features of type " + featureType + " across " + nseq); return true; } else { avcg.setStatus("No features of type " + featureType + " found."); return false; } } }