📄 sequence_display.cpp
字号:
dynamic_cast<const DisplayRowFromAlignment *>(displayRow); if (alnRow) { int blockNum = alnRow->alignment->GetAlignedBlockNumber(column); int rowNum = 0; // get apparent row number (crude!) for (int r=0; r<=row; ++r) { const DisplayRowFromAlignment *aRow = dynamic_cast<const DisplayRowFromAlignment *>(rows[r]); if (aRow && aRow->alignment == alnRow->alignment) ++rowNum; } if (blockNum > 0) status.Printf("Block %i, Row %i", blockNum, rowNum); else status.Printf("Row %i", rowNum); if (alnRow->alignment->GetRowStatusLine(alnRow->row).size() > 0) { status += " ; "; status += alnRow->alignment->GetRowStatusLine(alnRow->row).c_str(); } } } // else show length and description if we're in the title area else if (column < 0) { sequence = displayRow->GetSequence(); if (sequence) { idLoc.Printf("length %i", sequence->Length()); status = sequence->description.c_str(); } } } (*viewerWindow)->SetStatusText(idLoc, 0); (*viewerWindow)->SetStatusText(status, 1); }}void SequenceDisplay::UpdateAfterEdit(const BlockMultipleAlignment *forAlignment){ UpdateBlockBoundaryRow(forAlignment); UpdateMaxRowWidth(); // in case alignment width has changed (*viewerWindow)->viewer->Save(); // make undoable (*viewerWindow)->UpdateDisplay(this); if ((*viewerWindow)->AlwaysSyncStructures()) (*viewerWindow)->SyncStructures();}bool SequenceDisplay::MouseDown(int column, int row, unsigned int controls){ TRACEMSG("got MouseDown at col:" << column << " row:" << row); // process events in title area (launch of browser for entrez page on a sequence) if (column < 0 && row >= 0 && row < NRows()) { const Sequence *seq = rows[row]->GetSequence(); if (seq) seq->LaunchWebBrowserWithInfo(); return false; } shiftDown = ((controls & ViewableAlignment::eShiftDown) > 0); controlDown = ((controls &#ifdef __WXMAC__ // on Mac, can't do ctrl-clicks, so use meta instead ViewableAlignment::eAltOrMetaDown#else ViewableAlignment::eControlDown#endif ) > 0); if (!shiftDown && !controlDown && column == -1) GlobalMessenger()->RemoveAllHighlights(true); // process events in sequence area BlockMultipleAlignment *alignment = GetAlignmentForRow(row); if (alignment && column >= 0) { // operations for any viewer window if ((*viewerWindow)->DoSplitBlock()) { if (alignment->SplitBlock(column)) { if (!controlDown) (*viewerWindow)->SplitBlockOff(); UpdateAfterEdit(alignment); } return false; } if ((*viewerWindow)->DoDeleteBlock()) { if (alignment->DeleteBlock(column)) { if (!controlDown) (*viewerWindow)->DeleteBlockOff(); UpdateAfterEdit(alignment); } return false; } // operations specific to the sequence window SequenceViewerWindow *sequenceWindow = dynamic_cast<SequenceViewerWindow*>(*viewerWindow); if (sequenceWindow && row >= 0) { if (sequenceWindow->DoMarkBlock()) { if (alignment->MarkBlock(column)) { if (!controlDown) sequenceWindow->MarkBlockOff(); GlobalMessenger()->PostRedrawSequenceViewer(sequenceWindow->sequenceViewer); } return false; } if (sequenceWindow->DoProximitySort()) { if (ProximitySort(row)) { sequenceWindow->ProximitySortOff(); GlobalMessenger()->PostRedrawSequenceViewer(sequenceWindow->sequenceViewer); } return false; } if (sequenceWindow->DoRealignRow() || sequenceWindow->DoDeleteRow()) { DisplayRowFromAlignment *selectedRow = dynamic_cast<DisplayRowFromAlignment*>(rows[row]); if (!selectedRow || selectedRow->row == 0 || !selectedRow->alignment) { WARNINGMSG("Can't delete/realign that row..."); return false; } if (sequenceWindow->DoRealignRow()) { vector < int > selectedSlaves(1); selectedSlaves[0] = selectedRow->row; sequenceWindow->sequenceViewer->alignmentManager-> RealignSlaveSequences(alignment, selectedSlaves); if (!controlDown) sequenceWindow->RealignRowOff(); return false; } if (sequenceWindow->DoDeleteRow()) { if (alignment->NRows() <= 2) { WARNINGMSG("Can't delete that row..."); return false; } // in case we need to redraw molecule associated with removed row const Molecule *molecule = alignment->GetSequenceOfRow(selectedRow->row)->molecule; // delete row based on alignment row # (not display row #); redraw molecule if (alignment->DeleteRow(selectedRow->row)) { // delete this row from the display, and update higher row #'s RowVector::iterator r, re = rows.end(), toDelete; for (r=rows.begin(); r!=re; ++r) { DisplayRowFromAlignment *currentARow = dynamic_cast<DisplayRowFromAlignment*>(*r); if (!currentARow) continue; else if (currentARow->row > selectedRow->row) (currentARow->row)--; else if (currentARow == selectedRow) toDelete = r; } delete *toDelete; rows.erase(toDelete); if (!controlDown) sequenceWindow->DeleteRowOff(); UpdateAfterEdit(alignment); if (molecule && sequenceWindow->AlwaysSyncStructures()) GlobalMessenger()->PostRedrawMolecule(molecule); } return false; } } } // operations specific to the update window UpdateViewerWindow *updateWindow = dynamic_cast<UpdateViewerWindow*>(*viewerWindow); if (updateWindow && row >= 0) { // delete all blocks if (updateWindow->DoDeleteAllBlocks()) { if (alignment->DeleteAllBlocks()) { if (!controlDown) updateWindow->DeleteAllBlocksOff(); UpdateAfterEdit(alignment); } return false; } // thread single if (updateWindow->DoThreadSingle()) { if (!updateWindow->updateViewer->alignmentManager->GetCurrentMultipleAlignment()) { ERRORMSG("Can't run threader without existing core alignment"); return false; } // get threader options globalThreaderOptions.nRandomStarts = Threader::EstimateNRandomStarts( updateWindow->updateViewer->alignmentManager->GetCurrentMultipleAlignment(), alignment); ThreaderOptionsDialog optDialog(updateWindow, globalThreaderOptions); if (optDialog.ShowModal() == wxCANCEL) return false; // user cancelled if (!optDialog.GetValues(&globalThreaderOptions)) { ERRORMSG("Error retrieving options values from dialog"); return false; } updateWindow->updateViewer->alignmentManager->ThreadUpdate(globalThreaderOptions, alignment); updateWindow->ThreadSingleOff(); return false; } // BLAST single if (updateWindow->DoBlastSingle()) { updateWindow->updateViewer->BlastUpdate(alignment, false); if (!controlDown) updateWindow->BlastSingleOff(); return false; } // BLAST/PSSM single if (updateWindow->DoBlastPSSMSingle()) { updateWindow->updateViewer->BlastUpdate(alignment, true); if (!controlDown) updateWindow->BlastPSSMSingleOff(); return false; } // BLAST neighbor single if (updateWindow->DoBlastNeighborSingle()) { updateWindow->updateViewer->BlastNeighbor(alignment); if (!controlDown) updateWindow->BlastNeighborSingleOff(); return false; } // Block align single if (updateWindow->DoBlockAlignSingle()) { updateWindow->updateViewer->alignmentManager->BlockAlignUpdate(alignment); if (!controlDown) updateWindow->BlockAlignSingleOff(); return false; } // set region (on slave sequence) if (updateWindow->DoSetRegion()) { // dialog uses 1-based sequence locations RegionDialog dialog(updateWindow, alignment->GetSequenceOfRow(1), alignment->alignSlaveFrom + 1, alignment->alignSlaveTo + 1); if (dialog.ShowModal() == wxOK) { int from, to; if (!dialog.GetValues(&from, &to)) { ERRORMSG("RegionDialog returned OK, but values invalid"); } else { TRACEMSG("set region (slave): " << from << " to " << to); alignment->alignSlaveFrom = from - 1; alignment->alignSlaveTo = to - 1; } if (!controlDown) updateWindow->SetRegionOff(); } return false; } // merge single if (updateWindow->DoMergeSingle()) { AlignmentManager::UpdateMap single; single[alignment] = true; updateWindow->updateViewer->alignmentManager->MergeUpdates(single, false); if (!controlDown) updateWindow->MergeSingleOff(); return false; } // merge neighbor if (updateWindow->DoMergeNeighbor()) { AlignmentManager::UpdateMap single; single[alignment] = true; updateWindow->updateViewer->alignmentManager->MergeUpdates(single, true); if (!controlDown) updateWindow->MergeNeighborOff(); return false; } // delete single if (updateWindow->DoDeleteSingle()) { updateWindow->updateViewer->DeleteAlignment(alignment); if (!controlDown) updateWindow->DeleteSingleOff(); return false; } } } return true;}void SequenceDisplay::SelectedRectangle(int columnLeft, int rowTop, int columnRight, int rowBottom){ TRACEMSG("got SelectedRectangle " << columnLeft << ',' << rowTop << " to " << columnRight << ',' << rowBottom); BlockMultipleAlignment::eUnalignedJustification justification = (*viewerWindow)->GetCurrentJustification(); BlockMultipleAlignment *alignment = GetAlignmentForRow(rowTop); if (alignment && alignment == GetAlignmentForRow(rowBottom)) { if ((*viewerWindow)->DoMergeBlocks()) { if (alignment->MergeBlocks(columnLeft, columnRight)) { if (!controlDown) (*viewerWindow)->MergeBlocksOff(); UpdateAfterEdit(alignment); } return; } if ((*viewerWindow)->DoCreateBlock()) { if (alignment->CreateBlock(columnLeft, columnRight, justification)) { if (!controlDown) (*viewerWindow)->CreateBlockOff(); UpdateAfterEdit(alignment); } return; } } if (!shiftDown && !controlDown) GlobalMessenger()->RemoveAllHighlights(true); for (int i=rowTop; i<=rowBottom; ++i) rows[i]->SelectedRange(columnLeft, columnRight, justification, controlDown); // toggle if control down}void SequenceDisplay::DraggedCell(int columnFrom, int rowFrom, int columnTo, int rowTo){ // special shift-by-one if shift/ctrl click w/ no drag if (columnFrom == columnTo && rowFrom == rowTo) { if (shiftDown && columnTo > 0) --columnTo; else if (controlDown && columnTo < maxRowWidth-1) ++columnTo; } TRACEMSG("got DraggedCell " << columnFrom << ',' << rowFrom << " to " << columnTo << ',' << rowTo); if (rowFrom == rowTo && columnFrom == columnTo) return; if (rowFrom != rowTo && columnFrom != columnTo) return; // ignore diagonal drag if (columnFrom != columnTo) { BlockMultipleAlignment *alignment = GetAlignmentForRow(rowFrom); if (alignment) { // process horizontal drag on special block boundary row DisplayRowFromString *strRow = dynamic_cast<DisplayRowFromString*>(rows[rowFrom]); if (strRow) { wxString title; wxColour ignored; if (GetRowTitle(rowFrom, &title, &ignored) && title == blockBoundaryStringTitle.c_str()) { char ch = strRow->theString[columnFrom]; if (ch == blockRightEdgeChar || ch == blockLeftEdgeChar || ch == blockOneColumnChar) { if (alignment->MoveBlockBoundary(columnFrom, columnTo)) UpdateAfterEdit(alignment); } } return; } // process drag on regular row - block row shift DisplayRowFromAlignment *alnRow = dynamic_cast<DisplayRowFromAlignment*>(rows[rowFrom]); if (alnRow) { if (alignment->ShiftRow(alnRow->row, columnFrom, columnTo, (*viewerWindow)->GetCurrentJustification())) UpdateAfterEdit(alignment); return; } } return; } // use vertical drag to reorder row; move rowFrom so that it ends up just before the // initial rowTo row if (rowFrom == rowTo - 1) return; if (rowTo > rowFrom) --rowTo; RowVector newRows(rows); DisplayRow *row = newRows[rowFrom]; RowVector::iterator r = newRows.begin(); int i; for (i=0; i<rowFrom; ++i) ++r; // get iterator for position rowFrom newRows.erase(r); for (r=newRows.begin(), i=0; i<rowTo; ++i) ++r; // get iterator for position rowTo newRows.insert(r, row); // make sure that the master row of an alignment is still first bool masterOK = true; for (i=0; i<newRows.size(); ++i) { DisplayRowFromAlignment *alnRow = dynamic_cast<DisplayRowFromAlignment*>(newRows[i]); if (alnRow) { if (alnRow->row != 0) { WARNINGMSG("The first alignment row must always be the master sequence"); masterOK = false; } break; }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -