diff --git a/b_asic/GUI/drag_button.py b/b_asic/GUI/drag_button.py
index 638a04aaf0fdc738356d27c7450987e96dcf8c57..c28f5551b0c31dad8cc38d756a5b31e4f743e3e7 100644
--- a/b_asic/GUI/drag_button.py
+++ b/b_asic/GUI/drag_button.py
@@ -47,7 +47,7 @@ class DragButton(QPushButton):
         self,
         operation: Operation,
         show_name: bool,
-        window,
+        window: "SFGMainWindow",
         parent=None,
     ):
         self.name = operation.name or operation.graph_id
diff --git a/b_asic/scheduler_gui/operation_item.py b/b_asic/scheduler_gui/operation_item.py
index 01d0231a23d8dcd7fa4dd58e3f22560b0fe971d5..6259a643c9c376d2bdb8be59f057aca678d843e0 100644
--- a/b_asic/scheduler_gui/operation_item.py
+++ b/b_asic/scheduler_gui/operation_item.py
@@ -12,11 +12,13 @@ from typing import TYPE_CHECKING, Dict, List, Union, cast
 from qtpy.QtCore import QPointF, Qt
 from qtpy.QtGui import QBrush, QColor, QCursor, QPainterPath, QPen
 from qtpy.QtWidgets import (
+    QAction,
     QGraphicsEllipseItem,
     QGraphicsItem,
     QGraphicsItemGroup,
     QGraphicsPathItem,
     QGraphicsSimpleTextItem,
+    QMenu,
 )
 
 # B-ASIC
@@ -81,12 +83,13 @@ class OperationItem(QGraphicsItemGroup):
         self.setFlag(QGraphicsItem.ItemIsSelectable)  # mouse move events
         # self.setAcceptHoverEvents(True)                 # mouse hover events
         self.setAcceptedMouseButtons(
-            Qt.MouseButton.LeftButton
+            Qt.MouseButton.LeftButton | Qt.MouseButton.RightButton
         )  # accepted buttons for movements
         self.setCursor(
             QCursor(Qt.CursorShape.OpenHandCursor)
         )  # default cursor when hovering over object
 
+        self._context_menu = None
         self._make_component()
 
     # def sceneEvent(self, event: QEvent) -> bool:
@@ -106,6 +109,11 @@ class OperationItem(QGraphicsItemGroup):
         """The graph-id of the operation that the item corresponds to."""
         return self._operation.graph_id
 
+    @property
+    def name(self) -> str:
+        """The name of the operation that the item corresponds to."""
+        return self._operation.name
+
     @property
     def operation(self) -> Operation:
         """The operation that the item corresponds to."""
@@ -247,3 +255,14 @@ class OperationItem(QGraphicsItemGroup):
             self.addToGroup(self._execution_time_item)
 
         self.set_inactive()
+
+    def _open_context_menu(self):
+        menu = QMenu()
+        swap = QAction("Swap")
+        menu.addAction(swap)
+        swap.setEnabled(self._operation.is_swappable)
+        swap.triggered.connect(self._swap_io)
+        menu.exec_(self.cursor().pos())
+
+    def _swap_io(self, event=None) -> None:
+        self._operation.swap_io()
diff --git a/b_asic/scheduler_gui/scheduler_event.py b/b_asic/scheduler_gui/scheduler_event.py
index 1639d16618269d6960db435622acd151c067b9a9..f8c74dbeffb106e3925c1de6921b2261d6346841 100644
--- a/b_asic/scheduler_gui/scheduler_event.py
+++ b/b_asic/scheduler_gui/scheduler_event.py
@@ -10,7 +10,7 @@ import math
 from typing import List, Optional, overload
 
 # QGraphics and QPainter imports
-from qtpy.QtCore import QEvent, QObject, QPointF, Signal
+from qtpy.QtCore import QEvent, QObject, QPointF, Qt, Signal
 from qtpy.QtWidgets import QGraphicsItem, QGraphicsSceneMouseEvent
 
 from b_asic.schedule import Schedule
@@ -181,14 +181,22 @@ class SchedulerEvent:  # PyQt5
         allows the item to receive future move, release and double-click events.
         """
         item: OperationItem = self.scene().mouseGrabberItem()
-        self._old_op_position = self._schedule.get_y_location(item.operation.graph_id)
-        self._signals.component_selected.emit(item.graph_id)
-        self._current_pos = item.mapToParent(event.pos())
-        self.set_item_active(item)
-        event.accept()
+        if event.button() == Qt.MouseButton.LeftButton:
+            self._old_op_position = self._schedule.get_y_location(
+                item.operation.graph_id
+            )
+            self._signals.component_selected.emit(item.graph_id)
+            self._current_pos = item.mapToParent(event.pos())
+            self.set_item_active(item)
+            event.accept()
+        else:  # Right-button
+            item._open_context_menu()
 
     def operation_mouseReleaseEvent(self, event: QGraphicsSceneMouseEvent) -> None:
         """Change the cursor to OpenHandCursor when releasing an object."""
+        if event.button() != Qt.MouseButton.LeftButton:
+            return
+
         item: OperationItem = self.scene().mouseGrabberItem()
         self.set_item_inactive(item)
         self.set_new_start_time(item)