Skip to content

contest: comments layout, stems threshold, submit pre-fill, mobile listings#14253

Open
dylanjeffers wants to merge 2 commits intomainfrom
fix/contest-ux-feedback
Open

contest: comments layout, stems threshold, submit pre-fill, mobile listings#14253
dylanjeffers wants to merge 2 commits intomainfrom
fix/contest-ux-feedback

Conversation

@dylanjeffers
Copy link
Copy Markdown
Contributor

Summary

UI feedback from Julian on the remix-contest surface, batched into one PR. Each fix is the minimum change to unblock the report — happy to split if you'd rather review per-issue.

Companion to PR #14251 (notification rendering); the two are independent and can land in either order.

Web

  • Comments overflow button position — moved out of the header row and into the action bar next to Reply, matching the track-page `CommentBlock` layout. The header was wrapping when the user link + timestamp + badge were wide.
    File: `pages/contest-page/components/ContestCommentsTile.tsx`
  • Artist flair restyled to "Host" — replaced the inline `<Text variant='label' …>Artist` with the same `IconStar` + accent `Text` shape the track-page `CommentBadge` uses, and renamed the label to "Host" (contest hosts aren't necessarily the artist on the source track's comment thread).
  • Stems collapse threshold — Stems & Downloads card now collapses by default when there are more than 5 stems, stays expanded under that. Long lists were pushing followers + comments way down. Explicit user toggle wins over the heuristic so clicking the caret never gets stomped.
    File: `pages/contest-page/components/ContestStemsCard.tsx` (web) + `mobile/src/screens/contest-screen/ContestStemsCard.tsx` (native)
  • "Remixes (N)" → "Submissions (N)" on Pick Winners — added `pickWinnersSubmissionsTitle` message; didn't reuse the longer existing `submissionsTitle` since that's used on the regular remixes page.
    Files: `common/src/messages/remixes.ts`, `pages/pick-winners-page/PickWinnersPage.tsx`
  • Submit-to-contest pre-fill — the desktop track-page `RemixContestSection` already pre-filled artwork + genre + remix_of from the source track. The contest page (desktop + mobile) and the mobile track-page contest details tab were missing it (or worse — the contest page navigated with a query-string `?remix_of=…` that the upload page silently ignores). Factored into a shared `useEnterContest(trackId)` hook and wired into all three.
    Files: new `pages/contest-page/hooks/useEnterContest.ts`; `pages/contest-page/components/{desktop,mobile}/ContestPage.tsx`; `pages/track-page/components/mobile/remix-contests/RemixContestDetailsTab.tsx`

Mobile (native)

  • Discovery contests carousel — when the CONTESTS flag is on the section title is "Contests", but the data source was still the curated `featuredRemixContests` subset. Swapped to `useAllRemixContests` (same source the dedicated `/contests` screen uses) so the data matches the label.
    File: `mobile/src/screens/explore-screen/components/FeaturedRemixContests.tsx`
  • Profile Contests tab visibility (@DimensionX fix) — discovery endpoint doesn't support `host=…` filtering, so the tab paginates the global list and filters client-side. Bumped the page size 50 → 100 so deep-list hosts (ended contests, smaller accounts) are reached by the auto-pagination loop that was already in place.
    File: `mobile/src/screens/profile-screen/ProfileTabs/ContestsTab.tsx`

Out of scope (deliberately not touched)

  • Native `ContestScreen.handleEnterContest` is a stub (`console.info('Enter contest — native upload flow not yet wired')`). Wiring the native upload from the dedicated contest screen is a separate piece of work — `UploadRemixFooter` (track screen) already has the artwork/genre pre-fill and serves as the reference implementation.
  • Notification work (host doesn't get submission notification, non-host doesn't get winner notification) is being handled by the in-flight pedalboard fixes + apps PR #14251.
  • The "unfurl all stems by default" change in PR [Contest] Edit flow, listings, notifications, and mobile QA pass #14239 is in flight on a different branch — the threshold-based collapse here works regardless of merge order.

Test plan

  • `tsc --noEmit` clean on every file in this PR (`packages/web`, `packages/mobile`, `packages/common`). Remaining CI typecheck errors visible across the repo are pre-existing in unrelated files (jupiter/api, proxy-memoize, type-fest exports).
  • `eslint` clean on every changed file. Mobile shows pre-existing `react-native` import-resolution warnings that affect untouched files too.
  • Manual browser-preview verification (in the apps-3 worktree per stored preference):
    • Desktop contest page: comment row overflow kebab now sits next to Reply, no header wrapping.
    • Desktop contest page: host comment shows IconStar + "Host" label.
    • Desktop + mobile contest page: stems list with 6+ stems starts collapsed; with 1–5 stems starts expanded; user click overrides cleanly.
    • Pick winners: section title reads "Submissions (N)".
    • Click "Enter Contest" from desktop contest page → upload form pre-filled with source track's cover art and genre.
    • Mobile native explore: contest carousel shows the full list, not the curated subset.
    • Profile tab on a host whose contest was previously missing → contest now appears.

🤖 Generated with Claude Code

dylanjeffers and others added 2 commits May 6, 2026 15:01
Contest-related in-app notifications were silently dropped from the feed
in three layers (adapter -> useNotificationEntity -> per-renderer). The
deleted-track case alone makes a fan/artist remix contest row vanish:
useNotificationEntity returns null, every renderer early-returned null,
nothing reached the list. Same shape for comments on contest events,
which additionally couldn't resolve at all because the client Entity
enum had no Event member.

This commit lands the client side of the fix:

- common: add Entity.Event ('Event') and include it in the entityType
  unions on Comment / CommentThread / CommentMention / CommentReaction.
- common/useNotificationEntity: when entityType === Entity.Event,
  resolve the underlying track via useEvent -> useTrack (mirroring the
  two-hop lookup we already do server-side in the pedalboard mappers).
- web: 9 contest renderers (FanRemix* x5, ArtistRemix* x3, RemixContest
  Update) now degrade instead of returning null when entity/host can't
  be resolved. Fan-side renderers fall back to a host UserNameLink (via
  useUser on entityUserId) plus generic copy; artist-side renderers
  drop the inline TrackLink and render generic copy. Click-to-navigate
  is suppressed when there's no entity to link to.

SDK gap (separate fix needed upstream): the generated comment-notification
type enums in @audius/sdk only include Track/Playlist/Album. The
discovery-provider backend already emits 'Event' for contest comments,
and the adapter already passes it through via @ts-ignore, so this is
purely a typing gap, not a runtime one - but the SDK schema should be
regenerated to include 'Event' alongside the existing values.

Note: did not start the dev server to visually verify (per user pref,
preview servers run in the apps-3 worktree). Typecheck and lint pass
on every changed file.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…pre-fill

UI feedback from Julian on the remix-contest surface, batched into one
PR. Each fix below is the minimum change to unblock the report.

WEB:

- Comments overflow kebab moved out of the header row and into the
  action bar next to Reply, matching the track-page CommentBlock
  layout. The header was wrapping when the user link + timestamp +
  badge were wide. (ContestCommentsTile.tsx)

- Comment artist flair restyled to match the track-page CommentBadge
  (IconStar + accent text via Flex), and the label changed from
  "Artist" to "Host" — contest hosts aren't necessarily the comment-
  thread artist, and "Host" reads correctly here.
  (ContestCommentsTile.tsx)

- Stems & Downloads card now collapses by default when there are
  more than 5 stems and stays expanded when there are fewer — long
  lists were pushing the followers + comments tiles way down the
  page. The user's explicit toggle (override) wins over the
  heuristic, so clicking the caret never gets stomped.
  (ContestStemsCard.tsx, applied to both web and native variants)

- Pick-winners "Remixes (N)" heading renamed to "Submissions (N)".
  Added a dedicated `pickWinnersSubmissionsTitle` message rather
  than reusing `submissionsTitle` (which is the longer "Remix
  Contest Submissions" used on the regular remixes page).
  (messages/remixes.ts, PickWinnersPage.tsx)

- Submit-to-contest entry points now pre-fill the upload form with
  the source track's artwork (fetched as a File for the artwork
  input) + genre + remix_of, matching the desktop track-page
  RemixContestSection that already did this. Factored into a shared
  `useEnterContest(trackId)` hook used by:
    * Desktop contest page    (was: navigate('/upload?remix_of=…')
                                — query string ignored by upload page)
    * Mobile contest page     (same bug)
    * Mobile track-page contest details tab (had remix_of but no
                                              artwork/genre)

MOBILE (native):

- Discovery contest carousel: when the CONTESTS flag is on the
  section title is "Contests", but the data was still the curated
  `featuredRemixContests` subset. Swap to `useAllRemixContests` so
  the data matches the label (Julian: "the full list of contests
  isn't showing on the mobile discovery page").
  (FeaturedRemixContests.tsx)

- Profile Contests tab: bumped page size 50 → 100 so deep-list
  hosts (ended contests, smaller accounts — @DimensionX report) are
  reached by the auto-pagination effect that was already in place.
  No backend change needed; the discovery endpoint doesn't support
  host=… filtering, so client-side filter against the global list
  remains the only option.
  (ContestsTab.tsx)

OUT OF SCOPE (deliberately not touched):

- Native ContestScreen `handleEnterContest` is a stub
  (`console.info('Enter contest — native upload flow not yet
  wired')`). Wiring up the native upload from the dedicated contest
  screen is a separate piece of work — UploadRemixFooter (track
  screen) already has the artwork/genre pre-fill and serves as the
  reference implementation.

VERIFICATION:

- `tsc --noEmit` clean across `packages/web` and `packages/mobile`
  for every file in this PR. The remaining typecheck errors visible
  in CI are pre-existing in unrelated files (jupiter/api,
  proxy-memoize, type-fest exports, etc.) and unchanged by this PR.
- `eslint` clean on every changed file (mobile shows pre-existing
  `react-native` import-resolution warnings that affect untouched
  files too).
- Browser preview verification deferred to the apps-3 worktree per
  the user's stored preference.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@changeset-bot
Copy link
Copy Markdown

changeset-bot Bot commented May 6, 2026

⚠️ No Changeset found

Latest commit: d6f6c89

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

@dylanjeffers dylanjeffers changed the title contest: Julian's QA pass (comments layout, stems threshold, submit pre-fill, mobile listings) contest: comments layout, stems threshold, submit pre-fill, mobile listings May 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant