diff --git a/Wpf_AiSportsMicrospace/Common/SportOperate.cs b/Wpf_AiSportsMicrospace/Common/SportOperate.cs index f1a5c27..e7cd12a 100644 --- a/Wpf_AiSportsMicrospace/Common/SportOperate.cs +++ b/Wpf_AiSportsMicrospace/Common/SportOperate.cs @@ -1,4 +1,5 @@ using HandyControl.Controls; +using SportExpand; using System; using System.Collections.Generic; using System.Linq; @@ -24,18 +25,13 @@ namespace Wpf_AiSportsMicrospace.Common { IPointTracker _leftTracker; IPointTracker _rightTracker; - IPointTracker _leftElbow; - IPointTracker _rightElbow; + private int _leftWaveCount = 0; + private int _rightWaveCount = 0; + private const int WaveThreshold = 4; WebcamClient _webcamClient; - private DateTime _lastActionTime = DateTime.MinValue; - - private Point? _lastLeftWrist = null; - private Point? _lastRightWrist = null; private DateTime? _raiseStartTime = null; private DateTime? _wristStartTime = null; - private double _leftWristDeltaX = 0; - private double _rightWristDeltaX = 0; private bool _firstHandTriggered = false; @@ -43,13 +39,9 @@ namespace Wpf_AiSportsMicrospace.Common { _leftTracker = PostureCalculate.CreatePointTracker("left_wrist", 0); _rightTracker = PostureCalculate.CreatePointTracker("right_wrist", 0); - _leftElbow = PostureCalculate.CreatePointTracker("left_elbow", 0); - _rightElbow = PostureCalculate.CreatePointTracker("right_elbow", 0); - //_leftTracker.Amplitude = 0.03f; - //_rightTracker.Amplitude = 0.03f; - //_leftElbow.Amplitude = 0.03f; - //_rightElbow.Amplitude = 0.03f; + _leftTracker.Amplitude = 0.3f; + _rightTracker.Amplitude = 0.3f; } public WebcamClient CreateRTSP() @@ -65,6 +57,7 @@ namespace Wpf_AiSportsMicrospace.Common return _webcamClient; } + public int VerifyWavingAction(List humans) { if (humans == null || humans.Count == 0) @@ -83,47 +76,43 @@ namespace Wpf_AiSportsMicrospace.Common if (!(xNorm >= 0.44 && xNorm <= 0.57 && yNorm >= 0.81)) continue; - var leftWrist = human.Keypoints.FirstOrDefault(x => x.Name == "left_wrist"); - var leftElbow = human.Keypoints.FirstOrDefault(x => x.Name == "left_elbow"); - var rightWrist = human.Keypoints.FirstOrDefault(x => x.Name == "right_wrist"); - var rightElbow = human.Keypoints.FirstOrDefault(x => x.Name == "right_elbow"); - // --- 右手举手优先 --- int rightHandAction = DetectRightHandRaise(human); if (rightHandAction != (int)WavingAction.None) return rightHandAction; - // --- 左手挥手 --- - if (leftWrist != null && leftElbow != null) + var leftValue = _leftTracker.Tracking(human); + var rightValue = _rightTracker.Tracking(human); + + // ===== 左挥手判定 ===== + if (leftValue == 1 || leftValue == 2) + _leftWaveCount++; + //else + // _leftWaveCount = 0; + + // ===== 右挥手判定 ===== + if (rightValue == 1 || rightValue == 2) + _rightWaveCount++; + //else + // _rightWaveCount = 0; + + // ===== 触发判断 ===== + if (_leftWaveCount >= WaveThreshold) { - int leftResult = DetectHorizontalWave( - new Point(leftWrist.X, leftWrist.Y), - new Point(leftElbow.X, leftElbow.Y), - ref _lastLeftWrist, - ref _leftWristDeltaX, - true); - if (leftResult != (int)WavingAction.None) - return leftResult; + _leftWaveCount = 0; // 只重置左手 + return (int)WavingAction.LeftWave; } - // --- 右手挥手 --- - //if (rightWrist != null && rightElbow != null) - //{ - // int rightWaveResult = DetectHorizontalWave( - // new Point(rightWrist.X, rightWrist.Y), - // new Point(rightElbow.X, rightElbow.Y), - // ref _lastRightWrist, - // ref _rightWristDeltaX, - // false); - // if (rightWaveResult != (int)WavingAction.None) - // return rightWaveResult; - //} + if (_rightWaveCount >= WaveThreshold) + { + _rightWaveCount = 0; // 只重置右手 + return (int)WavingAction.RightWave; + } } return (int)WavingAction.None; } - /// /// 检测右手举手状态 /// @@ -131,16 +120,11 @@ namespace Wpf_AiSportsMicrospace.Common /// 返回 WavingAction:FirstHand / Raising / RaiseHand / None public int DetectRightHandRaise(Human human) { - var rightWrist = human.Keypoints.FirstOrDefault(k => k.Name == "right_wrist"); - var rightElbow = human.Keypoints.FirstOrDefault(k => k.Name == "right_elbow"); + var calculator = PostureCalculate.CreateCalculator(); + var rule = RaiseHand.RaiseRightHand(); + var pass = calculator.Calculating(human, rule); - if (rightWrist == null || rightElbow == null) - return (int)WavingAction.None; - - double verticalRise = rightElbow.Y - rightWrist.Y; // 手腕在肘上方 → 正值 - const double raiseThreshold = 60; // 举手阈值,可根据实际调整 - - if (verticalRise >= raiseThreshold) + if (pass) { // 初始化计时 if (_raiseStartTime == null) _raiseStartTime = DateTime.Now; @@ -177,44 +161,5 @@ namespace Wpf_AiSportsMicrospace.Common return (int)WavingAction.None; } } - - /// - /// 统一的水平挥手检测 - /// - private int DetectHorizontalWave(Point wrist, Point elbow, ref Point? lastWrist, ref double deltaX, bool isLeft) - { - if (lastWrist != null) - { - double dx = wrist.X - lastWrist.Value.X; - double dy = Math.Abs(wrist.Y - lastWrist.Value.Y); - - // 累计水平位移 - deltaX += dx; - - if (Math.Abs(deltaX) > 40 && dy < 60 && Math.Abs(wrist.Y - elbow.Y) < 60) - { - deltaX = 0; // 重置 - if (CheckCooldown()) - { - return isLeft ? (int)WavingAction.LeftWave : (int)WavingAction.RightWave; - } - } - } - - lastWrist = wrist; - return (int)WavingAction.None; - } - - /// - /// 冷却防抖(避免重复触发) - /// - private bool CheckCooldown(int cooldownMs = 1000) - { - if ((DateTime.Now - _lastActionTime).TotalMilliseconds < cooldownMs) - return false; - - _lastActionTime = DateTime.Now; - return true; - } } } diff --git a/Wpf_AiSportsMicrospace/SportExpand/RaiseHand.cs b/Wpf_AiSportsMicrospace/SportExpand/RaiseHand.cs new file mode 100644 index 0000000..15fe15e --- /dev/null +++ b/Wpf_AiSportsMicrospace/SportExpand/RaiseHand.cs @@ -0,0 +1,45 @@ +using System; +using System.Collections.Generic; +using System.Text; +using Yztob.AiSports.Postures.Things; + +namespace SportExpand +{ + /// + /// 举右手 + /// + public class RaiseHand + { + /// + /// 举右手 + /// + /// + public static CalcBaseRule RaiseRightHand() + { + return new CalcPositionRule() + { + Name = "右手是否举过头顶", + PositionKey = "right_wrist", + ReferenceKey = "right_eye", + Position = "top", + Relaxed = true + }; + } + + /// + /// 举左手 + /// + /// + public static CalcBaseRule RaiseLeftHand() + { + return new CalcPositionRule + { + Name = "左手是否举过头顶", + PositionKey = "left_wrist", + ReferenceKey = "left_eye", + Position = "top", + Relaxed = true + }; + } + } +} diff --git a/Wpf_AiSportsMicrospace/Views/JumpLong/StandingLeap - 复制.xaml.cs b/Wpf_AiSportsMicrospace/Views/JumpLong/StandingLeap - 复制.xaml.cs deleted file mode 100644 index c736ef3..0000000 --- a/Wpf_AiSportsMicrospace/Views/JumpLong/StandingLeap - 复制.xaml.cs +++ /dev/null @@ -1,568 +0,0 @@ -//using AiSportsMicrospaceDB.DBContext; -//using Dto; -//using Enum; -//using Microsoft.Extensions.DependencyInjection; -//using System; -//using System.Collections.Concurrent; -//using System.Collections.Generic; -//using System.IO; -//using System.Text; -//using System.Windows; -//using System.Windows.Controls; -//using System.Windows.Data; -//using System.Windows.Documents; -//using System.Windows.Input; -//using System.Windows.Media; -//using System.Windows.Media.Animation; -//using System.Windows.Media.Imaging; -//using System.Windows.Navigation; -//using System.Windows.Shapes; -//using Wpf_AiSportsMicrospace; -//using Wpf_AiSportsMicrospace.Common; -//using Wpf_AiSportsMicrospace.Enum; -//using Wpf_AiSportsMicrospace.MyUserControl; -//using Wpf_AiSportsMicrospace.Views; -//using Yztob.AiSports.Inferences.Abstractions; -//using Yztob.AiSports.Inferences.Implement; -//using Yztob.AiSports.Inferences.Things; -//using Yztob.AiSports.Postures.Sports; -//using Yztob.AiSports.Postures.Things; -//using Yztob.AiSports.Sensors.Abstractions; -//using Yztob.AiSports.Sensors.Things; - -//namespace Views.JumpLong -//{ -// /// -// /// StandingLeap.xaml 的交互逻辑 -// /// -// public partial class StandingLeap : UserControl -// { -// #region 私有成员 -// private Main _mainWin => Application.Current.MainWindow as Main; -// private IHumanPredictor _humanPredictor; -// private IObjectDetector _objectDetector; -// private HumanGraphicsRenderer _humanGraphicsRenderer; -// private SportBase _sport; -// private ApparatusLongJumpDelineation _measureApparatus; -// private MediaPlayer _mediaPlayer = new MediaPlayer(); -// private readonly SportDetectionQueue _detectQueue; - -// private int _sportType = 0; // 0:未开始 1:运动中 2:运动结束展示排行榜 - -// #endregion - -// public StandingLeap() -// { -// InitializeComponent(); -// Loaded += UserControl_Loaded; -// Unloaded += UserControl_Unloaded; - -// _humanPredictor = HumanPredictorFactory.Create(HumanPredictorType.SingleHigh); -// _humanGraphicsRenderer = new HumanGraphicsRenderer(); -// _humanGraphicsRenderer.DrawLabel = false; -// _objectDetector = ObjectDetectorFactory.CreateSportGoodsDetector(); -// _detectQueue = new SportDetectionQueue(); - -// _sport = SportBase.Create("standing-long-jump"); -// _sport.OnTicked += this.OnSportTick; -// _mainWin.HumanFrameUpdated += OnHumanFrameUpdated; - -// } - -// private async void UserControl_Loaded(object sender, RoutedEventArgs e) -// { -// // 播放音乐 -// PlayMusic("raisehand.mp3"); -// } - - -// //举手检测 -// private void OnHumanFrameUpdated(object sender, List humans) -// { -// try -// { -// if (humans == null || humans.Count == 0) return; - -// //举手检测 未开始 :退出& 开始 运动中:不检测 2.结束:继续测试 & 退出 -// if (_sportType != 1) -// { -// //左手返回 -// int leftWaving = DetectLeftHandRaise(humans); -// if (leftWaving == 5) -// { -// _mainWin.HumanFrameUpdated -= OnHumanFrameUpdated; -// _mainWin.WebcamClient.StopExtract(); - -// // 举左手逻辑,例如结束动画或退出 -// var newPage = new Home(); -// _mainWin?.SwitchPageWithMaskAnimation(newPage, true); -// return; // 提前退出 -// } - -// //右手判断 -// int rightWaving = DetectRightHandRaise(humans); -// if (rightWaving >= 3 && _sportType == 0) //举手完成 开始跳远检测 -// { -// Utils.PlayBackgroundMusic("countdown_3.mp3", false); -// _sportType = 1; -// StartSport(); -// } -// } -// } -// catch (Exception ex) -// { -// Console.WriteLine("OnFrameExtracted error: " + ex.Message); -// } -// } - - -// private void UserControl_Unloaded(object sender, RoutedEventArgs e) -// { -// _sport.Stop(); -// _humanPredictor?.Dispose(); -// _objectDetector?.Dispose(); -// } - -// private async void HumanPredicting(VideoFrame frame) -// { -// try -// { -// var buffer = frame.GetImageBuffer(ImageFormat.Jpeg).ToArray(); -// var humanResult = await Task.Run(() => _humanPredictor.Predicting(buffer, frame.Number)); -// var objects = _sport.Equipment ? await Task.Run>(() => _objectDetector.Detecting(buffer)) : new List(); -// if (_sport.MeasureApparatus != null) -// objects.AddRange(_sport.MeasureApparatus.Apparatuses); - -// //运动需要保证时序 -// var human = humanResult?.Humans?.FirstOrDefault(); -// _detectQueue.Enqueue(frame.Number, human, objects); -// } -// catch (Exception ex) -// { -// Console.WriteLine("ProcessFrame error: " + ex.Message); -// } -// } - -// //播放音乐 -// private void PlayMusic(string musicFileName) -// { -// // 获取项目根目录 -// string projectRoot = System.IO.Path.Combine(AppContext.BaseDirectory, @"..\..\.."); -// string musicPath = System.IO.Path.Combine(projectRoot, "Resources", "Music", musicFileName); - -// if (!File.Exists(musicPath)) -// { -// Console.WriteLine($"音乐文件不存在: {musicPath}"); -// return; -// } - -// _mediaPlayer.Open(new Uri(musicPath, UriKind.Absolute)); - -// ShowCenterTip(TimeSpan.FromSeconds(3)); - -// // 监听播放完成事件 -// _mediaPlayer.MediaEnded += MediaPlayer_MediaEnded; -// //_mainWin.WebcamClient.StartExtract(); -// _mediaPlayer.Play(); -// } -// private void ShowCenterTip(TimeSpan duration) -// { -// // 渐变出现动画 -// var fadeInAnimation = new DoubleAnimation -// { -// From = 0, -// To = 1, -// Duration = TimeSpan.FromSeconds(1.5) -// }; -// TipBox.BeginAnimation(UIElement.OpacityProperty, fadeInAnimation); - -// // 定时移除,并且渐变消失 -// Task.Delay(duration).ContinueWith(_ => -// { -// Dispatcher.Invoke(() => -// { -// // 渐变消失动画 -// var fadeOutAnimation = new DoubleAnimation -// { -// From = 1, -// To = 0, -// Duration = TimeSpan.FromSeconds(1.5) -// }; -// TipBox.BeginAnimation(UIElement.OpacityProperty, fadeOutAnimation); - -// }); -// }); - -// } -// private void MediaPlayer_MediaEnded(object sender, EventArgs e) -// { -// // 音乐播放完成后的逻辑 -// Console.WriteLine("音乐播放完成!"); -// } - -// private void OnSportTick(int counts, int times) -// { -// var ts = TimeSpan.FromSeconds(times); -// _ = Dispatcher.BeginInvoke(() => -// { -// //sportCounts.Content = _sport.GetFormatCounts(); //counts.ToString(); -// //sportTimes.Content = _sport.GetFormatTimes();//ts.ToString(@"mm\'ss\"""); -// var counts = _sport.GetFormatCounts(); -// if (double.Parse(counts[..^1]) > 0 && _sportType == 1) //正向跳远时候&&处于测试阶段时候触发更新 -// { -// _sport.Stop();//关闭运动 - -// count.Text = counts; -// time.Text = _sport.GetFormatTimes(); -// ShowRope(); -// if (!_sport.IsCounting) -// { -// _sport.Stop(); -// _sport.Start(); -// } -// } -// }); -// } - -// //展示成绩 -// private async void ShowRope() -// { -// // 渐变出现动画 -// var fadeInAnimation = new DoubleAnimation -// { -// From = 0, -// To = 1, -// Duration = TimeSpan.FromSeconds(1.5) -// }; -// var fadeInAnimation1 = new DoubleAnimation -// { -// From = 1, -// To = 0, -// Duration = TimeSpan.FromSeconds(1.5) -// }; -// //videoImage.Opacity = 0; -// //centerImg1.Opacity = 1; -// //centerImg2.Opacity = 1; -// //centerImg3.Opacity = 1; -// _sportType = 2; -// RankingGrid.BeginAnimation(UIElement.OpacityProperty, fadeInAnimation); -// //_mainWin.WebcamClient.OnExtractFrame -= this.OnFrameExtracted; -// for (int i = 12; i >= 0; i--) -// { -// countDown.Text = i.ToString() + "s"; -// if(i == 1) -// { -// RankingGrid.BeginAnimation(UIElement.OpacityProperty, fadeInAnimation1); -// _sportType = 0; -// PlayMusic("raisehand.mp3"); -// } -// await Task.Delay(1000); -// } -// // 关闭跳远抽帧线程 -// } - -// //关闭成绩展示 显示跳远页面 -// private void closRope() -// { -// //关闭动画 -// //var fadeInAnimation = new DoubleAnimation -// //{ -// // From = 1, -// // To = 0, -// // Duration = TimeSpan.FromSeconds(1) -// //}; -// // RankingGrid.BeginAnimation(UIElement.OpacityProperty, fadeInAnimation); -// RankingGrid.Opacity = 0; -// _sportType = 0; -// PlayMusic("raisehand.mp3"); -// } -// private bool ReactangleCalibrating(int frameWidth, int frameHeight) -// { - -// var mainWin = Application.Current.MainWindow as Main; -// var app = (App)Application.Current; -// using var scope = App.AppHost.Services.CreateScope(); -// var db = scope.ServiceProvider.GetRequiredService(); -// var points = db.JumpLongPoints.FirstOrDefault(); -// var boxes = new List() -// { -// new BoundingBox(){ -// ImageWidth = frameWidth, -// ImageHeight = frameHeight, -// Label = new PredictionLabel(){ -// Key = "begin" -// }, -// MaskLayer = new MaskLayer(){ -// Contours = [ -// new ((float)points.BottomPoint3.X, (float)points.BottomPoint3.Y), -// new ((float)points.TopPoint3.X, (float)points.TopPoint3.Y), -// ] -// } -// }, -// new BoundingBox(){ -// ImageWidth = frameWidth, -// ImageHeight = frameHeight, -// Label = new PredictionLabel{ -// Key = "end" -// }, -// MaskLayer = new MaskLayer(){ -// Contours = [ -// new((float)points.BottomPoint2.X, (float)points.BottomPoint2.Y), -// new((float)points.TopPoint2.X, (float)points.TopPoint2.Y), -// ] -// } -// } -// }; - -// boxes[1].Label.Key = "take-off"; -// boxes.Add(new BoundingBox() -// { -// ImageWidth = frameWidth, -// ImageHeight = frameHeight, -// Label = new PredictionLabel -// { -// Key = "end" -// }, -// MaskLayer = new MaskLayer() -// { -// Contours = [ -// new ((float)points.BottomPoint1.X, (float)points.BottomPoint1.Y), -// new ((float)points.TopPoint1.X, (float)points.TopPoint1.Y), -// ] -// } -// }); - -// return _measureApparatus.Calibrating(boxes); -// } - - -// public int DetectLeftHandRaise(List humans) -// { -// if (humans == null || humans.Count == 0) -// return (int)WavingAction.None; - - -// foreach (var human in humans) -// { -// if (human?.Keypoints == null) -// continue; - -// // --- 筛选右脚踝坐标 --- -// var rightAnkle = human.Keypoints.FirstOrDefault(k => k.Name == "right_ankle"); -// if (rightAnkle == null) -// continue; -// double xNorm = rightAnkle.X / 1920; -// double yNorm = rightAnkle.Y / 1080; -// // 仅检测中心区域内的人 -// if (!(xNorm >= 0.44 && xNorm <= 0.57 && yNorm >= 0.81)) -// continue; - -// // 获取左手关键点 -// var leftWrist = human.Keypoints.FirstOrDefault(k => k.Name == "left_wrist"); -// var leftElbow = human.Keypoints.FirstOrDefault(k => k.Name == "left_elbow"); - -// if (leftWrist == null || leftElbow == null) -// continue; - -// const double raiseThreshold = 60; // 举手阈值 - -// // 判断左手是否举起 -// double verticalRise = leftElbow.Y - leftWrist.Y; -// if (verticalRise >= raiseThreshold) -// { -// return (int)WavingAction.RaiseHand; // 一旦检测到左手举起,立即返回 -// } -// } - -// return (int)WavingAction.None; // 没有检测到举手 -// } - -// private DateTime? _raiseStartTime; -// private bool _firstHandTriggered; -// private int _lastCountdownSecond = 3; -// private DateTime? _countdownStartTime; -// public int DetectRightHandRaise(List humans) -// { -// if (humans == null || humans.Count == 0) -// return (int)WavingAction.None; - -// foreach (var human in humans) -// { -// if (human?.Keypoints == null) -// continue; - -// // --- 筛选右脚踝坐标 --- -// var rightAnkle = human.Keypoints.FirstOrDefault(k => k.Name == "right_ankle"); -// if (rightAnkle == null) -// continue; - -// //double xNorm = rightAnkle.X / 1920; -// //double yNorm = rightAnkle.Y / 1080; - - -// var app = (App)Application.Current; -// using var scope = App.AppHost.Services.CreateScope(); -// var db = scope.ServiceProvider.GetRequiredService(); -// var points = db.JumpLongPoints.FirstOrDefault(); - -// // 检测起跳区域的人 - -// var isinx = (rightAnkle.X < points.TopPoint3.X && rightAnkle.X > points.TopPoint2.X) || (rightAnkle.X < points.BottomPoint3.X && rightAnkle.X > points.BottomPoint2.X) ; -// if(points.TopPoint3.X < points.TopPoint2.X) -// { -// isinx = (rightAnkle.X > points.TopPoint3.X && rightAnkle.X < points.TopPoint2.X) || (rightAnkle.X > points.BottomPoint3.X && rightAnkle.X < points.BottomPoint2.X); -// } -// var isiny = (rightAnkle.Y > points.TopPoint3.Y && rightAnkle.X < points.BottomPoint3.Y) || (rightAnkle.Y < points.TopPoint2.Y && rightAnkle.X > points.BottomPoint2.Y) ; -// if (!isinx || !isiny) continue; - - -// var rightWrist = human.Keypoints.FirstOrDefault(k => k.Name == "right_wrist"); -// var rightElbow = human.Keypoints.FirstOrDefault(k => k.Name == "right_elbow"); - -// const double raiseThreshold = 60; // 举手阈值 -// const double holdDuration = 1; // 持续时间(秒) -// const int countdownSeconds = 3; // 倒计时长度 - -// bool handRaised = false; - -// if (rightWrist != null && rightElbow != null) -// { -// double verticalRise = rightElbow.Y - rightWrist.Y; -// handRaised = verticalRise >= raiseThreshold; -// } - -// // ---------- 第一步:持续举手触发倒计时 ---------- -// if (!_firstHandTriggered) -// { - -// if (handRaised) -// { -// _raiseStartTime ??= DateTime.Now; -// var holdElapsed = (DateTime.Now - _raiseStartTime.Value).TotalSeconds; -// if (holdElapsed >= holdDuration) -// { -// // 举手达到指定时间,启动倒计时 -// _firstHandTriggered = true; -// return (int)WavingAction.FirstHand; -// } -// } -// else -// { -// // 手放下,重置举手开始时间 -// _raiseStartTime = DateTime.Now; -// } - -// continue; // 本人未触发,检测下一个人 -// } - -// // ---------- 第二步:倒计时逻辑 ---------- -// var countdownElapsed = (DateTime.Now - _countdownStartTime.Value).TotalSeconds; -// int currentSecond = countdownSeconds - (int)Math.Floor(countdownElapsed); - -// if (currentSecond > 0 && currentSecond != _lastCountdownSecond) -// { -// _lastCountdownSecond = currentSecond; -// Console.WriteLine($"倒计时:{currentSecond}"); -// return (int)WavingAction.Raising; // 倒计时中 -// } - -// if (countdownElapsed >= countdownSeconds) -// { -// ResetRaiseState(); -// return (int)WavingAction.RaiseHand; // 举手完成 -// } - -// return (int)WavingAction.Raising; -// } - -// // 没有任何中心区域内的人举手 -// return (int)WavingAction.None; -// } - -// private void ResetRaiseState() -// { -// _raiseStartTime = null; -// _countdownStartTime = null; -// _firstHandTriggered = false; -// _lastCountdownSecond = 3; -// } - -// private void StartSport() -// { - - -// //if (_sport?.IsCounting == true) -// //_mainWin.WebcamClient.OnExtractFrame += this.OnFrameExtracted; -// _sport.Start(); - -// _measureApparatus = new ApparatusLongJumpDelineation(); -// _measureApparatus.MeasureLength = 300; -// var _isCalibrated = this.ReactangleCalibrating(1920, 1080); -// _sport.MeasureApparatus = _measureApparatus; -// _detectQueue.Sport = _sport; -// _detectQueue.Start(); - -// // 开始跳远抽帧线程 -// _mainWin.FacialRecognitionEvent += HumanPredicting; -// } - -// private WriteableBitmap _videoBitmap; -// private int _lastFrameNumber = -1; -// private async void OnFrameExtracted(VideoFrame frame) -// { -// if (frame == null) return; - -// // 跳帧:每秒只渲染 10~15 帧,降低 CPU 占用 - -// if (frame.Number %2 != 0) return; - -// if (_lastFrameNumber != -1 && frame.Number - _lastFrameNumber < 2) return; -// _lastFrameNumber = (int)frame.Number; - -// //获得帧二进制流,保存图像、人体识别竺 -// var buffer = frame.GetImageBuffer(Yztob.AiSports.Sensors.Things.ImageFormat.Jpeg).ToArray(); -// //await File.WriteAllBytesAsync($"./temps/{frame.Number}.jpg", buffer); - -// // === 显示到 WPF === -// BitmapImage bitmap = null; -// await Task.Run(() => -// { -// using var ms = new MemoryStream(buffer); -// bitmap = new BitmapImage(); -// bitmap.BeginInit(); -// bitmap.CacheOption = BitmapCacheOption.OnLoad; -// bitmap.StreamSource = ms; -// bitmap.EndInit(); -// bitmap.Freeze(); // 跨线程安全 -// }); - -// // UI 线程显示 -// Application.Current.Dispatcher.Invoke(() => -// { -// if (videoImage == null) return; - -// if (_videoBitmap == null || -// _videoBitmap.PixelWidth != bitmap.PixelWidth || -// _videoBitmap.PixelHeight != bitmap.PixelHeight) -// { -// _videoBitmap = new WriteableBitmap(bitmap.PixelWidth, bitmap.PixelHeight, -// 96, 96, PixelFormats.Bgra32, null); -// videoImage.Source = _videoBitmap; -// } - -// _videoBitmap.Lock(); -// bitmap.CopyPixels(new Int32Rect(0, 0, bitmap.PixelWidth, bitmap.PixelHeight), -// _videoBitmap.BackBuffer, -// _videoBitmap.BackBufferStride * bitmap.PixelHeight, -// _videoBitmap.BackBufferStride); -// _videoBitmap.AddDirtyRect(new Int32Rect(0, 0, bitmap.PixelWidth, bitmap.PixelHeight)); -// _videoBitmap.Unlock(); - -// videoImage.Opacity = 1; -// centerImg1.Opacity = 0; -// centerImg2.Opacity = 0; -// centerImg3.Opacity = 0; -// }); -// } -// } -//}