iFactory.Godot/Artists/Scripts/Data/DataPlayer.cs

187 lines
4.1 KiB
C#

using Godot;
using System;
using System.Timers;
namespace BITKit;
/// <summary>
/// 默认的String数据播放器,主要应用于播放json
/// </summary>
public partial class DataPlayer : Node
{
//参数
/// <summary>
/// 当前帧
/// </summary>
[Export]
public int CurrentFrame
{
get => _currentFrame;
set => _currentFrame = Math.Clamp(value, 0, Values?.Length ?? 0);
}
/// <summary>
/// 播放帧率
/// </summary>
[Export] private int frameRate = 60;
[Export] private string timeFormat="mm:ss:fff";
/// <summary>
/// 基于帧率的每帧播放数据
/// </summary>
[Signal]
public delegate void OnProcessPlayEventHandler(string value);
/// <summary>
/// 开始播放回调
/// </summary>
[Signal]
public delegate void OnPlayEventHandler();
/// <summary>
/// 暂停回调
/// </summary>
[Signal]
public delegate void OnPauseEventHandler();
/// <summary>
/// 播放和暂停回调
/// </summary>
[Signal]
public delegate void OnPlayOrPauseEventHandler(bool isPlaying);
/// <summary>
/// 设置总播放时间的回调
/// </summary>
[Signal]
public delegate void OnSetTotalTimeEventHandler(string dateTimeString);
/// <summary>
/// 设置当前播放时间的回调
/// </summary>
[Signal]
public delegate void OnSetPlaybackTimeEventHandler(string dateTimeString);
/// <summary>
/// 设置标准化播放时间的回调
/// </summary>
[Signal]
public delegate void OnSetNormalizeTimeEventHandler(double normalizeTime);
/// <summary>
/// 是否正在播放
/// </summary>
public bool IsPlaying { get; protected set; }
/// <summary>
/// 是否已暂停播放
/// </summary>
public bool IsPaused { get; protected set; }
/// <summary>
/// 内部计时器
/// </summary>
private readonly System.Timers.Timer timer = new();
/// <summary>
/// 内部数组
/// </summary>
private string[] Values;
//内部当前帧
private int _currentFrame;
public override void _Ready()
{
timer.Elapsed += Play;
}
/// <summary>
/// 播放
/// </summary>
/// <param name="values">播放数据的数组</param>
public bool Play(string[] values)
{
if (values?.Length is 0) return false;
if (values?.Length != Values?.Length)
{
CurrentFrame = 0;
}
Values = values;
timer.Interval = TimeSpan.FromSeconds(1f / frameRate).Milliseconds;
timer.Start();
return true;
}
/// <summary>
/// 播放(在暂停时)
/// </summary>
/// <returns></returns>
public bool Play()
{
if (!IsPlaying) return false;
IsPaused = false;
return true;
}
/// <summary>
/// 停止播放
/// </summary>
/// <returns></returns>
public bool Stop()
{
if (!IsPlaying) return false;
timer.Stop();
IsPlaying = IsPaused = false;
return true;
}
/// <summary>
/// 暂停播放
/// </summary>
/// <returns></returns>
public bool Pause()
{
if (!IsPlaying) return false;
IsPaused = true;
return true;
}
/// <summary>
/// 继续播放或暂停播放
/// </summary>
/// <returns></returns>
public bool PlayOrPause()
{
if (!IsPlaying) return false;
IsPaused = !IsPaused;
return true;
}
protected override void Dispose(bool disposing)
{
timer.Stop();
timer.Dispose();
}
/// <summary>
/// 内部调用方法
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
protected virtual void Play(object sender, ElapsedEventArgs e)
{
if (IsPlaying is false || IsPaused) return;
if (CurrentFrame > Values?.Length)
{
Stop();
return;
}
var current = Values?[CurrentFrame++];
var variant = Variant.From(current);
EmitSignal(nameof(OnProcessPlayEventHandler), variant);
}
}