Date: Wed, 13 Apr 2016 11:29:46 +0000 (+0200)
Subject: Merge branch 'LibrAlign' into develop
X-Git-Tag: 4.0.0^2~30
X-Git-Url: https://dev.e-taxonomy.eu/gitweb/taxeditor.git/commitdiff_plain/d4e581eb9d7a1717edd1bb8d24f3c3374645bf69?hp=0aeb6effa85da754cd4efb48f0953b0bf2662243
Merge branch 'LibrAlign' into develop
---
diff --git a/.gitattributes b/.gitattributes
index c7b12732e..877a615a0 100644
--- a/.gitattributes
+++ b/.gitattributes
@@ -963,6 +963,10 @@ eu.etaxonomy.taxeditor.help/src/eu/etaxonomy/taxeditor/help/Activator.java -text
eu.etaxonomy.taxeditor.help/toc.xml -text
eu.etaxonomy.taxeditor.help/tocgettingstarted.xml -text
eu.etaxonomy.taxeditor.help/tocnameparser.xml -text
+eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/editor/AlignmentEditorActionUpdater.java -text
+eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AbstractFocusedAlignmentAreaHandler.java -text
+eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorCutHandler.java -text
+eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorPasteHandler.java -text
eu.etaxonomy.taxeditor.navigation/.classpath -text
eu.etaxonomy.taxeditor.navigation/.project -text
eu.etaxonomy.taxeditor.navigation/META-INF/MANIFEST.MF -text
@@ -1984,4 +1988,4 @@ src/site/site.xml -text
eu.etaxonomy.taxeditor.cdmlib/.classpath merge=ours
eu.etaxonomy.taxeditor.cdmlib/build.properties merge=ours
eu.etaxonomy.taxeditor/eu.etaxonomy.taxeditor.product merge=ours
-eu.etaxonomy.taxeditor/eu.etaxonomy.taxeditor.product.with.jre merge=ours
\ No newline at end of file
+eu.etaxonomy.taxeditor/eu.etaxonomy.taxeditor.product.with.jre merge=ours
diff --git a/eu.etaxonomy.taxeditor.molecular/plugin.xml b/eu.etaxonomy.taxeditor.molecular/plugin.xml
index 27b08389f..78b734fd1 100644
--- a/eu.etaxonomy.taxeditor.molecular/plugin.xml
+++ b/eu.etaxonomy.taxeditor.molecular/plugin.xml
@@ -264,6 +264,42 @@
class="eu.etaxonomy.taxeditor.molecular.handler.ChangePherogramQualityOutputType"
commandId="eu.etaxonomy.taxeditor.molecular.pherogramComponent.changeQualityOutput">
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/editor/AlignmentEditor.java b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/editor/AlignmentEditor.java
index 4934d9a37..57608d5d8 100644
--- a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/editor/AlignmentEditor.java
+++ b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/editor/AlignmentEditor.java
@@ -10,6 +10,7 @@
package eu.etaxonomy.taxeditor.molecular.editor;
+import info.bioinfweb.commons.swt.SWTUtils;
import info.bioinfweb.libralign.alignmentarea.AlignmentArea;
import info.bioinfweb.libralign.alignmentarea.selection.SelectionModel;
import info.bioinfweb.libralign.alignmentarea.tokenpainter.NucleotideTokenPainter;
@@ -52,16 +53,16 @@ import java.util.TreeMap;
import org.biojava.bio.chromatogram.ChromatogramFactory;
import org.biojava.bio.chromatogram.UnsupportedChromatogramFormatException;
import org.eclipse.core.runtime.IProgressMonitor;
-import org.eclipse.jface.action.Action;
import org.eclipse.swt.SWT;
+import org.eclipse.swt.dnd.Clipboard;
import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Display;
import org.eclipse.ui.IActionBars;
import org.eclipse.ui.IEditorInput;
import org.eclipse.ui.IEditorPart;
import org.eclipse.ui.IEditorSite;
import org.eclipse.ui.PartInitException;
import org.eclipse.ui.PlatformUI;
-import org.eclipse.ui.actions.ActionFactory;
import org.eclipse.ui.commands.ICommandService;
import org.eclipse.ui.part.EditorPart;
@@ -128,13 +129,16 @@ public class AlignmentEditor extends EditorPart {
setDirty();
}
};
+ private final AlignmentEditorActionUpdater ACTION_UPDATER = new AlignmentEditorActionUpdater();
+ public final Clipboard CLIPBOARD = new Clipboard(Display.getCurrent()); //TODO Move to global EDITor class.
+
private MultipleAlignmentsContainer alignmentsContainer = null;
private final Map cdmMap = new TreeMap(); //TODO Move this to ContigSequenceDataProvider
private boolean dirty = false;
-
- public AlignmentEditor() {
+ public AlignmentEditor()
+ {
super();
conversationHolder = CdmStore.createConversation();
//conversationHolder = null;
@@ -151,34 +155,34 @@ public class AlignmentEditor extends EditorPart {
private void registerEditSettingListener(MultipleAlignmentsContainer container) {
- container.getEditSettings().addListener(new EditSettingsListener() {
- @Override
- public void workingModeChanged(EditSettingsChangeEvent e) {} // Currently nothing to do
+ container.getEditSettings().addListener(new EditSettingsListener() {
+ @Override
+ public void workingModeChanged(EditSettingsChangeEvent e) {} // Currently nothing to do
- @Override
- public void insertLeftInDataAreaChanged(EditSettingsChangeEvent e) {
- updateStatusBar();
- refreshToolbarElement(ToggleLeftRightInsertionHandler.COMMAND_ID);
- }
+ @Override
+ public void insertLeftInDataAreaChanged(EditSettingsChangeEvent e) {
+ updateStatusBar();
+ refreshToolbarElement(ToggleLeftRightInsertionHandler.COMMAND_ID);
+ }
- @Override
- public void insertChanged(EditSettingsChangeEvent e) {
- updateStatusBar();
- refreshToolbarElement(ToggleInsertOverwriteHandler.COMMAND_ID);
- }
- });
+ @Override
+ public void insertChanged(EditSettingsChangeEvent e) {
+ updateStatusBar();
+ refreshToolbarElement(ToggleInsertOverwriteHandler.COMMAND_ID);
+ }
+ });
}
- private AlignmentArea createIndexArea(MultipleAlignmentsContainer container, AlignmentArea labeledArea) {
+ private AlignmentArea createIndexArea(MultipleAlignmentsContainer container, AlignmentArea labeledArea) {
AlignmentArea result = new AlignmentArea(container);
result.setAllowVerticalScrolling(false);
result.getDataAreas().getTopAreas().add(new SequenceIndexArea(result.getContentArea(), labeledArea));
return result;
- }
+ }
- private AlignmentArea createEditableAlignmentArea(MultipleAlignmentsContainer container, boolean allowVerticalScrolling) {
+ private AlignmentArea createEditableAlignmentArea(MultipleAlignmentsContainer container, boolean allowVerticalScrolling) {
AlignmentArea result = new AlignmentArea(container);
result.setAllowVerticalScrolling(allowVerticalScrolling);
@@ -195,12 +199,12 @@ public class AlignmentEditor extends EditorPart {
private AlignmentArea createConsensusHintArea(MultipleAlignmentsContainer container,
AlignmentArea labeledArea) {
- AlignmentArea result = new AlignmentArea(container);
- result.setAllowVerticalScrolling(false);
- result.getDataAreas().getBottomAreas().add(
- new ConsensusSequenceArea(result.getContentArea(), labeledArea));
- return result;
- }
+ AlignmentArea result = new AlignmentArea(container);
+ result.setAllowVerticalScrolling(false);
+ result.getDataAreas().getBottomAreas().add(
+ new ConsensusSequenceArea(result.getContentArea(), labeledArea));
+ return result;
+ }
private MultipleAlignmentsContainer getAlignmentsContainer() {
@@ -209,9 +213,12 @@ public class AlignmentEditor extends EditorPart {
AlignmentAreaList list = alignmentsContainer.getAlignmentAreas();
AlignmentArea readsArea = createEditableAlignmentArea(alignmentsContainer, true);
+ readsArea.getSelection().addSelectionListener(ACTION_UPDATER);
list.add(createIndexArea(alignmentsContainer, readsArea));
list.add(readsArea); // Make sure READS_AREA_INDEX is correct.
- list.add(createEditableAlignmentArea(alignmentsContainer, false)); // Make sure COMSENSUS_AREA_INDEX is correct.
+ AlignmentArea editableConsensusArea = createEditableAlignmentArea(alignmentsContainer, false);
+ editableConsensusArea.getSelection().addSelectionListener(ACTION_UPDATER);
+ list.add(editableConsensusArea); // Make sure COMSENSUS_AREA_INDEX is correct.
list.add(createConsensusHintArea(alignmentsContainer, readsArea));
registerEditSettingListener(alignmentsContainer);
@@ -225,11 +232,49 @@ public class AlignmentEditor extends EditorPart {
}
- private AlignmentArea getEditableConsensusArea() {
+ public AlignmentArea getEditableConsensusArea() {
return getAlignmentsContainer().getAlignmentAreas().get(EDITABLE_CONSENSUS_AREA_INDEX);
}
+ /**
+ * Checks whether {@link #getReadsArea()} or {@link #getEditableConsensusArea()} currently
+ * have the user focus and returns the according component.
+ *
+ * @return either the reads or the consensus alignment area or {@code null} if none of these
+ * components is currently focused
+ */
+ public AlignmentArea getFocusedArea() {
+ AlignmentArea result = getReadsArea();
+ if (hasFocus(result)) {
+ return result;
+ }
+ else {
+ result = getEditableConsensusArea();
+ if (hasFocus(result)) {
+ return result;
+ }
+ else {
+ return null;
+ }
+ }
+ }
+
+
+ /**
+ * Checks whether the specified alignment area or one of its subcomponents currently has the
+ * focus.
+ *
+ * @param area the alignment area to be checked (Can only be {@link #getReadsArea()} or
+ * {@link #getEditableConsensusArea()}.)
+ * @return {@code true} if the specified component is focused and is either equal to
+ * {@link #getReadsArea()} or {@link #getEditableConsensusArea()}or {@code false} otherwise
+ */
+ private boolean hasFocus(AlignmentArea area) {
+ return SWTUtils.childHasFocus((Composite)area.getToolkitComponent());
+ }
+
+
public boolean hasPherogram(int sequenceID) {
return getReadsArea().getDataAreas().getSequenceAreas(sequenceID).size() > PHEROGRAM_AREA_INDEX;
}
@@ -312,12 +357,11 @@ public class AlignmentEditor extends EditorPart {
}
- /* (non-Javadoc)
- * @see org.eclipse.ui.part.WorkbenchPart#createPartControl(org.eclipse.swt.widgets.Composite)
- */
@Override
public void createPartControl(Composite parent) {
SWTComponentFactory.getInstance().getSWTComponent(getAlignmentsContainer(), parent, SWT.NONE);
+ Display.getCurrent().addFilter(SWT.FocusIn, ACTION_UPDATER);
+ Display.getCurrent().addFilter(SWT.FocusOut, ACTION_UPDATER);
updateStatusBar();
if (getEditorInput() instanceof AlignmentEditorInput) {
@@ -340,7 +384,17 @@ public class AlignmentEditor extends EditorPart {
}
- private void updateStatusBar() {
+ @Override
+ public void dispose() {
+ Display.getCurrent().removeFilter(SWT.FocusIn, ACTION_UPDATER);
+ Display.getCurrent().removeFilter(SWT.FocusOut, ACTION_UPDATER);
+ CLIPBOARD.dispose();
+ ((AlignmentEditorInput)getEditorInput()).dispose();
+ super.dispose();
+ }
+
+
+ private void updateStatusBar() {
IActionBars bars = getEditorSite().getActionBars();
bars.getStatusLineManager().setMessage("Edit mode: " +
(getReadsArea().getEditSettings().isInsert() ? "Insert" : "Overwrite") + " " +
@@ -360,9 +414,6 @@ public class AlignmentEditor extends EditorPart {
}
- /* (non-Javadoc)
- * @see org.eclipse.ui.part.EditorPart#doSave(org.eclipse.core.runtime.IProgressMonitor)
- */
@Override
public void doSave(IProgressMonitor monitor) {
if (getEditorInput() instanceof AlignmentEditorInput) {
@@ -432,40 +483,17 @@ public class AlignmentEditor extends EditorPart {
}
- /* (non-Javadoc)
- * @see org.eclipse.ui.part.EditorPart#doSaveAs()
- */
@Override
public void doSaveAs() {}
- /* (non-Javadoc)
- * @see org.eclipse.ui.part.EditorPart#init(org.eclipse.ui.IEditorSite, org.eclipse.ui.IEditorInput)
- */
@Override
public void init(IEditorSite site, IEditorInput input) throws PartInitException {
setSite(site);
setInput(input);
- System.out.println("AlignmentEditor.init(): " + ActionFactory.COPY.getId());
- site.getActionBars().setGlobalActionHandler(ActionFactory.COPY.getId(), new Action(ActionFactory.COPY.getId()) {
- @Override
- public boolean isEnabled() {
- System.out.println("isEnabled()");
- return true;
- }
-
- @Override
- public void run() {
- System.out.println("run");
- super.run();
- }
- });
}
- /* (non-Javadoc)
- * @see org.eclipse.ui.part.EditorPart#isDirty()
- */
@Override
public boolean isDirty() {
return dirty;
@@ -478,9 +506,6 @@ public class AlignmentEditor extends EditorPart {
}
- /* (non-Javadoc)
- * @see org.eclipse.ui.part.EditorPart#isSaveAsAllowed()
- */
@Override
public boolean isSaveAsAllowed() {
return false; // "Save as" not allowed.
@@ -489,17 +514,12 @@ public class AlignmentEditor extends EditorPart {
@Override
public void setFocus() {
- if(conversationHolder!=null){
+ if(conversationHolder != null){
conversationHolder.bind();
}
((AlignmentEditorInput)getEditorInput()).bind();
}
- @Override
- public void dispose() {
- ((AlignmentEditorInput)getEditorInput()).dispose();
- }
-
public boolean isInsertMode() {
return getAlignmentsContainer().getEditSettings().isInsert();
}
diff --git a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/editor/AlignmentEditorActionUpdater.java b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/editor/AlignmentEditorActionUpdater.java
new file mode 100644
index 000000000..7993a08c4
--- /dev/null
+++ b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/editor/AlignmentEditorActionUpdater.java
@@ -0,0 +1,55 @@
+package eu.etaxonomy.taxeditor.molecular.editor;
+
+
+import org.eclipse.swt.widgets.Event;
+import org.eclipse.swt.widgets.Listener;
+import org.eclipse.ui.PlatformUI;
+import org.eclipse.ui.actions.ActionFactory;
+import org.eclipse.ui.commands.ICommandService;
+
+import eu.etaxonomy.taxeditor.molecular.handler.AbstractAlignmentEditorHandler;
+import info.bioinfweb.libralign.alignmentarea.selection.SelectionChangeEvent;
+import info.bioinfweb.libralign.alignmentarea.selection.SelectionListener;
+
+
+
+/**
+ * Listener used to update copy/paste events associated with {@link AlignmentEditor}.
+ *
+ * @author Ben Stöver
+ * @date 25.08.2015
+ */
+public class AlignmentEditorActionUpdater implements SelectionListener, Listener {
+ private static final String[] IDS = {ActionFactory.COPY.getCommandId(), ActionFactory.CUT.getCommandId(),
+ ActionFactory.PASTE.getCommandId()};
+
+
+ private void updateEvents() {
+ ICommandService service = (ICommandService)PlatformUI.getWorkbench().getService(ICommandService.class);
+ for (int i = 0; i < IDS.length; i++) {
+ service.refreshElements(IDS[i], null);
+ }
+ }
+
+
+ @Override
+ public void handleEvent(Event event) {
+ AlignmentEditor editor = AbstractAlignmentEditorHandler.getActiveAlignmentEditor();
+ if (editor != null) {
+ updateEvents();
+ }
+ }
+
+
+ @Override
+ public void selectionChanged(SelectionChangeEvent e) {
+ AlignmentEditor editor = AbstractAlignmentEditorHandler.getActiveAlignmentEditor();
+ if (editor != null) {
+ if ((e.getSource() == editor.getReadsArea().getSelection()) ||
+ (e.getSource() == editor.getEditableConsensusArea().getSelection())) {
+
+ updateEvents();
+ }
+ }
+ }
+}
diff --git a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AbstractAlignmentEditorHandler.java b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AbstractAlignmentEditorHandler.java
index 0c8a6edb1..1d44449b9 100644
--- a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AbstractAlignmentEditorHandler.java
+++ b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AbstractAlignmentEditorHandler.java
@@ -29,15 +29,26 @@ import eu.etaxonomy.taxeditor.molecular.editor.AlignmentEditor;
* @date 19.06.2015
*/
public abstract class AbstractAlignmentEditorHandler extends AbstractHandler {
- @Override
- public Object execute(ExecutionEvent event) throws ExecutionException {
+ public static AlignmentEditor getActiveAlignmentEditor() {
IEditorPart activeEditor = AbstractUtility.getActiveEditor();
if (activeEditor instanceof AlignmentEditor) {
- doExecute(event, (AlignmentEditor)activeEditor);
+ return (AlignmentEditor)activeEditor;
+ }
+ else {
+ return null;
+ }
+ }
+
+
+ @Override
+ public Object execute(ExecutionEvent event) throws ExecutionException {
+ AlignmentEditor editor = getActiveAlignmentEditor();
+ if (editor != null) {
+ doExecute(event, editor);
}
return null;
}
- public abstract void doExecute(ExecutionEvent event, AlignmentEditor editor) throws ExecutionException;
+ protected abstract void doExecute(ExecutionEvent event, AlignmentEditor editor) throws ExecutionException;
}
diff --git a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AbstractFocusedAlignmentAreaHandler.java b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AbstractFocusedAlignmentAreaHandler.java
new file mode 100644
index 000000000..1fc418aae
--- /dev/null
+++ b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AbstractFocusedAlignmentAreaHandler.java
@@ -0,0 +1,24 @@
+package eu.etaxonomy.taxeditor.molecular.handler;
+
+
+import info.bioinfweb.libralign.alignmentarea.AlignmentArea;
+
+import org.eclipse.core.commands.ExecutionEvent;
+import org.eclipse.core.commands.ExecutionException;
+
+import eu.etaxonomy.taxeditor.molecular.editor.AlignmentEditor;
+
+
+
+public abstract class AbstractFocusedAlignmentAreaHandler extends AbstractAlignmentEditorHandler {
+ @Override
+ protected void doExecute(ExecutionEvent event, AlignmentEditor editor) throws ExecutionException {
+ AlignmentArea focusedArea = editor.getFocusedArea();
+ if (focusedArea != null) {
+ doExecute2(event, editor, focusedArea);
+ }
+ }
+
+
+ protected abstract void doExecute2(ExecutionEvent event, AlignmentEditor editor, AlignmentArea focusedArea);
+}
diff --git a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorCopyHandler.java b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorCopyHandler.java
new file mode 100644
index 000000000..381cf3536
--- /dev/null
+++ b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorCopyHandler.java
@@ -0,0 +1,62 @@
+package eu.etaxonomy.taxeditor.molecular.handler;
+
+
+import java.util.Map;
+
+import info.bioinfweb.libralign.alignmentarea.AlignmentArea;
+import info.bioinfweb.libralign.alignmentarea.selection.SelectionModel;
+import info.bioinfweb.libralign.model.AlignmentModelUtils;
+
+import org.eclipse.core.commands.ExecutionEvent;
+import org.eclipse.swt.dnd.TextTransfer;
+import org.eclipse.swt.dnd.Transfer;
+import org.eclipse.ui.commands.IElementUpdater;
+import org.eclipse.ui.menus.UIElement;
+
+import eu.etaxonomy.taxeditor.molecular.editor.AlignmentEditor;
+
+
+
+/**
+ * Handler that copies the currently selected nucleotides from an alignment editor to the clipboard.
+ *
+ * The copied contents either come from the single reads or the consensus sequence alignment area,
+ * depending on which component currently has the focus. If none of these components has the focus,
+ * nothing will be copied, even if nucleotides are currently selected.
+ *
+ * If the selection contains parts of multiple sequence, these are separated by the line separator
+ * of the current operating system.
+ *
+ * @author Ben Stöver
+ * @date 25.08.2015
+ */
+public class AlignmentEditorCopyHandler extends AbstractFocusedAlignmentAreaHandler implements IElementUpdater {
+ @Override
+ @SuppressWarnings("unchecked")
+ protected void doExecute2(ExecutionEvent event, AlignmentEditor editor, AlignmentArea focusedArea) {
+ SelectionModel selection = focusedArea.getSelection();
+ if (!selection.isEmpty()) {
+ editor.CLIPBOARD.setContents(new Object[]{AlignmentModelUtils.selectionAsString(focusedArea, false)},
+ new Transfer[]{TextTransfer.getInstance()});
+ }
+ }
+
+
+ @Override
+ public boolean isEnabled() {
+ AlignmentEditor editor = getActiveAlignmentEditor();
+ if (editor != null) {
+ AlignmentArea focusedArea = editor.getFocusedArea();
+ if (focusedArea != null) {
+ return !focusedArea.getSelection().isEmpty();
+ }
+ }
+ return false;
+ }
+
+
+ @Override
+ public void updateElement(UIElement element, @SuppressWarnings("rawtypes") Map parameters) {
+ setBaseEnabled(isEnabled());
+ }
+}
diff --git a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorCutHandler.java b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorCutHandler.java
new file mode 100644
index 000000000..2236686fb
--- /dev/null
+++ b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorCutHandler.java
@@ -0,0 +1,31 @@
+package eu.etaxonomy.taxeditor.molecular.handler;
+
+
+import info.bioinfweb.libralign.alignmentarea.AlignmentArea;
+
+import org.eclipse.core.commands.ExecutionEvent;
+
+import eu.etaxonomy.taxeditor.molecular.editor.AlignmentEditor;
+
+
+
+/**
+ * Handler that cuts the currently selected nucleotides from an alignment editor to the clipboard.
+ *
+ * The cut contents either come from the single reads or the consensus sequence alignment area,
+ * depending on which component currently has the focus. If none of these components has the focus,
+ * nothing will be cut, even if nucleotides are currently selected.
+ *
+ * If the selection contains parts of multiple sequence, these are separated by the line separator
+ * of the current operating system.
+ *
+ * @author Ben Stöver
+ * @date 25.08.2015
+ */
+public class AlignmentEditorCutHandler extends AlignmentEditorCopyHandler {
+ @Override
+ protected void doExecute2(ExecutionEvent event, AlignmentEditor editor, AlignmentArea focusedArea) {
+ super.doExecute2(event, editor, focusedArea); // Copy selected contents.
+ focusedArea.getActionProvider().deleteSelection();
+ }
+}
diff --git a/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorPasteHandler.java b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorPasteHandler.java
new file mode 100644
index 000000000..ca037657c
--- /dev/null
+++ b/eu.etaxonomy.taxeditor.molecular/src/main/java/eu/etaxonomy/taxeditor/molecular/handler/AlignmentEditorPasteHandler.java
@@ -0,0 +1,129 @@
+package eu.etaxonomy.taxeditor.molecular.handler;
+
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+import java.util.Scanner;
+
+import info.bioinfweb.libralign.alignmentarea.AlignmentArea;
+import info.bioinfweb.libralign.alignmentarea.order.SequenceOrder;
+import info.bioinfweb.libralign.alignmentarea.selection.SelectionModel;
+import info.bioinfweb.libralign.model.AlignmentModel;
+import info.bioinfweb.libralign.model.AlignmentModelUtils;
+
+import org.eclipse.core.commands.ExecutionEvent;
+import org.eclipse.jface.dialogs.MessageDialog;
+import org.eclipse.swt.dnd.TextTransfer;
+import org.eclipse.ui.commands.IElementUpdater;
+import org.eclipse.ui.handlers.HandlerUtil;
+import org.eclipse.ui.menus.UIElement;
+
+import eu.etaxonomy.taxeditor.molecular.editor.AlignmentEditor;
+
+
+
+/**
+ * Handler that pastes the current contents of the clipboard into an active instance of {@link AlignmentEditor}.
+ *
+ * @author Ben Stöver
+ * @date 26.08.2015
+ */
+public class AlignmentEditorPasteHandler extends AbstractFocusedAlignmentAreaHandler implements IElementUpdater {
+ private void pasteString(AlignmentArea area, int sequenceID, String content) {
+ area.getActionProvider().deleteSelection(); // Overwrite selected tokens.
+ area.getActionProvider().elongateSequence(sequenceID, area.getSelection().getCursorColumn());
+
+ AlignmentModel