Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/329.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何制作倒计时计时器(包括毫秒分和秒)c#_C#_Time - Fatal编程技术网

如何制作倒计时计时器(包括毫秒分和秒)c#

如何制作倒计时计时器(包括毫秒分和秒)c#,c#,time,C#,Time,我正在为我的测验做一个倒计时,目前有: 它倒计时,虽然当它达到0:00:00时,它只是不断下降,不会停止。另外,当我点击一个不正确的答案时,它会减去10秒,但是如果时间是1:01:00,我减去10秒,它会转到0:59:00而不是0:51:00。有什么帮助吗 标签3显示我的时间 int mili = 59; int second = 15; int minute = 2; private void TimerCountdown_Tick(object sender, Ev

我正在为我的测验做一个倒计时,目前有:

它倒计时,虽然当它达到0:00:00时,它只是不断下降,不会停止。另外,当我点击一个不正确的答案时,它会减去10秒,但是如果时间是1:01:00,我减去10秒,它会转到0:59:00而不是0:51:00。有什么帮助吗

标签3显示我的时间

    int mili = 59;
    int second = 15;
    int minute = 2;
 private void TimerCountdown_Tick(object sender, EventArgs e)
        {


            if (mili > 0 )
            {
                mili--;
            }
           

            if (mili <= 00 )
            {
                mili = 99;
                second--;
            }
            if (second <= 00)
            {
                second = 59;
                minute--;
            }

            label3.Text = minute.ToString() + ":" + second.ToString() + ":" + mili.ToString();


        }
intmili=59;
int秒=15;
int分钟=2;
私有void TimerCountdown_Tick(对象发送方,事件参数e)
{
如果(mili>0)
{
米利--;
}

如果(mili正如一些人在评论中指出的那样,最好使用TimeSpan类型来处理时间

要制作计时器,可以使用Stopwatch类,该类可以启动和停止,并具有已用时间属性

当你从预设时间中减去这个经过的时间,你基本上得到了一个倒计时计时器

您还需要添加/删除时间,因此您至少需要一个附加字段来存储此“奖金”时间,它可以是正的,也可以是负的

stopwatch类没有在特定时间引发的可用事件。因此,我添加了System.Timers.Timer字段(_zeroTimer),它在设定的时间后引发已用事件。计时器被赋予剩余时间,并在剩余时间为零时触发。每当添加/删除奖金时间,以及暂停后再次启动QuizTimer时,计时器都会用新的剩余时间重置。暂停时,我们也希望暂停此计时器,但因为System.Timers。计时器不允许这样,我们销毁它并在启动时重新创建它

我冒昧地为您制作了一个粗糙的QuizTimer类来实现这一点。使用它作为灵感和/或扩展它以满足您的需要

它有一个启动、暂停和重置方法,以及添加/删除时间方法。 您还可以选择是否允许负时间

您可以从TimeRemaining(TimeSpan)属性获取分钟、秒、毫秒。或者使用类中的其他属性公开它们

还有timeremainingclipped,它只是TimeRemaining值,但如果时间为负,则返回TimeSpan.Zero

当时间达到零时,将引发TimeZeroed事件。 如果“AllowNegativeValues”为负值,这也将停止/暂停QuizTimer

在测试过程中,我注意到时间归零事件后剩余的时间将有一个非常小的负值(1ms的分数)。为了防止向用户显示此值,您可以使用TimeRemainingClipped值或仅以1ms或1s的分辨率显示

它是有效的,但它是粗糙的,没有经过彻底的测试。我会让你来决定

using System;
using System.Diagnostics;
using System.Timers;

namespace QuizTimerNs
{
    public class QuizTimer
    {
        private Stopwatch _stopwatch;
        private Timer _zeroTimer;
        private TimeSpan _startTime;
        private TimeSpan _bonusTime = TimeSpan.Zero;

        public event EventHandler TimeZeroed;

        public TimeSpan TimeRemaining => _startTime + _bonusTime - (_stopwatch?.Elapsed ?? TimeSpan.Zero);
        public TimeSpan TimeRemainingClamped => TimeRemaining > TimeSpan.Zero ? TimeRemaining : TimeSpan.Zero;

        public int TimeRemaining_ms => (int)Math.Floor(TimeRemaining.TotalMilliseconds);
        public int TimeRemaining_s => (int)Math.Floor(TimeRemaining.TotalSeconds);
        public int TimeRemaining_min => (int)Math.Floor(TimeRemaining.TotalMinutes);

        public int TimeRemainingClamped_ms => (int)Math.Floor(TimeRemainingClamped.TotalMilliseconds);
        public int TimeRemainingClamped_s => (int)Math.Floor(TimeRemainingClamped.TotalSeconds);
        public int TimeRemainingClamped_min => (int)Math.Floor(TimeRemainingClamped.TotalMinutes);

        public bool AllowNegativeTime { get; set; } = false;


        public QuizTimer(TimeSpan startTime)
        {
            if (startTime == null) throw new ArgumentNullException(nameof(startTime));
            _stopwatch = new Stopwatch();
            _zeroTimer = null;
            _startTime = startTime;
        }

        public void Reset()
        {
            _stopwatch.Reset();
            _bonusTime = TimeSpan.Zero;
            EndZeroTimer();
        }

        private void EndZeroTimer()
        {
            if (_zeroTimer != null)
            {
                _zeroTimer.Stop();
                _zeroTimer.Elapsed -= OnZeroTimerElapsed;
                _zeroTimer.Dispose();
                _zeroTimer = null;
            }
        }

        private void ResetZeroTimerForRemainingTime()
        {
            if (_zeroTimer != null)
                EndZeroTimer();

            _zeroTimer = new Timer(TimeRemaining.TotalMilliseconds);
            _zeroTimer.Elapsed += OnZeroTimerElapsed;
            _zeroTimer.AutoReset = false;
        }

        public void Start()
        {
            if (!_stopwatch.IsRunning && (AllowNegativeTime || TimeRemaining >= TimeSpan.Zero))
            {
                ResetZeroTimerForRemainingTime();

                _stopwatch.Start();
                _zeroTimer.Start();
            }
        }

        private void OnZeroTimerElapsed(object sender, ElapsedEventArgs e)
        {
            if (!AllowNegativeTime)
                Pause();

            OnTimeZeroed();
        }

        public void AddTime(TimeSpan time)
        {
            _bonusTime = _bonusTime + time;

            EndZeroTimer();
            
            if (_stopwatch.IsRunning && TimeRemaining > TimeSpan.Zero)
            {
                ResetZeroTimerForRemainingTime();
                _zeroTimer.Start();
            }
        }

        public void RemoveTime(TimeSpan time)
        {
            _bonusTime = _bonusTime - time;
            
            EndZeroTimer();

            if (_stopwatch.IsRunning && TimeRemaining > TimeSpan.Zero)
            {
                ResetZeroTimerForRemainingTime();
                _zeroTimer.Start();
            }

            if (_stopwatch.IsRunning && TimeRemaining <= TimeSpan.Zero && !AllowNegativeTime)
            {
                Pause();
            }
        }

        public void Pause()
        {
            _stopwatch.Stop();
            EndZeroTimer();
        }

        private void OnTimeZeroed()
        {
            TimeZeroed?.Invoke(this, EventArgs.Empty);
        }
    }
}

使用系统;
使用系统诊断;
使用系统计时器;
名称空间QuizTimerNs
{
公共类QuizTimer
{
私人秒表(秒表);;
专用定时器_零定时器;
私人时间跨度(startTime);;
私有时间跨度_bonusTime=TimeSpan.Zero;
公共事件事件处理程序时间为零;
公共时间间隔剩余时间=>\u开始时间+\u停止时间-(\u秒表?已用时间??时间间隔.0);
公共TimeSpan TimeRemainingClamped=>TimeLeving>TimeSpan.Zero?TimeLeving:TimeSpan.Zero;
public int TimeRemaining_ms=>(int)Math.Floor(TimeRemaining.total毫秒);
public int TimeRemaining_s=>(int)Math.Floor(TimeRemaining.TotalSeconds);
公共整数TimeRemaining_min=>(整数)Math.Floor(TimeRemaining.TotalMinutes);
public int timeremainingclipped_ms=>(int)Math.Floor(timeremainingclipped.total毫秒);
公共int-timeremaingchemped\u s=>(int)Math.Floor(timeremaingchemped.TotalSeconds);
公共int timeremaingchemped_min=>(int)Math.Floor(timeremaingchemped.TotalMinutes);
public bool AllowNegativeTime{get;set;}=false;
公共提问时间(TimeSpan startTime)
{
如果(startTime==null)抛出新的ArgumentNullException(nameof(startTime));
_秒表=新秒表();
_zeroTimer=null;
_开始时间=开始时间;
}
公共无效重置()
{
_秒表复位();
_bonusTime=TimeSpan.Zero;
EndZeroTimer();
}
私有void EndZeroTimer()
{
如果(_zeroTimer!=null)
{
_zeroTimer.Stop();
_zeroTimer.Appeased-=OnZeroTimeRecursed;
_Dispose();
_zeroTimer=null;
}
}
私有void ResetZeroTimerForRemainingTime()
{
如果(_zeroTimer!=null)
EndZeroTimer();
_zeroTimer=新计时器(剩余时间.总毫秒);
_zeroTimer.Appeased+=OnZeroTimeRecursed;
_zeroTimer.AutoReset=false;
}
公开作废开始()
{
如果(!_stopwatch.IsRunning&(AllowNegativeTime | | TimeRemaining>=TimeSpan.Zero))
{
ResetZeroTimerForRemainingTime();
_秒表。开始();
_zeroTimer.Start();
}
}
ZeroTimeRecursed上的私有无效(对象发送方,ElapsedEventArgs e)
{
如果(!AllowNegativeTime)
暂停();
OnTimeZeroed();
}
公共无效添加时间(TimeSpan时间)
{
_博努斯蒂姆=_博努斯蒂姆+时间;
EndZeroTimer();
如果(_stopwatch.IsRunning&&TimeRemaining>TimeSpan.Zero)
{
ResetZeroTimerForRemainingTime();
_zeroTimer.Start();
}
}
公共无效删除时间(TimeSpan时间)
{
_bonusTime=_bonusTime-时间;
EndZeroTimer();
<Window x:Class="QuizTimerNs.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:QuizTimerNs"
        mc:Ignorable="d"
        Title="MainWindow" Height="200" Width="200">
    <StackPanel>
        <Button Content="Start" Click="StartButton_Click"></Button>
        <Button Content="Pause" Click="PauseButton_Click"></Button>
        <Button Content="Reset" Click="ResetButton_Click"></Button>
        <Button Content="Add 10 s"  Click="AddButton_Click"></Button>
        <Button Content="Remove 10 s"  Click="RemoveButton_Click"></Button>
        <TextBox x:Name="TimeRemainingTextBox"></TextBox>
        <TextBox x:Name="TimeRemainingTextBox2"></TextBox>
    </StackPanel>
</Window>
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
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.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using System.Windows.Threading;

namespace QuizTimerNs
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        private QuizTimer _quizTimer;

        public MainWindow()
        {
            _quizTimer = new QuizTimer(TimeSpan.FromSeconds(20));

            var timer = new DispatcherTimer(DispatcherPriority.Background) { Interval = TimeSpan.FromSeconds(0.1) };
            timer.Tick += (o, e) => Update();
            timer.Start();

            InitializeComponent();
        }

        private void StartButton_Click(object sender, RoutedEventArgs e) => _quizTimer.Start();
        private void PauseButton_Click(object sender, RoutedEventArgs e) => _quizTimer.Pause();
        private void ResetButton_Click(object sender, RoutedEventArgs e) => _quizTimer.Reset();
        private void AddButton_Click(object sender, RoutedEventArgs e) => _quizTimer.AddTime(TimeSpan.FromSeconds(10));
        private void RemoveButton_Click(object sender, RoutedEventArgs e) => _quizTimer.RemoveTime(TimeSpan.FromSeconds(10));


        private void Update()
        {
            TimeRemainingTextBox.Text = _quizTimer.TimeRemaining.ToString();
            TimeRemainingTextBox2.Text = _quizTimer.TimeRemainingClamped.ToString();
        }
    }
}