mirror of
https://github.com/ajisaacs/OpenNest.git
synced 2026-10-27 02:41:06 -04:00
refactor(ui): consolidate MainForm busy guards
Moves every MainForm busy predicate into MainForm.Guards.cs, built on IsJobRunning, ViewsOf, IsPlateWorkBusy and IsNestFillBusy. Auto Nest, Validate and Post share TryBeginPlateCommand; Clamps, Automatic Cutoffs and Plan Cutting reuse the shared predicates. The deliberate variants (Expand Spacing ignores busy actions; the report guard adds database saves) keep their names and remain pinned by characterization tests. NavigationEnableCheck now takes the lockout flag instead of SetNestingLockout repeating its logic. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
1 parent
d87d113ceb
commit
e6b1e0308f
7 files changed
+102
-126
No files matched your search
@@ -413,16 +413,6 @@ namespace OpenNest.Forms
|
||||
ReportSuccess(destination);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// True while any operation could mutate nests or hold their plate views: whole-job
|
||||
/// nesting, an open progress window (a closed one can still await its commit), or a
|
||||
/// background database save serializing the live nest.
|
||||
/// </summary>
|
||||
private bool IsNestJobBusy() =>
|
||||
nestingInProgress
|
||||
|| Application.OpenForms.OfType<NestProgressForm>().Any()
|
||||
|| databaseSaveInProgress;
|
||||
|
||||
/// <summary>Returns the chosen path, or null on cancel. Overwrite consent is the dialog prompt.</summary>
|
||||
internal virtual string ShowReportSaveDialog(string suggestedFileName)
|
||||
{
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
using System.Linq;
|
||||
using System.Windows.Forms;
|
||||
using OpenNest.Actions;
|
||||
using OpenNest.Controls;
|
||||
|
||||
namespace OpenNest.Forms
|
||||
{
|
||||
public partial class MainForm
|
||||
{
|
||||
/// <summary>
|
||||
/// True while whole-job nesting runs or a progress window is open; a closed
|
||||
/// progress window can still have a fill awaiting its final commit.
|
||||
/// </summary>
|
||||
private bool IsJobRunning =>
|
||||
nestingInProgress || Application.OpenForms.OfType<NestProgressForm>().Any();
|
||||
|
||||
private PlateView[] ViewsOf(Nest nest) =>
|
||||
MdiChildren
|
||||
.OfType<EditNestForm>()
|
||||
.Where(form => ReferenceEquals(form.Nest, nest))
|
||||
.Select(form => form.PlateView)
|
||||
.ToArray();
|
||||
|
||||
/// <summary>
|
||||
/// The guard for plate commands: a running job, or any of <paramref name="views"/>
|
||||
/// filling or holding a busy current action.
|
||||
/// </summary>
|
||||
private bool IsPlateWorkBusy(PlateView[] views) =>
|
||||
IsJobRunning
|
||||
|| views.Any(v => v.IsFillInProgress || v.Actions.CurrentAction?.IsBusy() == true);
|
||||
|
||||
/// <summary>
|
||||
/// A running job or a fill on any view of <paramref name="nest"/>; a busy current
|
||||
/// action does not count.
|
||||
/// </summary>
|
||||
private bool IsNestFillBusy(Nest nest) =>
|
||||
IsJobRunning || ViewsOf(nest).Any(v => v.IsFillInProgress);
|
||||
|
||||
/// <summary>
|
||||
/// True while a nest run or fill may be reading <paramref name="nest"/>'s clamps.
|
||||
/// Clamps feed nesting and validation: never change them under a running operation.
|
||||
/// </summary>
|
||||
private bool ClampsInUse(Nest nest) => IsNestFillBusy(nest);
|
||||
|
||||
/// <summary>
|
||||
/// True while whole-job nesting or a fill on any view of the nest can still
|
||||
/// change its plates. Unlike the other plate commands' guard, a busy current
|
||||
/// action does not count: ActionSelect reports busy whenever parts are
|
||||
/// selected, and Expand Spacing needs a selection.
|
||||
/// </summary>
|
||||
internal bool IsExpandSpacingBusy(EditNestForm editForm) => IsNestFillBusy(editForm.Nest);
|
||||
|
||||
internal bool IsCuttingPlanBusy(PlateView[] views) => IsPlateWorkBusy(views);
|
||||
|
||||
/// <summary>
|
||||
/// True while any operation could mutate nests or hold their plate views: whole-job
|
||||
/// nesting, an open progress window (a closed one can still await its commit), or a
|
||||
/// background database save serializing the live nest.
|
||||
/// </summary>
|
||||
private bool IsNestJobBusy() => IsJobRunning || databaseSaveInProgress;
|
||||
|
||||
/// <summary>
|
||||
/// Refuses with <paramref name="message"/> while plate work on <paramref name="nest"/>
|
||||
/// is busy; otherwise returns every view of the nest to selection and returns true.
|
||||
/// </summary>
|
||||
private bool TryBeginPlateCommand(Nest nest, string message, string caption)
|
||||
{
|
||||
var views = ViewsOf(nest);
|
||||
if (IsPlateWorkBusy(views))
|
||||
{
|
||||
MessageBox.Show(this, message, caption, MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
return false;
|
||||
}
|
||||
|
||||
foreach (var view in views)
|
||||
view.SetAction(typeof(ActionSelect));
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -6,9 +6,7 @@ using System.Linq;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using System.Windows.Forms;
|
||||
using OpenNest.Actions;
|
||||
using OpenNest.Collections;
|
||||
using OpenNest.Controls;
|
||||
using OpenNest.Diagnostics;
|
||||
using OpenNest.Engine;
|
||||
using OpenNest.Engine.Fill;
|
||||
@@ -64,22 +62,6 @@ namespace OpenNest.Forms
|
||||
activeForm.ShowNestInfoEditor();
|
||||
}
|
||||
|
||||
private PlateView[] ViewsOf(Nest nest) =>
|
||||
MdiChildren
|
||||
.OfType<EditNestForm>()
|
||||
.Where(form => ReferenceEquals(form.Nest, nest))
|
||||
.Select(form => form.PlateView)
|
||||
.ToArray();
|
||||
|
||||
/// <summary>
|
||||
/// True while a nest run or fill may be reading <paramref name="nest"/>'s clamps.
|
||||
/// Clamps feed nesting and validation: never change them under a running operation.
|
||||
/// </summary>
|
||||
private bool ClampsInUse(Nest nest) =>
|
||||
nestingInProgress
|
||||
|| Application.OpenForms.OfType<NestProgressForm>().Any()
|
||||
|| ViewsOf(nest).Any(v => v.IsFillInProgress);
|
||||
|
||||
private void Clamps_Click(object sender, EventArgs e)
|
||||
{
|
||||
var editForm = activeForm;
|
||||
@@ -88,7 +70,7 @@ namespace OpenNest.Forms
|
||||
|
||||
var nest = editForm.Nest;
|
||||
var views = ViewsOf(nest);
|
||||
if (ClampsInUse(nest) || views.Any(v => v.Actions.CurrentAction?.IsBusy() == true))
|
||||
if (IsPlateWorkBusy(views))
|
||||
{
|
||||
MessageBox.Show(
|
||||
this,
|
||||
@@ -193,17 +175,9 @@ namespace OpenNest.Forms
|
||||
var target = activeForm;
|
||||
if (target == null || target.IsDisposed || target.PlateView.Plate == null)
|
||||
return;
|
||||
var views = MdiChildren.OfType<EditNestForm>()
|
||||
.Where(f => ReferenceEquals(f.Nest, target.Nest)).Select(f => f.PlateView).ToArray();
|
||||
if (nestingInProgress || Application.OpenForms.OfType<NestProgressForm>().Any()
|
||||
|| views.Any(v => v.IsFillInProgress || v.Actions.CurrentAction?.IsBusy() == true))
|
||||
{
|
||||
MessageBox.Show(this, "Finish or cancel the current plate operation before Auto Nest.",
|
||||
"Auto Nest", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
if (!TryBeginPlateCommand(target.Nest,
|
||||
"Finish or cancel the current plate operation before Auto Nest.", "Auto Nest"))
|
||||
return;
|
||||
}
|
||||
foreach (var view in views)
|
||||
view.SetAction(typeof(ActionSelect));
|
||||
|
||||
using var form = new AutoNestForm(target.Nest);
|
||||
if (target.Nest.PlateOptions.Count > 0)
|
||||
@@ -356,19 +330,10 @@ namespace OpenNest.Forms
|
||||
if (editForm == null)
|
||||
return;
|
||||
|
||||
var views = MdiChildren.OfType<EditNestForm>()
|
||||
.Where(form => ReferenceEquals(form.Nest, editForm.Nest))
|
||||
.Select(form => form.PlateView).ToArray();
|
||||
if (nestingInProgress || Application.OpenForms.OfType<NestProgressForm>().Any()
|
||||
|| views.Any(view => view.IsFillInProgress || view.Actions.CurrentAction?.IsBusy() == true))
|
||||
{
|
||||
MessageBox.Show(this, "Finish or cancel the current nesting or plate action before validating.",
|
||||
"Validate Nest", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
if (!TryBeginPlateCommand(editForm.Nest,
|
||||
"Finish or cancel the current nesting or plate action before validating.", "Validate Nest"))
|
||||
return;
|
||||
}
|
||||
|
||||
foreach (var view in views)
|
||||
view.SetAction(typeof(ActionSelect));
|
||||
editForm.OpenValidationInspection();
|
||||
}
|
||||
|
||||
@@ -389,19 +354,11 @@ namespace OpenNest.Forms
|
||||
"Verify Nest Before Posting", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
return;
|
||||
}
|
||||
var views = MdiChildren.OfType<EditNestForm>()
|
||||
.Where(form => ReferenceEquals(form.Nest, editForm.Nest))
|
||||
.Select(form => form.PlateView).ToArray();
|
||||
if (nestingInProgress || Application.OpenForms.OfType<NestProgressForm>().Any()
|
||||
|| views.Any(view => view.IsFillInProgress || view.Actions.CurrentAction?.IsBusy() == true))
|
||||
{
|
||||
MessageBox.Show(this, "Finish or cancel the current nesting or plate action before posting.",
|
||||
"Verify Nest Before Posting", MessageBoxButtons.OK, MessageBoxIcon.Information);
|
||||
if (!TryBeginPlateCommand(editForm.Nest,
|
||||
"Finish or cancel the current nesting or plate action before posting.",
|
||||
"Verify Nest Before Posting"))
|
||||
return;
|
||||
}
|
||||
|
||||
foreach (var view in views)
|
||||
view.SetAction(typeof(ActionSelect));
|
||||
var nest = editForm.Nest;
|
||||
|
||||
if (postProcessor is IPostProcessorNestAware nestAware)
|
||||
|
||||
@@ -2,7 +2,6 @@ using System;
|
||||
using System.Linq;
|
||||
using System.Windows.Forms;
|
||||
using OpenNest.Actions;
|
||||
using OpenNest.Controls;
|
||||
|
||||
namespace OpenNest.Forms
|
||||
{
|
||||
@@ -119,12 +118,8 @@ namespace OpenNest.Forms
|
||||
return;
|
||||
|
||||
var nest = editForm.Nest;
|
||||
var views = MdiChildren.OfType<EditNestForm>()
|
||||
.Where(form => ReferenceEquals(form.Nest, nest))
|
||||
.Select(form => form.PlateView).ToArray();
|
||||
// A closed progress window can still have a fill awaiting completion/commit.
|
||||
bool IsBusy() => nestingInProgress || Application.OpenForms.OfType<NestProgressForm>().Any()
|
||||
|| views.Any(v => v.IsFillInProgress || v.Actions.CurrentAction?.IsBusy() == true);
|
||||
var views = ViewsOf(nest);
|
||||
bool IsBusy() => IsPlateWorkBusy(views);
|
||||
if (IsBusy())
|
||||
{
|
||||
MessageBox.Show(this, "Finish or cancel the current nesting or plate action first.",
|
||||
@@ -157,10 +152,6 @@ namespace OpenNest.Forms
|
||||
|
||||
private void NestPlanCutting_Click(object sender, EventArgs e) => ShowCuttingPlan(allPlates: true);
|
||||
|
||||
internal bool IsCuttingPlanBusy(PlateView[] views) => nestingInProgress
|
||||
|| Application.OpenForms.OfType<NestProgressForm>().Any()
|
||||
|| views.Any(v => v.IsFillInProgress || v.Actions.CurrentAction?.IsBusy() == true);
|
||||
|
||||
// Native tests capture this notice without opening a modal dialog in session zero.
|
||||
internal System.Action<string, string> CuttingPlanNotice { get; set; }
|
||||
|
||||
@@ -181,10 +172,7 @@ namespace OpenNest.Forms
|
||||
return;
|
||||
|
||||
var nest = editForm.Nest;
|
||||
var views = MdiChildren.OfType<EditNestForm>()
|
||||
.Where(form => ReferenceEquals(form.Nest, nest))
|
||||
.Select(form => form.PlateView).ToArray();
|
||||
// A closed progress window can still have a fill awaiting completion/commit.
|
||||
var views = ViewsOf(nest);
|
||||
if (IsCuttingPlanBusy(views))
|
||||
{
|
||||
ShowCuttingPlanNotice("Finish or cancel the current nesting or plate action first.", "Plan Cutting");
|
||||
|
||||
@@ -37,49 +37,25 @@ namespace OpenNest.Forms
|
||||
toolStripMenuItem15.Visible = hasValue;
|
||||
}
|
||||
|
||||
private void NavigationEnableCheck()
|
||||
private void NavigationEnableCheck(bool locked = false)
|
||||
{
|
||||
if (activeForm == null)
|
||||
{
|
||||
mnuNestPreviousPlate.Enabled = false;
|
||||
mnuNestNextPlate.Enabled = false;
|
||||
mnuNestFirstPlate.Enabled = false;
|
||||
mnuNestLastPlate.Enabled = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
mnuNestPreviousPlate.Enabled = !activeForm.PlateManager.IsFirst;
|
||||
mnuNestNextPlate.Enabled = !activeForm.PlateManager.IsLast;
|
||||
mnuNestFirstPlate.Enabled =
|
||||
activeForm.PlateManager.Count > 0 && !activeForm.PlateManager.IsFirst;
|
||||
mnuNestLastPlate.Enabled =
|
||||
activeForm.PlateManager.Count > 0 && !activeForm.PlateManager.IsLast;
|
||||
}
|
||||
var plates = locked ? null : activeForm?.PlateManager;
|
||||
var hasPlates = plates != null && plates.Count > 0;
|
||||
|
||||
mnuNestPreviousPlate.Enabled = plates != null && !plates.IsFirst;
|
||||
mnuNestNextPlate.Enabled = plates != null && !plates.IsLast;
|
||||
mnuNestFirstPlate.Enabled = hasPlates && !plates.IsFirst;
|
||||
mnuNestLastPlate.Enabled = hasPlates && !plates.IsLast;
|
||||
}
|
||||
|
||||
private void SetNestingLockout(bool locked)
|
||||
{
|
||||
nestingInProgress = locked;
|
||||
|
||||
// Disable nesting-related menus while running
|
||||
// Disable nesting-related menus and plate navigation while running
|
||||
mnuNest.Enabled = !locked;
|
||||
mnuPlate.Enabled = !locked;
|
||||
|
||||
// Lock plate navigation
|
||||
mnuNestPreviousPlate.Enabled =
|
||||
!locked && activeForm != null && !activeForm.PlateManager.IsFirst;
|
||||
mnuNestNextPlate.Enabled =
|
||||
!locked && activeForm != null && !activeForm.PlateManager.IsLast;
|
||||
mnuNestFirstPlate.Enabled =
|
||||
!locked
|
||||
&& activeForm != null
|
||||
&& activeForm.PlateManager.Count > 0
|
||||
&& !activeForm.PlateManager.IsFirst;
|
||||
mnuNestLastPlate.Enabled =
|
||||
!locked
|
||||
&& activeForm != null
|
||||
&& activeForm.PlateManager.Count > 0
|
||||
&& !activeForm.PlateManager.IsLast;
|
||||
NavigationEnableCheck(locked);
|
||||
}
|
||||
|
||||
private void UpdateLocationStatus()
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Windows.Forms;
|
||||
using OpenNest.Actions;
|
||||
using OpenNest.Data;
|
||||
@@ -81,20 +80,6 @@ namespace OpenNest.Forms
|
||||
ShowExpandSpacingNotice("Select at least two parts on the plate to expand.");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// True while whole-job nesting or a fill on any view of the nest can still
|
||||
/// change its plates. Unlike the other plate commands' guard, a busy current
|
||||
/// action does not count: ActionSelect reports busy whenever parts are
|
||||
/// selected, and Expand Spacing needs a selection.
|
||||
/// </summary>
|
||||
internal bool IsExpandSpacingBusy(EditNestForm editForm) =>
|
||||
nestingInProgress
|
||||
|| Application.OpenForms.OfType<NestProgressForm>().Any()
|
||||
|| MdiChildren
|
||||
.OfType<EditNestForm>()
|
||||
.Where(form => ReferenceEquals(form.Nest, editForm.Nest))
|
||||
.Any(form => form.PlateView.IsFillInProgress);
|
||||
|
||||
// Native tests capture this notice without opening a modal dialog in session zero.
|
||||
internal System.Action<string> ExpandSpacingNotice { get; set; }
|
||||
|
||||
|
||||
@@ -44,7 +44,7 @@
|
||||
<DependentUpon>Settings.settings</DependentUpon>
|
||||
<DesignTimeSharedInput>True</DesignTimeSharedInput>
|
||||
</Compile>
|
||||
<Compile Update="Forms\MainForm.File.cs;Forms\MainForm.Nest.cs;Forms\MainForm.Plate.cs;Forms\MainForm.Status.cs;Forms\MainForm.Tools.cs;Forms\MainForm.View.cs">
|
||||
<Compile Update="Forms\MainForm.File.cs;Forms\MainForm.Guards.cs;Forms\MainForm.Nest.cs;Forms\MainForm.Plate.cs;Forms\MainForm.Status.cs;Forms\MainForm.Tools.cs;Forms\MainForm.View.cs">
|
||||
<DependentUpon>MainForm.cs</DependentUpon>
|
||||
<SubType>Code</SubType>
|
||||
</Compile>
|
||||
|
||||
Reference in new issue
Block a user