Home/Calendar polish: person switcher placement, full-width Calendar, sponsors
- Home: the person switcher (chip row) now lives in the white content area instead of the navy header, matching the design canvas's own M1 markup, and renders smaller. Home is now the only screen that shows it at all. - Calendar: dropped the person switcher and the "My schedule"/"All members" toggle entirely -- it always shows every event self.managed_people is invited to, full stop. Rows now run edge-to-edge (-mx-4) instead of living in a rounded, inset card, matching the M3 design canvas's own full-bleed layout. (The design mock's List/Month/"Games only" controls aren't reproduced -- no real functionality behind them yet.) - Home's "Needs your answer" card caps at 5 items with a "+N more in Calendar" link, so it can't crowd the dues/news cards below it off the first screenful. - Home gains a sponsors strip at the very bottom (horizontally scrolling, scrollbar hidden) -- active sponsors only, reshuffled on every request. club.services.sponsors.active_sponsors factors the "what counts as active" query out of club/api.py's public sponsors endpoint so both it and Home share one definition. - Also removed mobile/views.py's now-fully-dead _PlaceholderScreen and its template -- every M1-M7 screen has had a real implementation for a while and nothing subclassed it anymore. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01ECGMEwrc2k4D8VQuwjstj9
This commit is contained in:
23
club/api.py
23
club/api.py
@@ -2,17 +2,14 @@
|
||||
mounted.
|
||||
"""
|
||||
|
||||
import random
|
||||
import uuid
|
||||
from datetime import date
|
||||
|
||||
from django.db.models import Q
|
||||
from django.utils import timezone
|
||||
from ninja import Router, Schema
|
||||
|
||||
from api.errors import require_club
|
||||
|
||||
from .models import Sponsor
|
||||
from .services.sponsors import active_sponsors
|
||||
|
||||
router = Router(tags=["sponsors"])
|
||||
|
||||
@@ -43,20 +40,8 @@ def _to_sponsor_out(sponsor, request) -> SponsorOut:
|
||||
|
||||
@router.get("/", response=list[SponsorOut], summary="Active sponsors")
|
||||
def list_sponsors(request, randomize: bool = False):
|
||||
"""Sponsors currently "live": start_date has passed and either there's no
|
||||
end_date (runs indefinitely once started) or it hasn't passed yet. Both
|
||||
bounds are inclusive of today.
|
||||
|
||||
`randomize=true` shuffles the result (e.g. for a sponsor strip that
|
||||
shouldn't always lead with the same one) -- shuffled in Python after a
|
||||
stable-ordered fetch rather than an ORDER BY RANDOM(), which sponsor
|
||||
counts are far too small to need and which SQLite/Postgres don't even
|
||||
express the same way."""
|
||||
"""See club.services.sponsors.active_sponsors for what "active" means and
|
||||
why `randomize=true` shuffles in Python rather than in SQL."""
|
||||
club = require_club(request)
|
||||
today = timezone.localdate()
|
||||
|
||||
sponsors = list(Sponsor.objects.filter(club=club, start_date__lte=today).filter(Q(end_date__isnull=True) | Q(end_date__gte=today)).order_by("name"))
|
||||
if randomize:
|
||||
random.shuffle(sponsors)
|
||||
|
||||
sponsors = active_sponsors(club, randomize=randomize)
|
||||
return [_to_sponsor_out(sponsor, request) for sponsor in sponsors]
|
||||
|
||||
30
club/services/sponsors.py
Normal file
30
club/services/sponsors.py
Normal file
@@ -0,0 +1,30 @@
|
||||
"""Which sponsors are currently "live" -- shared by the public API
|
||||
(club/api.py, the club's own external website) and the mobile member app's
|
||||
Home screen (mobile/views.py), so both read the same definition of "active"
|
||||
rather than each re-deriving it.
|
||||
"""
|
||||
|
||||
import random
|
||||
|
||||
from django.db.models import Q
|
||||
from django.utils import timezone
|
||||
|
||||
from ..models import Sponsor
|
||||
|
||||
|
||||
def active_sponsors(club, *, randomize=False):
|
||||
"""Sponsors currently live for ``club``: ``start_date`` has passed and
|
||||
either there's no ``end_date`` (runs indefinitely once started) or it
|
||||
hasn't passed yet. Both bounds are inclusive of today.
|
||||
|
||||
``randomize=True`` shuffles the result (e.g. for a sponsor strip that
|
||||
shouldn't always lead with the same one) -- shuffled in Python after a
|
||||
stable-ordered fetch rather than an ORDER BY RANDOM(), which sponsor
|
||||
counts are far too small to need and which SQLite/Postgres don't even
|
||||
express the same way.
|
||||
"""
|
||||
today = timezone.localdate()
|
||||
sponsors = list(Sponsor.objects.filter(club=club, start_date__lte=today).filter(Q(end_date__isnull=True) | Q(end_date__gte=today)).order_by("name"))
|
||||
if randomize:
|
||||
random.shuffle(sponsors)
|
||||
return sponsors
|
||||
Reference in New Issue
Block a user