From 50955e84c75db4e88306c8a4b8477e42f046573b Mon Sep 17 00:00:00 2001 From: Solin Date: Sat, 17 Jan 2026 14:12:52 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=B7=BB=E5=8A=A0=E6=9A=82=E5=81=9C?= =?UTF-8?q?=E5=92=8C=E6=81=A2=E5=A4=8D=E5=8A=9F=E8=83=BD=E4=BB=A5=E4=BC=98?= =?UTF-8?q?=E5=8C=96=E5=B7=A5=E4=BD=9C=E8=AE=A1=E6=97=B6=E7=AE=A1=E7=90=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ActivityMonitor.cs | 60 ++++++++++++++++++++++++++++++++++++++++++++ MainForm.Designer.cs | 29 +++++++++++++++++---- MainForm.cs | 32 +++++++++++++++++++++-- 3 files changed, 114 insertions(+), 7 deletions(-) diff --git a/ActivityMonitor.cs b/ActivityMonitor.cs index 52b0527..086e4de 100644 --- a/ActivityMonitor.cs +++ b/ActivityMonitor.cs @@ -17,6 +17,10 @@ namespace TimerApp private TimeSpan _accumulatedWorkTime; private DateTime _restStartTime; private int _restElapsedSeconds; // 休息已过秒数(用于避免时间计算导致的跳变) + private bool _isPaused = false; // 暂停状态 + private DateTime _pauseStartTime; // 暂停开始时间 + private TimeSpan _pauseDuration = TimeSpan.Zero; // 累计暂停时间(用于工作计时) + private int _restPauseStartSeconds = 0; // 休息暂停时的已过秒数 // 配置 (默认值) public TimeSpan WorkDuration { get; set; } = TimeSpan.FromMinutes(20); @@ -24,6 +28,7 @@ namespace TimerApp public TimeSpan IdleThreshold { get; set; } = TimeSpan.FromSeconds(30); public MonitorState CurrentState { get; private set; } = MonitorState.Idle; + public bool IsPaused { get; private set; } = false; // 事件 public event EventHandler WorkProgressChanged; // 剩余工作时间 @@ -68,6 +73,12 @@ namespace TimerApp private void Timer_Tick(object sender, EventArgs e) { + // 如果处于暂停状态,不处理计时逻辑 + if (_isPaused) + { + return; + } + long idleMs = NativeMethods.GetIdleTime(); TimeSpan idleTime = TimeSpan.FromMilliseconds(idleMs); @@ -188,6 +199,9 @@ namespace TimerApp { _accumulatedWorkTime = TimeSpan.Zero; _lastWorkStartTime = DateTime.Now; + _isPaused = false; + IsPaused = false; + _pauseDuration = TimeSpan.Zero; // Ensure timer is running if (!_timer.Enabled) _timer.Start(); @@ -198,5 +212,51 @@ namespace TimerApp // Immediately refresh UI to show full duration RefreshStatus(); } + + public void Pause() + { + if (!_isPaused && CurrentState != MonitorState.Idle) + { + _isPaused = true; + IsPaused = true; + _pauseStartTime = DateTime.Now; + + // 如果正在休息,记录当前已过秒数 + if (CurrentState == MonitorState.Resting) + { + _restPauseStartSeconds = _restElapsedSeconds; + } + + StateChanged?.Invoke(this, EventArgs.Empty); + } + } + + public void Resume() + { + if (_isPaused) + { + _isPaused = false; + IsPaused = false; + + // 计算暂停时长 + TimeSpan pauseTime = DateTime.Now - _pauseStartTime; + + // 如果正在工作,将暂停时间累加到暂停总时长中 + // 这样工作时间就不会因为暂停而减少 + if (CurrentState == MonitorState.Working) + { + _pauseDuration += pauseTime; + } + // 如果正在休息,调整已过秒数,使剩余时间保持不变 + else if (CurrentState == MonitorState.Resting) + { + // 保持已过秒数不变,这样恢复后剩余时间不会变化 + // _restElapsedSeconds 保持不变 + } + + StateChanged?.Invoke(this, EventArgs.Empty); + RefreshStatus(); + } + } } } diff --git a/MainForm.Designer.cs b/MainForm.Designer.cs index de75682..772120a 100644 --- a/MainForm.Designer.cs +++ b/MainForm.Designer.cs @@ -41,6 +41,7 @@ namespace TimerApp this.btnStartStop = new System.Windows.Forms.Button(); this.btnReset = new System.Windows.Forms.Button(); + this.btnPause = new System.Windows.Forms.Button(); this.lblStatus = new System.Windows.Forms.Label(); this.lblTimeLeft = new System.Windows.Forms.Label(); this.notifyIcon1 = new System.Windows.Forms.NotifyIcon(this.components); @@ -169,6 +170,7 @@ namespace TimerApp // pnlSettings // this.pnlSettings.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(30)))), ((int)(((byte)(30)))), ((int)(((byte)(30))))); + this.pnlSettings.Controls.Add(this.btnPause); this.pnlSettings.Controls.Add(this.btnReset); this.pnlSettings.Controls.Add(this.btnStartStop); this.pnlSettings.Controls.Add(this.btnRestPlus); @@ -305,11 +307,11 @@ namespace TimerApp this.btnStartStop.FlatStyle = System.Windows.Forms.FlatStyle.Flat; this.btnStartStop.Font = new System.Drawing.Font("Microsoft YaHei UI", 9F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); this.btnStartStop.ForeColor = System.Drawing.Color.White; - this.btnStartStop.Location = new System.Drawing.Point(170, 110); + this.btnStartStop.Location = new System.Drawing.Point(210, 110); this.btnStartStop.Name = "btnStartStop"; - this.btnStartStop.Size = new System.Drawing.Size(110, 35); + this.btnStartStop.Size = new System.Drawing.Size(70, 35); this.btnStartStop.TabIndex = 4; - this.btnStartStop.Text = "应用设置"; + this.btnStartStop.Text = "应用"; this.btnStartStop.UseVisualStyleBackColor = false; this.btnStartStop.Click += new System.EventHandler(this.btnStartStop_Click); @@ -323,12 +325,28 @@ namespace TimerApp this.btnReset.ForeColor = System.Drawing.Color.White; this.btnReset.Location = new System.Drawing.Point(40, 110); this.btnReset.Name = "btnReset"; - this.btnReset.Size = new System.Drawing.Size(110, 35); + this.btnReset.Size = new System.Drawing.Size(70, 35); this.btnReset.TabIndex = 8; - this.btnReset.Text = "重置计时"; + this.btnReset.Text = "重置"; this.btnReset.UseVisualStyleBackColor = false; this.btnReset.Click += new System.EventHandler(this.btnReset_Click); + // + // btnPause + // + this.btnPause.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(63)))), ((int)(((byte)(63)))), ((int)(((byte)(70))))); + this.btnPause.FlatAppearance.BorderSize = 0; + this.btnPause.FlatStyle = System.Windows.Forms.FlatStyle.Flat; + this.btnPause.Font = new System.Drawing.Font("Microsoft YaHei UI", 9F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); + this.btnPause.ForeColor = System.Drawing.Color.White; + this.btnPause.Location = new System.Drawing.Point(125, 110); + this.btnPause.Name = "btnPause"; + this.btnPause.Size = new System.Drawing.Size(70, 35); + this.btnPause.TabIndex = 9; + this.btnPause.Text = "暂停"; + this.btnPause.UseVisualStyleBackColor = false; + this.btnPause.Click += new System.EventHandler(this.btnPause_Click); + // // btnHide // @@ -419,6 +437,7 @@ namespace TimerApp private System.Windows.Forms.Button btnRestPlus; private System.Windows.Forms.Button btnStartStop; private System.Windows.Forms.Button btnReset; + private System.Windows.Forms.Button btnPause; private System.Windows.Forms.Label lblStatus; private System.Windows.Forms.Label lblTimeLeft; private System.Windows.Forms.NotifyIcon notifyIcon1; diff --git a/MainForm.cs b/MainForm.cs index 37c1f86..34c159d 100644 --- a/MainForm.cs +++ b/MainForm.cs @@ -61,6 +61,7 @@ namespace TimerApp btnRestPlus.BackColor = panelColor; btnStartStop.BackColor = dark ? Color.FromArgb(63, 63, 70) : Color.White; btnReset.BackColor = dark ? Color.FromArgb(63, 63, 70) : Color.White; + btnPause.BackColor = dark ? Color.FromArgb(63, 63, 70) : Color.White; // 优化绘制,减少闪烁 this.SetStyle(ControlStyles.AllPaintingInWmPaint | @@ -256,6 +257,7 @@ namespace TimerApp // Update buttons UpdateButtonStyle(btnStartStop, dark); UpdateButtonStyle(btnReset, dark); + UpdateButtonStyle(btnPause, dark); UpdateButtonStyle(btnHide, dark); // Numeric buttons and text @@ -372,6 +374,20 @@ namespace TimerApp _monitor.Restart(); } + private void btnPause_Click(object sender, EventArgs e) + { + if (_monitor.IsPaused) + { + _monitor.Resume(); + btnPause.Text = "暂停"; + } + else + { + _monitor.Pause(); + btnPause.Text = "恢复"; + } + } + private void ApplySettings() { int workMin = 20; @@ -400,6 +416,18 @@ namespace TimerApp bool dark = _settings.IsDarkMode; + // 更新暂停按钮状态 + if (_monitor.CurrentState == MonitorState.Idle) + { + btnPause.Enabled = false; + btnPause.Text = "暂停"; + } + else + { + btnPause.Enabled = true; + btnPause.Text = _monitor.IsPaused ? "恢复" : "暂停"; + } + switch (_monitor.CurrentState) { case MonitorState.Idle: @@ -409,12 +437,12 @@ namespace TimerApp lblTimeLeft.ForeColor = Color.Gray; break; case MonitorState.Working: - lblStatus.Text = "状态: 工作中"; + lblStatus.Text = _monitor.IsPaused ? "状态: 工作中 (已暂停)" : "状态: 工作中"; lblStatus.ForeColor = dark ? Color.LightGreen : Color.Green; lblTimeLeft.ForeColor = dark ? Color.White : Color.Black; break; case MonitorState.Resting: - lblStatus.Text = "状态: 休息中"; + lblStatus.Text = _monitor.IsPaused ? "状态: 休息中 (已暂停)" : "状态: 休息中"; lblStatus.ForeColor = dark ? Color.LightSkyBlue : Color.Blue; lblTimeLeft.ForeColor = dark ? Color.LightSkyBlue : Color.Blue; break;