이클립스 흐름 — 배너 진입 · 이벤트 버튼 · 오버레이 · 방어 진행 표시 · 흔들기 감지 통일

This commit is contained in:
Sn-Kinos
2026-10-05 19:05:21 +09:00
parent be623d2e46
commit 576dcfbdfd
27 changed files with 1369 additions and 369 deletions
@@ -1,5 +1,4 @@
import 'dart:async';
import 'dart:math' as math;
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:sensors_plus/sensors_plus.dart';
@@ -8,6 +7,7 @@ import '../../core/data/backend.dart';
import '../../core/ui/live_stream.dart';
import 'planet_data.dart';
import '../../core/i18n/app_locale.dart';
import '../quest/quest_evidence.dart' show ShakeDetector;
/// 수량·상한·중복 여부는 서버가 결정한다. 단말은 참여 의사와 결과만 전달한다.
class HeroParticipationSheet extends StatefulWidget {
@@ -38,24 +38,16 @@ class _HeroParticipationSheetState extends State<HeroParticipationSheet>
bool _sending = false;
bool _failed = false;
bool _foreground = true;
DateTime _lastShake = DateTime.fromMillisecondsSinceEpoch(0);
@override
void initState() {
super.initState();
WidgetsBinding.instance.addObserver(this);
_sensor = (widget.accelerometer ?? accelerometerEventStream()).listen((
event,
) {
final magnitude = math.sqrt(
event.x * event.x + event.y * event.y + event.z * event.z,
);
final now = DateTime.now();
if (!magnitude.isFinite ||
magnitude < 18 ||
now.difference(_lastShake).inMilliseconds < 220)
return;
_lastShake = now;
final shakes = ShakeDetector();
_sensor = (widget.accelerometer ??
accelerometerEventStream(samplingPeriod: ShakeDetector.sampling))
.listen((event) {
if (!shakes.add(event.x, event.y, event.z, DateTime.now())) return;
if (!_failed) _claim();
}, onError: (_) {}); // 센서가 없어도 동일한 서버 경로의 참여 버튼을 제공한다.
}