Difficulty Achieving Smooth Rotation and Precise Stopping of Wheel in Specified Time in flutter flame

Description:

I’m encountering challenges with my Flutter application where I’ve implemented a spinning wheel feature. The goal is to rotate the wheel smoothly and stop it at a predefined position within a specified duration. However, I’m facing difficulties ensuring that the wheel stops precisely at the desired slice within the given time frame.

Here’s a breakdown of the issues and the relevant code snippet:

Smooth Rotation: While the wheel rotates, I aim to maintain a smooth movement throughout the spin. However, achieving consistent angular velocity and smooth deceleration pose challenges.

Precise Stopping: The main issue arises when trying to halt the wheel precisely at a predetermined slice within the specified time frame. Despite setting up conditions for stopping, such as checking if the maximum speed is reached and verifying the angle, the stopping point often exceeds the target or takes extra time.

Below is the excerpt of the code I’m currently using for wheel rotation and stopping logic:


class WheelUpdater extends PositionComponent {
  final SpinTheWheel spinTheWheelModel;
  final VoidCallback onSpinStop;

  late double _angularVelocity;
  late bool _spinning;
  late bool _isMaxSpeedReached;
  late int _sliceCount;
  late double _sliceAngle;
  late AudioService _audioService;
  late double _elapsedTime;
  late double stopAngle;
  late int totalDuration;

  WheelUpdater({
    required this.spinTheWheelModel,
    required this.onSpinStop,
  })  : assert(
            spinTheWheelModel.stopPosition <= spinTheWheelModel.slices.length,
            'Stop position must be less than or equal to the number of slices'),
        assert(spinTheWheelModel.duration >= 0,
            'duration must be greater than or equal to 0') {
    _sliceCount = spinTheWheelModel.slices.length;
    _sliceAngle = 2 * pi / _sliceCount;
    _angularVelocity = 0;
    _spinning = false;
    _isMaxSpeedReached = false;
    _audioService = AudioServiceImp();
    totalDuration = spinTheWheelModel.duration;
    _elapsedTime = 0;
  }

  @override
  FutureOr<void> onLoad() async {
    await _audioService.loadAll([Song.tick, Song.winner]);
    return super.onLoad();
  }

  @override
  void onRemove() async {
    await _audioService.clearAll();
    super.onRemove();
  }

  @override
  void update(double dt) {
    super.update(dt);

    double previousAngle = angle;

    if (_spinning) {
      _elapsedTime += dt * 1000;

      angle += _angularVelocity * dt;

      double maxSpeedTime = totalDuration * 0.5;

      if (_elapsedTime >= maxSpeedTime && !_isMaxSpeedReached) {
        _isMaxSpeedReached = true;
      }

      if (_isMaxSpeedReached && _angularVelocity >= 1) {
        _angularVelocity -= dt;
      } else {
        _angularVelocity += dt;
      }

      if (angle >= 2 * pi) {
        angle = (2 * pi) - angle;
      }

      int previousSliceIndex = (previousAngle / _sliceAngle).floor();
      int currentSliceIndex = (angle / _sliceAngle).floor();
      if (previousSliceIndex != currentSliceIndex) {
        _playTickSound();
      }
      if (isStoppingConditionReached) {
        _spinning = false;
        angle = stopAngle + 0.3;
        _winnerDeclared();
        onSpinStop();
      }
    }
  }

  void startSpin() {
    if (!_spinning) {
      _spinning = true;
      _angularVelocity = 0;
      _isMaxSpeedReached = false;
      _elapsedTime = 0;
    }
  }

  bool get isStoppingConditionReached {
    if (spinTheWheelModel.stopPosition == 0) {
      stopAngle = 0;
    } else {
      stopAngle = _sliceAngle * (_sliceCount - spinTheWheelModel.stopPosition);
    }

    double offsetAngle = _sliceAngle * 0.4;
    return _isMaxSpeedReached &&
        _angularVelocity <= 1 &&
        angle >= (stopAngle + offsetAngle) &&
        angle <= (stopAngle + _sliceAngle - offsetAngle);
  }

  /// Plays the tick sound when the wheel rotates to a new slice.
  Future<void> _playTickSound() async {
    await _audioService.play(Song.tick);
  }

  Future<void> _winnerDeclared() async {
    if (spinTheWheelModel.showHapticFeedback) {
      await HapticFeedback.vibrate();
    }

    /// Plays the winner sound when the spinning stops at the designated position.
    await _audioService.play(Song.winner);
  }
}

I’ve attempted to adjust parameters such as angular velocity and stopping conditions but haven’t achieved the desired outcome yet.

Image

Could someone assist me in refining the logic or suggest a formula to ensure smooth rotation and precise stopping within the specified time frame? Any insights or guidance would be greatly appreciated. Thank you!

Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa Dịch vụ tổ chức sự kiện 5 sao Thông tin về chúng tôi Dịch vụ sinh nhật bé trai Dịch vụ sinh nhật bé gái Sự kiện trọn gói Các tiết mục giải trí Dịch vụ bổ trợ Tiệc cưới sang trọng Dịch vụ khai trương Tư vấn tổ chức sự kiện Hình ảnh sự kiện Cập nhật tin tức Liên hệ ngay Thuê chú hề chuyên nghiệp Tiệc tất niên cho công ty Trang trí tiệc cuối năm Tiệc tất niên độc đáo Sinh nhật bé Hải Đăng Sinh nhật đáng yêu bé Khánh Vân Sinh nhật sang trọng Bích Ngân Tiệc sinh nhật bé Thanh Trang Dịch vụ ông già Noel Xiếc thú vui nhộn Biểu diễn xiếc quay đĩa Dịch vụ tổ chức tiệc uy tín Khám phá dịch vụ của chúng tôi Tiệc sinh nhật cho bé trai Trang trí tiệc cho bé gái Gói sự kiện chuyên nghiệp Chương trình giải trí hấp dẫn Dịch vụ hỗ trợ sự kiện Trang trí tiệc cưới đẹp Khởi đầu thành công với khai trương Chuyên gia tư vấn sự kiện Xem ảnh các sự kiện đẹp Tin mới về sự kiện Kết nối với đội ngũ chuyên gia Chú hề vui nhộn cho tiệc sinh nhật Ý tưởng tiệc cuối năm Tất niên độc đáo Trang trí tiệc hiện đại Tổ chức sinh nhật cho Hải Đăng Sinh nhật độc quyền Khánh Vân Phong cách tiệc Bích Ngân Trang trí tiệc bé Thanh Trang Thuê dịch vụ ông già Noel chuyên nghiệp Xem xiếc khỉ đặc sắc Xiếc quay đĩa thú vị
Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa
Thiết kế website Thiết kế website Thiết kế website Cách kháng tài khoản quảng cáo Mua bán Fanpage Facebook Dịch vụ SEO Tổ chức sinh nhật