Skip to content

(SP: 1) [Frontend] Fix mobile quiz answer selection blocked by anti-cheat contextmenu handler #273

@LesiaUKR

Description

@LesiaUKR

Goal

Allow users to select quiz answers on mobile devices without triggering anti-cheat violation.

Problem

On mobile phones, users could not select quiz answers. Instead, anti-cheat showed "context menu" violation message.

Root cause:

  • Long-press on mobile triggers contextmenu event
  • Anti-cheat handler called e.preventDefault() and recorded violation
  • This blocked normal touch interaction on mobile

Solution

1. useAntiCheat.ts — Detect touch vs mouse input

  • Added lastInteractionWasTouch ref
  • Track touchstart → flag = true
  • Track mousedown → flag = false
  • In contextmenu handler: skip violation if touch-triggered
const handleContextMenu = (e: MouseEvent) => {
  e.preventDefault();
  if (!lastInteractionWasTouch.current) {
    addViolation('context-menu');
  }
};

2. QuizQuestion.tsx — Prevent text selection

  • Added select-none class (CSS user-select: none)
  • Added [-webkit-touch-callout:none] for iOS Safari
  • Prevents long-press text selection on protected content

3. CountdownTimer.tsx — Fix progress bar jump on mount

  • Changed initial state from Date.now() calculation to timeLimitSeconds
  • Added isSynced state, set to true on first interval tick
  • Transition enabled only after sync (prevents visual "jump")

Why this fix:

  • useState with Date.now() causes hydration mismatch (SSR vs client)
  • Progress bar animated from wrong position on page navigation
  • Now: initial render shows 100%, then syncs without transition

4. page.tsx (quiz/[slug]) — TypeScript fix

  • Fixed description metadata type error
  • quiz.description ?? t('fallback', { title: quiz.title ?? '' })

Files Changed

File Change
hooks/useAntiCheat.ts Touch detection for contextmenu
components/quiz/QuizQuestion.tsx select-none + webkit-touch-callout
components/quiz/CountdownTimer.tsx isSynced state for transition
app/[locale]/quiz/[slug]/page.tsx TypeScript metadata fix

Testing

  • Mobile: long-press no longer triggers violation
  • Mobile: text selection disabled on quiz content
  • Desktop: right-click still blocked with violation
  • Timer: no visual jump on page navigation

UX Behavior After Fix

Platform Contextmenu Text Selection Violation
Desktop Blocked Blocked (CSS) Yes
Mobile Blocked Blocked (CSS) No

Metadata

Metadata

Assignees

Labels

UXUser experience improvements, visual polish, interaction feedbackbugSomething isn't working

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions