/** * Get component to be rendered, if pos outside of current range getFeatureAtPosition and reset * currentRange, if feature is non null and not an instance of FeatureSetI then its an exon, and * set isExon flag */ public Component getBaseComponent(int position, TierI tier, Orientation o) { transcript = null; int bp = tier.getBasePair(position); int oldPos = position; // We need to change the position if dealing with aa view if (tier.getType() == SequenceType.AA) { int offset = getOffset(position, tier); bp += offset * tier.getStrand().toInt(); position = tier.getPosition(bp); } char base = tier.charAt(position); if (tier.featureExsitsAt(position, TierI.Level.BOTTOM)) { this.state = State.EXON; SeqFeatureI feature = tier.featureAt(position, TierI.Level.BOTTOM); Transcript parentClone = null; Transcript otherParentClone = null; if (tier.getType() == SequenceType.AA && feature.getParent() != null && feature.getParent().isTranscript()) { FeatureSetI parent = feature.getParent(); int index = parent.getFeatureIndex(feature); int start = parent.getEnd(); // the transcript start might be different than the lowest exon start // when in the middle of an edit if (parent.canHaveChildren()) { for (int i = 0; i < parent.size(); i++) { SeqFeatureI sf = parent.getFeatureAt(i); if ((Strand.valueOf(sf.getStrand()) == Strand.FORWARD && sf.getStart() < start) || (Strand.valueOf(sf.getStrand()) == Strand.REVERSE && sf.getStart() > start)) start = sf.getStart(); } } int translationStart = parent.getTranslationStart(); int translationEnd = parent.getTranslationEnd(); int translationPos = parent.getFeaturePosition(translationStart); int oldstart = start; start += ((translationPos - 1) % 3) * parent.getStrand(); // Tring to avoid all the recalculation... if (feature.getParent() == currentParent && start == currentStart && featureStart == feature.getStart() && featureEnd == feature.getEnd()) { parentClone = currentParentClone; otherParentClone = currentParentClone2; } else { // need to get a full translation so that we can get the amino acids // in the UTR region parentClone = (Transcript) feature.getParent().clone(); otherParentClone = (Transcript) feature.getParent().clone(); if (!parentClone.setTranslationStart(start)) { start = oldstart; TranslationI cds = otherParentClone.getTranslation(); cds.calcTranslationStartForLongestPeptide(); translationStart = otherParentClone.getTranslationStart(); translationPos = otherParentClone.getFeaturePosition(translationStart); start += ((translationPos - 1) % 3) * otherParentClone.getStrand(); parentClone.setTranslationStart(start); } parentClone.setTranslationEnd(parentClone.getEnd()); parentClone.setPeptideSequence(null); String translation = parentClone.translate(); SequenceI sequence = parentClone.getPeptideSequence(); currentParent = (Transcript) feature.getParent(); currentParentClone = parentClone; currentParentClone2 = otherParentClone; currentStart = start; featureStart = feature.getStart(); featureEnd = feature.getEnd(); if (otherParentClone.getFeatureContaining(translationEnd) == null) { TranslationI cds = otherParentClone.getTranslation(); cds.setTranslationEndFromStart(); } } SeqFeatureI sf = parentClone.getFeatureAt(index); if (bp >= sf.getLow() && bp <= sf.getHigh()) { base = getPeptide(bp, sf); } else { base = '\0'; } if (otherParentClone != null) { feature = otherParentClone.getFeatureAt(index); } } else if (tier.getType() == SequenceType.AA && feature.getParent() != null && !feature.getParent().isTranscript()) { base = '\0'; } if (isUTR(bp, feature, tier)) { this.state = State.UTR; } if (isTranslationStart(bp, feature)) { this.state = State.TRANSLATION_START; } if (isTranslationEnd(bp, feature)) { this.state = State.TRANSLATION_END; } // Can have an error or a shift on a position but not both if (isSequencingErrorPosition(bp, feature, tier.getType())) { this.state = State.ERROR; // set base to the base of the new sequence? } if (isShiftPosition(bp, feature, tier.getType())) { this.state = State.SHIFT; } } else if (tier.featureExsitsAt(position, TierI.Level.TOP)) { SeqFeatureI feature = tier.featureAt(position, Level.TOP); this.state = State.INTRON; if (tier.getType() == SequenceType.AA) { base = '\0'; } int start = feature.getEnd(); int end = feature.getStart(); if (feature.canHaveChildren()) { for (int i = 0; i < feature.size(); i++) { SeqFeatureI sf = feature.getFeatureAt(i); if ((Strand.valueOf(sf.getStrand()) == Strand.FORWARD && sf.getStart() < start) || (Strand.valueOf(sf.getStrand()) == Strand.REVERSE && sf.getStart() > start)) start = sf.getStart(); if ((Strand.valueOf(sf.getStrand()) == Strand.FORWARD && sf.getEnd() > end) || (Strand.valueOf(sf.getStrand()) == Strand.REVERSE && sf.getEnd() < end)) end = sf.getEnd(); } } if (bp <= Math.min(start, end) || bp >= Math.max(start, end)) { this.state = State.OUT; base = '\0'; } } else { this.state = State.OUT; base = '\0'; } if (!(state == State.SHIFT || state == State.ERROR) && getRegionLow() <= position && position <= getRegionHigh()) { this.state = State.SELECTED; base = tier.charAt(oldPos); } init(base); return this; }
/** * If right mouse deselect base If end of feature drag notify AnnotationEditor (endRangeChange) * and recalc translation end from start */ public void mouseReleased(MouseEvent e) { // RIGHT MOUSE CLICK if (MouseButtonEvent.isRightMouseClick(e)) { BaseRenderer rend = baseEditorPanel.getRendererAt(tier); if (rend instanceof SelectableDNARenderer) { ((SelectableDNARenderer) rend).setTargetPos(-1, -1); baseEditorPanel.repaint(); } } // SEQ SELECT DRAG if (dragType == baseEditorPanel.SEQ_SELECT_DRAG) { SequenceI seq = baseEditorPanel.getSequenceForTier(startDragTier); int lowBP = baseEditorPanel.posToResidue(baseEditorPanel.selectLowPos()); int highBP = baseEditorPanel.posToResidue(baseEditorPanel.selectHighPos()); String sequence = seq.getResidues(lowBP, highBP); String header = " Arbitrary selection (" + seq.getName() + ": " + lowBP + "," + highBP + ")"; // controllingWindow.copySeqToClipboard(new Sequence (header, sequence)); ClipboardUtil.copySeqToClipboard(new Sequence(header, sequence)); resetDragState(); baseEditorPanel.repaint(); return; } // NOT SEQ SELECT DRAG else { // NOT DRAGGING - RETURN if (!MouseButtonEvent.isLeftMouseClick(e) || !dragging || dragFeature == null) { resetDragState(); return; } // DRAGGING ANNOT ENDS if (dragging && dragFeature != null && dragFeature.isAnnot()) { // NOTIFY ANNOTATION EDITOR (generates transaction) int oldStart = (preDragStartBasePair == -1) ? dragFeature.getStart() : preDragStartBasePair; int oldEnd = (preDragEndBasePair == -1) ? dragFeature.getEnd() : preDragEndBasePair; AnnotationEditor ae = baseEditorPanel.getAnnotationEditor(); ae.setAnnotTerminus( dragFeature.getAnnotatedFeature(), oldStart, oldEnd, dragFeature.getStart(), dragFeature.getEnd()); // RECALC CDS (if exon/transcript - not for 1 level annots) if (dragFeature.isExon() && dragFeature.getRefFeature() != null && (dragFeature.getRefFeature().isTranscript())) { // ExonI exon = (ExonI)dragFeature; // Transcript t = (Transcript)exon.getRefFeature(); SeqFeatureI transcript = dragFeature.getRefFeature(); TranslationI cds = transcript.getTranslation(); int transStart = transcript.getStart(); int cdsStart = cds.getTranslationStart(); boolean isForward = transcript.isForwardStrand(); if (cds.isMissing5prime() && ((isForward && transStart < cdsStart) || (!isForward && transStart > cdsStart))) { cds.calcTranslationStartForLongestPeptide(); // missing start } else { cds.setTranslationEndFromStart(); // got start - set end } } baseEditorPanel.repaint(); } } resetDragState(); baseEditorPanel.getCurationState().getSZAP().repaint(); }