import 'package:audioplayers/audioplayers.dart';
import 'package:flutter/services.dart';
import 'package:vibration/vibration.dart';

class FeedbackService {
  FeedbackService() : _player = AudioPlayer() {
    _player.setReleaseMode(ReleaseMode.stop);
  }

  final AudioPlayer _player;

  Future<void> onCodeDetected() async {
    await Future.wait([
      _play('sounds/scan.wav'),
      _vibratePattern(const [0, 40]),
    ]);
  }

  Future<void> onSuccess() async {
    await Future.wait([
      _play('sounds/success.wav'),
      _vibratePattern(const [0, 90, 70, 140]),
    ]);
    await HapticFeedback.heavyImpact();
  }

  Future<void> onWarning() async {
    await Future.wait([
      _play('sounds/warning.wav'),
      _vibratePattern(const [0, 120, 80, 120, 80, 120]),
    ]);
    await HapticFeedback.mediumImpact();
  }

  Future<void> _play(String asset) async {
    try {
      await _player.stop();
      await _player.play(AssetSource(asset));
    } catch (_) {
      // Ignore audio errors on devices without speaker routing.
    }
  }

  Future<void> _vibratePattern(List<int> pattern) async {
    try {
      final hasVibrator = await Vibration.hasVibrator();
      if (hasVibrator != true) return;

      final hasAmplitude = await Vibration.hasAmplitudeControl();
      if (hasAmplitude == true) {
        final intensities = pattern
            .asMap()
            .entries
            .map((entry) => entry.key.isOdd ? 180 : 0)
            .toList();
        await Vibration.vibrate(
          pattern: pattern,
          intensities: intensities,
        );
        return;
      }

      await Vibration.vibrate(pattern: pattern);
    } catch (_) {
      await HapticFeedback.selectionClick();
    }
  }

  Future<void> dispose() async {
    await _player.dispose();
  }
}