Feature: Configurable ΔE₀₀ Traffic-Light Thresholds #184

Closed
opened 2026-09-02 02:41:05 +01:00 by gronod · 1 comment
Owner

Description

Currently the live swatch grid in Stage 3 — Interactive Measurement hard-codes CIEDE2000 (ΔE₀₀) quality bands:

Band Condition CSS class Colour
Good ΔE₀₀ < 2 de-good Green
Warning ΔE₀₀ < 5 de-warning Amber
Bad ΔE₀₀ ≥ 5 de-bad Red

These fixed values are industry-common defaults but are not universally appropriate. Different media, instruments, customer SLAs, or quality standards (e.g. ISO 12647, GRACoL, FOGRA, internal print-house tolerances) require different acceptance thresholds.

This feature makes the two threshold values (good upper-bound and warning upper-bound) user-configurable via the existing Settings dialog, persists them, and applies them to all subsequent Stage 3 swatch rendering and statistics.


Motivation / User Value

  • Print-house operators and colour scientists can match ICCery’s visual quality indicators to their contractual or process-control limits.
  • Avoids false “bad” flags on high-gamut or noisy media where a slightly higher ΔE is still acceptable.
  • Allows tighter thresholds for critical proofing workflows.
  • Completes the Settings surface that already manages Argyll path, default instrument and log level.

Scope & Technical Requirements

1. Settings schema extension

Extend the persisted settings object (currently loaded/saved via load_settings / save_settings) with:

{
  "delta_e_good_max": 2.0,
  "delta_e_warning_max": 5.0
}
  • Both values are floating-point ≥ 0.
  • Invariant: delta_e_good_maxdelta_e_warning_max.
  • Defaults remain the current hard-coded values (2.0 / 5.0) so existing behaviour is unchanged for users who never open Settings.

2. Settings UI

Add a new section inside the existing Settings dialog (#settingsDialog), preferably under a heading such as “Measurement Quality Indicators” or “ΔE₀₀ Thresholds”:

  • Two numeric inputs (step 0.1, min 0):
    • “Good (green) when ΔE₀₀ < …”
    • “Warning (amber) when ΔE₀₀ < …”
  • Live validation: if the user enters a good value larger than the warning value, show an inline error and disable Save until corrected.
  • Optional “Reset to defaults (2.0 / 5.0)” link/button.
  • Short explanatory tooltip or help text: “These thresholds control the traffic-light colours on the Stage 3 live swatch grid and the average/max ΔE statistics.”

3. Runtime application

  • On Settings load / app start, expose the two values to the frontend (either via the existing settings object or a small dedicated getter).
  • swatch_grid.js must read the configured thresholds instead of the literals 2 and 5.
  • Classification logic becomes:
if (deltaE < goodMax) {
  patchEl.classList.add("de-good");
} else if (deltaE < warningMax) {
  patchEl.classList.add("de-warning");
} else {
  patchEl.classList.add("de-bad");
}
  • The same thresholds are used for any future aggregate statistics or summary badges that rely on the same bands.
  • Changing thresholds while a measurement session is in progress should either:
    • re-classify already-rendered patches immediately, or
    • apply only to newly completed rows (document the chosen behaviour in the UI).

4. Persistence & defaults

  • Values are stored in the same settings file / store already used for argyll_binary_dir, default_instrument and log_level.
  • On first run (or missing keys) the defaults 2.0 / 5.0 are written so the schema is always complete.
  • No migration of existing measurement artefacts is required; thresholds only affect live visualisation.

5. Out of scope (this feature)

  • Per-profile or per-preset threshold overrides (can be a later enhancement).
  • Changing the ΔE formula itself (stays CIEDE2000).
  • Exporting thresholds into the generated .ti3 / ICC metadata.
  • Colour-blind-safe alternative palettes (separate accessibility ticket).

Acceptance Criteria

  • Settings dialog contains two editable numeric fields for the good and warning ΔE₀₀ upper bounds, defaulting to 2.0 and 5.0.
  • Validation prevents saving when good-max > warning-max.
  • Saved values persist across application restarts.
  • Stage 3 swatch grid uses the configured thresholds for de-good / de-warning / de-bad classification and for the average/max statistics panel.
  • Existing behaviour is identical when the user has never changed the thresholds.
  • Tooltip / help text clearly explains the effect of the settings.
  • No regression in chartread state machine, JSON row parsing, or multi-pass averaging.

Implementation Notes

Frontend

  • src/js/settings.js — load / save the two new fields; add validation on the Save button path.
  • src/js/swatch_grid.js — replace hard-coded 2 / 5 with values obtained from settings (cache them at listener start or read once per row).
  • HTML of the Settings dialog — add the new form controls and any required labels/tooltips.
  • Optional: small CSS variable or data-attribute approach if the traffic-light colours themselves later become themeable.

Backend (Rust / Tauri)

  • Extend the settings struct (or equivalent) with the two f64 fields and their serde defaults.
  • Ensure load_settings / save_settings round-trip the new keys.

Testing suggestions

  • Unit-style: feed synthetic Lab pairs with known ΔE₀₀ and assert correct CSS classes for various threshold pairs.
  • Manual: set thresholds to 1.0 / 3.0, re-measure a strip, confirm visual bands move accordingly; restart app and confirm persistence.

Dependencies & Ordering

  • Depends on: Existing Settings dialog and persistence infrastructure (already present).
  • Blocks: None.
  • Suggested ordering: Can be implemented independently of other Stage 3 work; natural fit for a dedicated “Settings & Preferences” milestone or as a small follow-up to the current measurement polish.

References

  • Current hard-coded logic: src/js/swatch_grid.js (ΔE classification block).
  • Settings surface: src/js/settings.js + Settings dialog markup.
  • CIEDE2000 implementation: src/js/delta_e.js.
  • Industry context: ISO 12647, GRACoL, FOGRA tolerances frequently use ΔE₀₀ bands in the 1.5–5 range depending on process and substrate.
## Description Currently the live swatch grid in **Stage 3 — Interactive Measurement** hard-codes CIEDE2000 (ΔE₀₀) quality bands: | Band | Condition | CSS class | Colour | |-------------|-------------|---------------|--------| | Good | ΔE₀₀ < 2 | `de-good` | Green | | Warning | ΔE₀₀ < 5 | `de-warning` | Amber | | Bad | ΔE₀₀ ≥ 5 | `de-bad` | Red | These fixed values are industry-common defaults but are not universally appropriate. Different media, instruments, customer SLAs, or quality standards (e.g. ISO 12647, GRACoL, FOGRA, internal print-house tolerances) require different acceptance thresholds. This feature makes the two threshold values (good upper-bound and warning upper-bound) user-configurable via the existing Settings dialog, persists them, and applies them to all subsequent Stage 3 swatch rendering and statistics. --- ## Motivation / User Value - Print-house operators and colour scientists can match ICCery’s visual quality indicators to their contractual or process-control limits. - Avoids false “bad” flags on high-gamut or noisy media where a slightly higher ΔE is still acceptable. - Allows tighter thresholds for critical proofing workflows. - Completes the Settings surface that already manages Argyll path, default instrument and log level. --- ## Scope & Technical Requirements ### 1. Settings schema extension Extend the persisted settings object (currently loaded/saved via `load_settings` / `save_settings`) with: ```json { "delta_e_good_max": 2.0, "delta_e_warning_max": 5.0 } ``` - Both values are floating-point ≥ 0. - Invariant: `delta_e_good_max` ≤ `delta_e_warning_max`. - Defaults remain the current hard-coded values (2.0 / 5.0) so existing behaviour is unchanged for users who never open Settings. ### 2. Settings UI Add a new section inside the existing Settings dialog (`#settingsDialog`), preferably under a heading such as **“Measurement Quality Indicators”** or **“ΔE₀₀ Thresholds”**: - Two numeric inputs (step 0.1, min 0): - “Good (green) when ΔE₀₀ < …” - “Warning (amber) when ΔE₀₀ < …” - Live validation: if the user enters a good value larger than the warning value, show an inline error and disable Save until corrected. - Optional “Reset to defaults (2.0 / 5.0)” link/button. - Short explanatory tooltip or help text: “These thresholds control the traffic-light colours on the Stage 3 live swatch grid and the average/max ΔE statistics.” ### 3. Runtime application - On Settings load / app start, expose the two values to the frontend (either via the existing settings object or a small dedicated getter). - `swatch_grid.js` must read the configured thresholds instead of the literals `2` and `5`. - Classification logic becomes: ```js if (deltaE < goodMax) { patchEl.classList.add("de-good"); } else if (deltaE < warningMax) { patchEl.classList.add("de-warning"); } else { patchEl.classList.add("de-bad"); } ``` - The same thresholds are used for any future aggregate statistics or summary badges that rely on the same bands. - Changing thresholds while a measurement session is in progress should either: - re-classify already-rendered patches immediately, **or** - apply only to newly completed rows (document the chosen behaviour in the UI). ### 4. Persistence & defaults - Values are stored in the same settings file / store already used for `argyll_binary_dir`, `default_instrument` and `log_level`. - On first run (or missing keys) the defaults 2.0 / 5.0 are written so the schema is always complete. - No migration of existing measurement artefacts is required; thresholds only affect live visualisation. ### 5. Out of scope (this feature) - Per-profile or per-preset threshold overrides (can be a later enhancement). - Changing the ΔE formula itself (stays CIEDE2000). - Exporting thresholds into the generated `.ti3` / ICC metadata. - Colour-blind-safe alternative palettes (separate accessibility ticket). --- ## Acceptance Criteria - [ ] Settings dialog contains two editable numeric fields for the good and warning ΔE₀₀ upper bounds, defaulting to 2.0 and 5.0. - [ ] Validation prevents saving when good-max > warning-max. - [ ] Saved values persist across application restarts. - [ ] Stage 3 swatch grid uses the configured thresholds for `de-good` / `de-warning` / `de-bad` classification and for the average/max statistics panel. - [ ] Existing behaviour is identical when the user has never changed the thresholds. - [ ] Tooltip / help text clearly explains the effect of the settings. - [ ] No regression in chartread state machine, JSON row parsing, or multi-pass averaging. --- ## Implementation Notes **Frontend** - `src/js/settings.js` — load / save the two new fields; add validation on the Save button path. - `src/js/swatch_grid.js` — replace hard-coded `2` / `5` with values obtained from settings (cache them at listener start or read once per row). - HTML of the Settings dialog — add the new form controls and any required labels/tooltips. - Optional: small CSS variable or data-attribute approach if the traffic-light colours themselves later become themeable. **Backend (Rust / Tauri)** - Extend the settings struct (or equivalent) with the two `f64` fields and their serde defaults. - Ensure `load_settings` / `save_settings` round-trip the new keys. **Testing suggestions** - Unit-style: feed synthetic Lab pairs with known ΔE₀₀ and assert correct CSS classes for various threshold pairs. - Manual: set thresholds to 1.0 / 3.0, re-measure a strip, confirm visual bands move accordingly; restart app and confirm persistence. --- ## Dependencies & Ordering - **Depends on:** Existing Settings dialog and persistence infrastructure (already present). - **Blocks:** None. - **Suggested ordering:** Can be implemented independently of other Stage 3 work; natural fit for a dedicated “Settings & Preferences” milestone or as a small follow-up to the current measurement polish. --- ## References - Current hard-coded logic: `src/js/swatch_grid.js` (ΔE classification block). - Settings surface: `src/js/settings.js` + Settings dialog markup. - CIEDE2000 implementation: `src/js/delta_e.js`. - Industry context: ISO 12647, GRACoL, FOGRA tolerances frequently use ΔE₀₀ bands in the 1.5–5 range depending on process and substrate.
gronod added the Kind/Feature
Reviewed
Confirmed
1
Priority
Medium
3
labels 2026-09-02 02:41:05 +01:00
gronod added this to the Milestone 13 : Polish milestone 2026-09-03 22:55:36 +01:00
Author
Owner

Implemented in feat/184-configurable-delta-e (stacked on enh/178-swatch-grid):

  • Added delta_e_good_max and delta_e_warning_max to AppSettings in src-tauri/src/settings.rs with defaults 2.0 and 5.0.
  • Added a Stage 3 ΔE₀₀ threshold section to the Settings dialog.
  • Enforced the invariant good_max < warning_max on save.
  • Updated swatch_grid.js to load thresholds from settings and apply them to traffic-light classification.
  • Added live re-classification of rendered patches when settings change.

Closes #184.

Implemented in `feat/184-configurable-delta-e` (stacked on `enh/178-swatch-grid`): - Added `delta_e_good_max` and `delta_e_warning_max` to `AppSettings` in `src-tauri/src/settings.rs` with defaults `2.0` and `5.0`. - Added a Stage 3 ΔE₀₀ threshold section to the Settings dialog. - Enforced the invariant `good_max < warning_max` on save. - Updated `swatch_grid.js` to load thresholds from settings and apply them to traffic-light classification. - Added live re-classification of rendered patches when settings change. Closes #184.
Sign in to join this conversation.