diff --git a/vrobbler/apps/moods/models.py b/vrobbler/apps/moods/models.py
index 9f4181d..f36bc2b 100644
--- a/vrobbler/apps/moods/models.py
+++ b/vrobbler/apps/moods/models.py
@@ -1,5 +1,6 @@
import logging
from dataclasses import dataclass
+from enum import IntEnum
from typing import Optional
from uuid import uuid4
@@ -21,10 +22,21 @@ class MoodType(models.TextChoices):
NEGATIVE = "negative", "Negative"
+class MoodQuality(IntEnum):
+ VERY_UNPLEASANT = 1
+ UNPLEASANT = 2
+ SLIGHTLY_UNPLEASANT = 3
+ NEUTRAL = 4
+ SLIGHTLY_PLEASANT = 5
+ PLEASANT = 6
+ VERY_PLEASANT = 7
+
+
@dataclass
class MoodLogData(BaseLogData):
mood_type: Optional[str] = None
mood_reason_ids: Optional[list[int]] = None
+ mood_quality: Optional[int] = None
@classmethod
def override_fields(cls) -> dict:
@@ -42,6 +54,14 @@ class MoodLogData(BaseLogData):
required=False,
widget=forms.SelectMultiple(attrs={"size": 10}),
),
+ "mood_quality": forms.ChoiceField(
+ choices=[
+ (mq.value, mq.name.replace("_", " ").title())
+ for mq in MoodQuality
+ ],
+ required=False,
+ widget=forms.Select(attrs={"class": "form-control"}),
+ ),
}
diff --git a/vrobbler/apps/moods/templates/moods/checkin_mood.html b/vrobbler/apps/moods/templates/moods/checkin_mood.html
new file mode 100644
index 0000000..67d9464
--- /dev/null
+++ b/vrobbler/apps/moods/templates/moods/checkin_mood.html
@@ -0,0 +1,28 @@
+{% extends "base.html" %}
+
+{% block page_title %}Check-in - Select your mood{% endblock %}
+
+{% block content %}
+
+{% endblock %}
diff --git a/vrobbler/apps/moods/templates/moods/checkin_quality.html b/vrobbler/apps/moods/templates/moods/checkin_quality.html
new file mode 100644
index 0000000..120936f
--- /dev/null
+++ b/vrobbler/apps/moods/templates/moods/checkin_quality.html
@@ -0,0 +1,24 @@
+{% extends "base.html" %}
+
+{% block page_title %}Check-in - How are you feeling?{% endblock %}
+
+{% block content %}
+
+
+
+
How are you feeling?
+
+
+
+
+{% endblock %}
diff --git a/vrobbler/apps/moods/templates/moods/checkin_success.html b/vrobbler/apps/moods/templates/moods/checkin_success.html
new file mode 100644
index 0000000..03990c2
--- /dev/null
+++ b/vrobbler/apps/moods/templates/moods/checkin_success.html
@@ -0,0 +1,15 @@
+{% extends "base.html" %}
+
+{% block page_title %}Check-in Complete{% endblock %}
+
+{% block content %}
+
+
+
+
Check-in Complete!
+
Your mood has been recorded.
+
Back to Home
+
+
+
+{% endblock %}
diff --git a/vrobbler/apps/moods/urls.py b/vrobbler/apps/moods/urls.py
index ad02987..bcccdc9 100644
--- a/vrobbler/apps/moods/urls.py
+++ b/vrobbler/apps/moods/urls.py
@@ -11,4 +11,6 @@ urlpatterns = [
views.MoodDetailView.as_view(),
name="mood_detail",
),
+ path("checkin/", views.checkin, name="checkin"),
+ path("checkin/success/", views.checkin_success, name="checkin_success"),
]
diff --git a/vrobbler/apps/moods/views.py b/vrobbler/apps/moods/views.py
index a807963..9935e80 100644
--- a/vrobbler/apps/moods/views.py
+++ b/vrobbler/apps/moods/views.py
@@ -1,4 +1,83 @@
-from moods.models import Mood
+import logging
+from django.contrib.auth.decorators import login_required
+from django.shortcuts import redirect, render
+from django.urls import reverse
+from django.utils import timezone
+from moods.models import Mood, MoodLogData, MoodQuality
+from scrobbles.models import Scrobble
+
+logger = logging.getLogger(__name__)
+
+
+@login_required
+def checkin(request):
+ """Two-step mood check-in wizard"""
+ step = request.session.get("checkin_step", 1)
+
+ if request.method == "POST":
+ if step == 1:
+ quality = request.POST.get("mood_quality")
+ if quality:
+ request.session["checkin_quality"] = int(quality)
+ request.session["checkin_step"] = 2
+ return redirect("moods:checkin")
+ qualities = [
+ {"value": q.value, "name": q.name.replace("_", " ").title()}
+ for q in MoodQuality
+ ]
+ return render(
+ request, "moods/checkin_quality.html", {"qualities": qualities}
+ )
+
+ elif step == 2:
+ mood_id = request.POST.get("mood")
+ quality = request.session.get("checkin_quality")
+
+ if mood_id and quality:
+ try:
+ mood = Mood.objects.get(id=mood_id)
+ log_data = MoodLogData(
+ mood_quality=quality,
+ mood_type=mood.mood_type,
+ )
+
+ scrobble = Scrobble.objects.create(
+ user=request.user,
+ mood=mood,
+ media_type=Scrobble.MediaType.MOOD,
+ timestamp=timezone.now(),
+ source="web_checkin",
+ log=log_data.asdict,
+ )
+
+ # Clear session data
+ request.session.pop("checkin_step", None)
+ request.session.pop("checkin_quality", None)
+
+ return redirect("moods:checkin_success")
+ except Mood.DoesNotExist:
+ logger.error(f"Mood with id {mood_id} not found")
+
+ return redirect("moods:checkin")
+
+ if step == 1:
+ qualities = [
+ {"value": q.value, "name": q.name.replace("_", " ").title()}
+ for q in MoodQuality
+ ]
+ return render(
+ request, "moods/checkin_quality.html", {"qualities": qualities}
+ )
+ else:
+ moods = Mood.objects.all()
+ return render(request, "moods/checkin_mood.html", {"moods": moods})
+
+
+@login_required
+def checkin_success(request):
+ return render(request, "moods/checkin_success.html")
+
+
from scrobbles.views import ScrobbleableListView, ScrobbleableDetailView
diff --git a/vrobbler/apps/scrobbles/constants.py b/vrobbler/apps/scrobbles/constants.py
index d9c08fe..592c2fd 100644
--- a/vrobbler/apps/scrobbles/constants.py
+++ b/vrobbler/apps/scrobbles/constants.py
@@ -15,6 +15,7 @@ AUTO_FINISH_MEDIA = {
"webpages": "WebPage",
"tracks": "Track",
"videos": "Video",
+ "moods": "Mood",
}
PLAY_AGAIN_MEDIA = {
diff --git a/vrobbler/templates/base.html b/vrobbler/templates/base.html
index d1cbc05..b0326f4 100644
--- a/vrobbler/templates/base.html
+++ b/vrobbler/templates/base.html
@@ -218,6 +218,9 @@
{% endif %}
{% if user.is_authenticated %}