diff --git a/scipost_django/submissions/migrations/0165_add_journal_transfer_conditional_offer.py b/scipost_django/submissions/migrations/0165_add_journal_transfer_conditional_offer.py
new file mode 100644
index 0000000000000000000000000000000000000000..2e6959a07627a934d86e82057e524480ad46f60d
--- /dev/null
+++ b/scipost_django/submissions/migrations/0165_add_journal_transfer_conditional_offer.py
@@ -0,0 +1,19 @@
+# Generated by Django 4.2.15 on 2024-09-30 11:01
+
+from django.db import migrations, models
+
+
+class Migration(migrations.Migration):
+    dependencies = [
+        ("submissions", "0164_conditionalassignmentoffer"),
+    ]
+
+    operations = [
+        migrations.AlterField(
+            model_name="conditionalassignmentoffer",
+            name="condition_type",
+            field=models.CharField(
+                choices=[("JournalTransfer", "Journal Transfer")], max_length=32
+            ),
+        ),
+    ]
diff --git a/scipost_django/submissions/models/assignment.py b/scipost_django/submissions/models/assignment.py
index b4794ea7b6e3246c655ad2e68e64fb43db9035f7..28b0a1b4964046d4b49f215e0acc402ae94c0e11 100644
--- a/scipost_django/submissions/models/assignment.py
+++ b/scipost_django/submissions/models/assignment.py
@@ -193,6 +193,66 @@ class BaseAssignmentCondition(abc.ABC):
         )
 
 
+class JournalTransferCondition(BaseAssignmentCondition):
+    """
+    Condition that offers assignment if the submission is transferred to a different journal.
+
+    Needs to specify the alternative journal in the condition_details
+    - `alternative_journal_id`: the journal to which the submission should be transferred.
+    """
+
+    def __init__(self, alternative_journal_id: int):
+        self.alternative_journal_id = alternative_journal_id
+
+    def __eq__(self, other):
+        return (
+            isinstance(other, JournalTransferCondition)
+            and self.alternative_journal_id == other.alternative_journal_id
+        )
+
+    def __hash__(self):
+        return hash(self.alternative_journal_id)
+
+    def __str__(self):
+        return f"Transfer to {self.alternative_journal}"
+
+    def __repr__(self):
+        return str(self)
+
+    @cached_property
+    def alternative_journal(self) -> Journal | None:
+        try:
+            return Journal.objects.get(id=self.alternative_journal_id)
+        except Journal.DoesNotExist:
+            return None
+
+    def is_met(self, offer: "ConditionalAssignmentOffer") -> bool:
+        """
+        Check if the submission is transferred to the alternative journal.
+        """
+        return offer.submission.submitted_to == self.alternative_journal
+
+    def accept(self, offer: "ConditionalAssignmentOffer"):
+        """
+        Accept the offer, transferring the submission to the alternative journal.
+        """
+        if self.alternative_journal is None:
+            raise ValueError("The journal for this transfer is not found.")
+
+        if (
+            self.alternative_journal
+            not in offer.submission.submitted_to.alternative_journals.all()
+        ):
+            raise ValueError(
+                "The alternative journal is not valid for the current journal."
+            )
+
+        offer.submission.submitted_to = self.alternative_journal
+        offer.submission.save()
+
+        super().accept(offer)
+
+
 class ConditionalAssignmentOffer(models.Model):
     """
     Represents an EditorialAssignment that is offered conditionally.
@@ -311,6 +371,7 @@ class ConditionalAssignmentOffer(models.Model):
         """
         Check if all conditions are met. If so:
         - Create the EditorialAssignment
+        - Set the submission's editor_in_charge to the offering fellow
         - Invalidate all other offers for this submission
 
         Returns the created EditorialAssignment or None if the conditions are not met.