Dictionary containing constructor arguments for color guides.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Common.Collections.LazyLinkedList-1.html b/App/wwwroot/HiAPI-docsite/api/Hi.Common.Collections.LazyLinkedList-1.html
index e1f09965..07f888fa 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Common.Collections.LazyLinkedList-1.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Common.Collections.LazyLinkedList-1.html
@@ -308,6 +308,41 @@ or
+
+
+ ExhaustedLast
+
+
+
+
Forces full materialization of the lazy source and returns the last node.
+Walks the source to completion (no-op if already exhausted), then returns
+Last. Use when callers need the definitive tail at this point
+in time (e.g. as a stable predecessor before AppendSource(IEnumerable<T>)).
+
+
+
+
+
public LazyLinkedListNode<T> ExhaustedLast { get; }
Appends a new lazy source after the current source. The existing source's
+remaining items (if any) are drained first, then the new source is yielded.
+Re-opens the list for further on-demand materialization, so calling
+Next on the prior tail materializes the
+next item and links Previous across the
+boundary.
Compares the current instance with another object of the same type and returns an integer that indicates whether the current instance precedes, follows, or occurs in the same position in the sort order as the other object.
Interface for a character-level position within a file: file, line, and character index.
+All indices are 0-based.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Common.InternalException.html b/App/wwwroot/HiAPI-docsite/api/Hi.Common.InternalException.html
index 2d33b64c..0dffc6f2 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Common.InternalException.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Common.InternalException.html
@@ -194,9 +194,6 @@ Used to indicate programming errors or unexpected states that require developer
Serializes a JsonNode so that stem containers are indented
+but leaf containers (all children are primitive values) are written on a
+single compact line. Supports NaN / Infinity / -Infinity.
+
+
+
+
+
public static string ToLeafCompactJsonString(this JsonNode src, JsonSerializerOptions options = null)
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Common.LooseRunner.html b/App/wwwroot/HiAPI-docsite/api/Hi.Common.LooseRunner.html
index f9acb125..17273db4 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Common.LooseRunner.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Common.LooseRunner.html
@@ -187,8 +187,44 @@ Only the most recent action is executed and previous pending actions are discard
-
- LooseRunner(CancellationToken?)
+
+ LooseRunner(ILogger, CancellationToken?)
+
+
+
+
Initializes a new instance of the LooseRunner class with an ILogger for exception reporting.
+
+
+
+
+
public LooseRunner(ILogger logger, CancellationToken? cancellationToken = null)
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Common.ParallelBulkUtils.ParallelBulkReader-1.html b/App/wwwroot/HiAPI-docsite/api/Hi.Common.ParallelBulkUtils.ParallelBulkReader-1.html
index af1cf873..074e47ac 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Common.ParallelBulkUtils.ParallelBulkReader-1.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Common.ParallelBulkUtils.ParallelBulkReader-1.html
@@ -193,8 +193,8 @@ Manages reading data in parallel with forward and backward caching to optimize p
-
@@ -203,7 +203,7 @@ Manages reading data in parallel with forward and backward caching to optimize p
-
public ParallelBulkReader(int cacheBackwardDistance, int cacheForwardDistance, int cacheQueueLimit, ReadBulkDelegate<TData> readBulkFunc, Func<TData, int?> getIndexFunc, Func<int> countFunc)
+
public ParallelBulkReader(int cacheBackwardDistance, int cacheForwardDistance, int cacheQueueLimit, ReadBulkDelegate<TData> readBulkFunc, Func<TData, int?> getIndexFunc, Func<int> countFunc, Action<Exception> exceptionAction = null)
Parameters
@@ -225,6 +225,9 @@ Manages reading data in parallel with forward and backward caching to optimize p
Carries the API version read from a project file's XML attribute
+through the XFactory deserialization pipeline via the
+object[] res parameter.
+Consumers retrieve it with res?.OfType<ProjectApiVersion>().FirstOrDefault().
Generates an object of type T from a child element of the provided XML element.
+
Generates an object of type T from the first child element of the provided XML element.
This overload discards the relative file path output.
-
public static T GenByChild<T>(XElement src, string baseDirectory, GenMode genMode, params object[] res) where T : class
+
public static T GenByChild<T>(XElement src, string baseDirectory, IProgress<object> progress, bool enableRebase = true, object[] res = null) where T : class
The generated object of type T, or null if generation fails
-
+
Type Parameters
T
-
The type of object to generate
-
+
@@ -249,17 +245,17 @@ This overload discards the relative file path output.
-
- GenByChild<T>(XElement, string, out string, GenMode, params object[])
+
+ GenByChild<T>(XElement, string, out string, IProgress<object>, bool, object[])
-
Generates an object of type T from a child element of the provided XML element.
+
Generates an object of type T from the first child element of the provided XML element.
-
public static T GenByChild<T>(XElement src, string baseDirectory, out string relFile, GenMode genMode, params object[] res) where T : class
+
public static T GenByChild<T>(XElement src, string baseDirectory, out string relFile, IProgress<object> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
@@ -273,8 +269,11 @@ This overload discards the relative file path output.
@@ -316,7 +315,7 @@ This overload discards the relative file path output.
-
public static T GenByFile<T>(string baseDirectory, string relFile, GenMode genMode, params object[] res) where T : class
+
public static T GenByFile<T>(string baseDirectory, string relFile, IProgress<object> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
@@ -327,8 +326,11 @@ This overload discards the relative file path output.
@@ -555,7 +548,7 @@ This overload discards the relative file path output.
Returns
T
-
The generated object of type T, or null if generation fails
+
The generated object of type T
@@ -577,17 +570,17 @@ This overload discards the relative file path output.
-
- Gen<T>(XElement, string, out string, GenMode, params object[])
+
+ Gen<T>(XElement, string, out string, IProgress<object>, bool, object[])
-
Generates an object of type T from an XML element with specified generation mode.
+
Generates an object of type T from an XML element.
-
public static T Gen<T>(XElement src, string baseDirectory, out string relFile, GenMode mode, params object[] res) where T : class
+
public static T Gen<T>(XElement src, string baseDirectory, out string relFile, IProgress<object> progress, bool enableRebase = true, object[] res = null) where T : class
Parameters
@@ -601,8 +594,11 @@ This overload discards the relative file path output.
public static Dictionary<string, T> GetDictionaryByXmlSource<T>(this XElement src, string baseDirectory, GenMode genMode) where T : class
+
public static Dictionary<string, T> GetDictionaryByXmlSource<T>(this XElement src, string baseDirectory, IProgress<object> progress, bool enableRebase = true) where T : class
Carries the API version read from a project file's XML attribute
+through the XFactory deserialization pipeline via the
+object[] res parameter.
+Consumers retrieve it with res?.OfType<ProjectApiVersion>().FirstOrDefault().
Enumeration of generation modes for XML factory operations.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Common.html b/App/wwwroot/HiAPI-docsite/api/Hi.Common.html
index a35d39ea..55c531cd 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Common.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Common.html
@@ -135,11 +135,6 @@ If the execution time is over the
Block the thread to the given delay from the previous block.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.CutterLocations.ClStrips.ClStrip.html b/App/wwwroot/HiAPI-docsite/api/Hi.CutterLocations.ClStrips.ClStrip.html
index a15e76a8..a8a77510 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.CutterLocations.ClStrips.ClStrip.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.CutterLocations.ClStrips.ClStrip.html
@@ -231,6 +231,37 @@ This class manages the display and interaction of cutter location points and lin
+
+ InternalMachiningStepSelected
+
+
+
+
Host wiring hook invoked when a strip position selects a machining step (low-level; prefer MachiningStepSelected for UI).
+
+
+
+
+
public Action<MachiningStep> InternalMachiningStepSelected
Optional progress reporter for the XML parsing chain
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Geom.StlFile.html b/App/wwwroot/HiAPI-docsite/api/Hi.Geom.StlFile.html
index 03fe5661..8935864e 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Geom.StlFile.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Geom.StlFile.html
@@ -307,8 +307,8 @@ If base directory is provided, the STL will be loaded immediately.
-
- StlFile(XElement, string)
+
+ StlFile(XElement, string, IProgress<object>)
@@ -317,7 +317,7 @@ If base directory is provided, the STL will be loaded immediately.
-
public StlFile(XElement src, string baseDirectory)
+
public StlFile(XElement src, string baseDirectory, IProgress<object> progress)
Parameters
@@ -328,6 +328,8 @@ If base directory is provided, the STL will be loaded immediately.
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Geom.TransformationGeom.html b/App/wwwroot/HiAPI-docsite/api/Hi.Geom.TransformationGeom.html
index f09f5308..066f5642 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Geom.TransformationGeom.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Geom.TransformationGeom.html
@@ -268,8 +268,8 @@ This class combines a transformer with a target geometry to produce transformed
-
+
@@ -298,7 +300,7 @@ This class combines a transformer with a target geometry to produce transformed
-
Remarks
+
Remarks
This constructor deserializes both the transformer and geometry data from the provided XML.
If either element is missing or invalid, the corresponding property will be null.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.HiNcKits.HiNcHost.html b/App/wwwroot/HiAPI-docsite/api/Hi.HiNcKits.HiNcHost.html
index d186103d..ca82e376 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.HiNcKits.HiNcHost.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.HiNcKits.HiNcHost.html
@@ -187,8 +187,8 @@ Host class for HiNC functionality that provides project management, path resolut
-
- HiNcHost(ProxyProjectService)
+
+ HiNcHost(ProxyProjectService, ILogger)
@@ -197,7 +197,7 @@ Host class for HiNC functionality that provides project management, path resolut
-
public HiNcHost(ProxyProjectService proxyProjectService)
+
public HiNcHost(ProxyProjectService proxyProjectService, ILogger logger = null)
Parameters
@@ -205,41 +205,8 @@ Host class for HiNC functionality that provides project management, path resolut
Per-user visibility flags for the Player page's divisions (charts and
+info panels). Mirrors the HiNcRcl PlayerDivConfig + PlayerDivFlag
+pair, flattened into a single all-boolean config so the webservice
+(which has no HiNcHost / HiNcUser) can persist the whole
+layout through UserConfig alone.
Defaults are tuned for a first-time user: the two info panels
+(EnableStepDiv and MessageTable) are ON
+so the Player page looks populated without having to open the
+Division Visibility dropdown; every chart toggle starts OFF.
+
+
+
+
Constructors
+
+
+
+
+
+
+ PlayerDivConfig()
+
+
+
+
Default constructor.
+
+
+
+
+
public PlayerDivConfig()
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ PlayerDivConfig(XElement)
+
+
+
+
Initializes a new instance of the PlayerDivConfig class from XML data.
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.HiNcKits.UserConfig.html b/App/wwwroot/HiAPI-docsite/api/Hi.HiNcKits.UserConfig.html
index da0ca928..1237a896 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.HiNcKits.UserConfig.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.HiNcKits.UserConfig.html
@@ -509,6 +509,40 @@ Not used yet.
+
+
+
+ PlayerDivConfig
+
+
+
+
Per-user visibility flags for the Player page's divisions (charts and info panels).
+Used by the webservice Division Visibility dropdown; persisted alongside the rest of
+this UserConfig so the layout survives a page refresh.
+
+
+
+
+
public PlayerDivConfig PlayerDivConfig { get; set; }
Per-user visibility flags for the Player page's divisions (charts and
+info panels). Mirrors the HiNcRcl PlayerDivConfig + PlayerDivFlag
+pair, flattened into a single all-boolean config so the webservice
+(which has no HiNcHost / HiNcUser) can persist the whole
+layout through UserConfig alone.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Licenses.License.html b/App/wwwroot/HiAPI-docsite/api/Hi.Licenses.License.html
index 1c96afc7..589e4f4a 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Licenses.License.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Licenses.License.html
@@ -496,8 +496,8 @@ Class License
-
- AbortEventHandler
+
+ AbortMessageAction
@@ -506,7 +506,7 @@ Class License
-
public static event EventHandler<string> AbortEventHandler
+
public static event Action<string> AbortMessageAction
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Machining.FreeformRemover.html b/App/wwwroot/HiAPI-docsite/api/Hi.Machining.FreeformRemover.html
index 7e6190c7..45023d43 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Machining.FreeformRemover.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Machining.FreeformRemover.html
@@ -266,8 +266,8 @@ and topology bricks for both the noble and shaper parts.
-
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Machining.MachiningEquipmentUtils.MachiningEquipmentCollisionIndex.html b/App/wwwroot/HiAPI-docsite/api/Hi.Machining.MachiningEquipmentUtils.MachiningEquipmentCollisionIndex.html
index f897cc77..a92d124d 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Machining.MachiningEquipmentUtils.MachiningEquipmentCollisionIndex.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Machining.MachiningEquipmentUtils.MachiningEquipmentCollisionIndex.html
@@ -434,6 +434,38 @@ When set, updates the component anchor and collidable based on the equipment's s
+
+
+
+ WorkpieceRuntimeGeomGetter
+
+
+
+
Getter for runtime geometry of the workpiece. Set by the service layer.
+
+
+
+
+
public Func<CubeTree> WorkpieceRuntimeGeomGetter { get; set; }
@@ -1784,6 +1888,45 @@ Clear the state from previous session (if existed).
+
+
+
+ PowerReset()
+
+
+
+
Performs a controller power reset, modelling a power-off / power-on cycle:
+
Every IPowerResettable dependency clears its volatile
+ subset. Persistent dependency state (controller parameters,
+ Fanuc #500-#999, etc.) is left intact.
+Without the second step, calling PowerReset while a project is
+loaded would leave volatile commons alive across the supposed power
+cycle (they live in the SyntaxPiece JSON dataflow rather than in any
+IPowerResettable dependency).
+
+
+
+
+
public void PowerReset()
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -2074,6 +2217,33 @@ Clear the state from previous session (if existed).
+
+
+
+ RunToLineEnd()
+
+
+
+
Advances the player by one NC/CSV line and pauses.
+
+
+
+
+
public void RunToLineEnd()
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -2398,17 +2568,17 @@ The previous step is null if no previous step exists.
-
- OnRanNcBlock
+
+ OnNcFileRan
-
Event triggered after an NC block is executed.
+
Event triggered after an NC file is executed.
-
public event Action OnRanNcBlock
+
public event Action OnNcFileRan
@@ -2429,6 +2599,68 @@ The previous step is null if no previous step exists.
+
+ OnSourcedActEntry
+
+
+
+
App-lifetime event triggered for each SourcedActEntry produced during NC/CSV execution.
+
+
+
+
+
public event Action<SourcedActEntry> OnSourcedActEntry
Represents a machining session that manages the execution and optimization of machining operations.
Provides functionality for controlling the machining process, handling optimization options,
-and managing session state.
Per-line scripts injected externally (without modifying NC files).
+Key: FileLineIndex of the NC block.
+Value: C# script text to execute after the NC block.
+Consumed by CsScriptEndSemantic.
+
+
+
+
+
public Dictionary<FileLineIndex, string> PostBlockScripts { get; }
Per-line scripts injected externally (without modifying NC files).
+Key: FileLineIndex of the NC block.
+Value: C# script text to execute before the NC block.
+Consumed by CsScriptBeginSemantic.
+
+
+
+
+
public Dictionary<FileLineIndex, string> PreBlockScripts { get; }
StreamWriters registered during the session (e.g. by diagnostic output methods).
+Key: relative output file path. Disposed automatically when the session ends.
+
+
+
+
+
public Dictionary<string, StreamWriter> SessionWriters { get; }
+Idempotent and reusable: after Reset() the object is in
+the same lazy-uninitialised state as a freshly constructed instance,
+so the first subsequent RunControlLines hits the
+!IsInitialized branch and re-creates everything.
+
Performs a controller power reset: every IPowerResettable dependency
+in the active NcDependencyList clears its volatile subset (e.g. Fanuc
+common volatile macro variables #100-#499). Persistent state is left intact.
@@ -3820,6 +3988,42 @@ public bool? ScanRuntimeGeomInfDefect()
+
+
+
+ SetAllSnapshotSyntaxEnabled(bool)
+
+
+
+
Sets IsEnabled on every SnapshotSyntax reachable from the
+active SoftNcRunner's NcSyntaxList (top-level slots
+and inside BundleSyntax). No-op when SoftNcRunner
+is not the active runner.
+
+
+
+
+
[JsAce(DocContentHtml = "Enable or disable every SnapshotSyntax in the active SoftNcRunner pipeline at once.")]
+public void SetAllSnapshotSyntaxEnabled(bool isEnabled)
[JsAce(Snippet = "MachiningStepBuilt+=($1preStep,$2curStep)=>{$3Command};", DocContentHtml = "Runtime Step Configuration action. preStep is the Previous Milling Step; curStep is the Current Milling Step. preStep is null if no previous step existed.")]
+
[Obsolete("Use SessionStepBuilt instead.")]
public event MachiningActRunner.MachiningStepBuiltDelegate MachiningStepBuilt
@@ -4360,13 +4565,13 @@ public event MachiningActRunner.MachiningStepBuiltDelegate MachiningStepBuilt
-
Event that is triggered when a milling step is selected.
-The event will be cleared by the calling of ResetRuntime().
[JsAce(Snippet = "SessionSourcedActEntry+=($1entry)=>{$2Command};", DocContentHtml = "Session-scoped event triggered for each SourcedActEntry. entry.SentenceSource is the source sentence; entry.Act is the associated act (may be null).")]
+public event Action<SourcedActEntry> SessionSourcedActEntry
[JsAce(Snippet = "SessionStepBuilt+=($1preStep,$2curStep)=>{$3Command};", DocContentHtml = "Session-scoped step built event. preStep is the Previous Milling Step; curStep is the Current Milling Step. preStep is null if no previous step existed.")]
+public event MachiningActRunner.MachiningStepBuiltDelegate SessionStepBuilt
[JsAce(Snippet = "SessionSyntaxPieceRan+=($1syntaxPiece)=>{$2Command};", DocContentHtml = "Session-scoped event triggered after each SyntaxPiece is executed. syntaxPiece may be null if the source command is not a SyntaxPiece.")]
+public event Action<SyntaxPiece> SessionSyntaxPieceRan
Creates a SpindleSpeedCache from spindle capability and machine motion step.
+Returns preSpindleSpeedCache if the spindle speed is unchanged
+or the capability data is incomplete.
Represents a machining session that manages the execution and optimization of machining operations.
Provides functionality for controlling the machining process, handling optimization options,
-and managing session state.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.MachiningSteps.MachineMotionStep.html b/App/wwwroot/HiAPI-docsite/api/Hi.MachiningSteps.MachineMotionStep.html
index a70c4abe..28427d9f 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.MachiningSteps.MachineMotionStep.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.MachiningSteps.MachineMotionStep.html
@@ -218,8 +218,8 @@ Note that the spindle information is only for milling behavior.
-
Shared CSV column tags and physics-related column prefixes for mapping simulator or
+logged controller data onto MachiningStep rows.
+
@@ -314,7 +316,8 @@ The actual time basically obtained by the external data from controller.
-
+
CSV column prefix for holder moment / torque channels.
+
@@ -593,7 +596,8 @@ The time generally obtained by the simulated data.
-
+
CSV column prefix for tool-side force components (e.g. dynamometer).
+
@@ -654,7 +658,8 @@ The time generally obtained by the simulated data.
-
+
CSV column prefix for workpiece-side force components.
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Mapping.html b/App/wwwroot/HiAPI-docsite/api/Hi.Mapping.html
index 2a817a3a..ef6105fb 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Mapping.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Mapping.html
@@ -107,7 +107,9 @@ This class manages the loading and caching of time shot data from measurement fi
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Milling.Cutters.CustomSpinningProfile.html b/App/wwwroot/HiAPI-docsite/api/Hi.Milling.Cutters.CustomSpinningProfile.html
index 279dbf5c..31a6b506 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Milling.Cutters.CustomSpinningProfile.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.Milling.Cutters.CustomSpinningProfile.html
@@ -237,8 +237,8 @@ This profile allows for custom geometry to be used as the cutter profile.
-
WorkpieceService handles runtime geometry, caching, diff calculation,
+defect scanning, display and collision — state that does not require configuration IO.
+Compare to Workpiece, which holds the persistent/serializable configuration.
+
+
+
+
Constructors
+
+
+
+
+
+
+ WorkpieceService(Func<Workpiece>)
+
+
+
+
Ctor.
+
+
+
+
+
public WorkpieceService(Func<Workpiece> workpieceGetter)
Progress reporter for loading XyzabcChain and related children.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcOpt.NcOptProc.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcOpt.NcOptProc.html
index a41ac6b2..7f0d8aa0 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcOpt.NcOptProc.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcOpt.NcOptProc.html
@@ -455,7 +455,7 @@ Since the folder can be moving with the configuration file.
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
ParamAxisType
@@ -392,6 +540,72 @@ following real Fanuc parameter numbering.
+
+ ParamG54OffsetBase
+
+
+
+
#5221: Base address (X) of G54 work coordinate offset.
+G54.Y at +1 (#5222), G54.Z at +2 (#5223). G55..G59 follow at stride 20.
+See IsoCoordinateAddressMap.
Routes Fanuc system-variable reads to SystemParams:
+#5221-#5328 (G54-G59 work coordinate offsets) and
+#7001-#7999 (G54.1 P1-P48 extended offsets) are returned
+directly by parameter address. Other ranges return null so
+the evaluator's lookup chain can fall through.
+
+
+
+
+
+
+
+
+ GetCoordinateOffset(string)
+
+
+
+
Gets the offset for the given G-code coordinate id.
+Returns null when no offset is configured for that id by this provider
+(callers iterate the next provider, or fall back to Zero).
#5041-#5043Current absolute position X/Y/Z → previous block's ProgramXyz.
+
+Stateless. Configured on
+VariableEvaluatorSyntax.RuntimeVariableLookups rather than
+NcDependencyList because the read needs the block node for
+Previous access — there is no
+long-lived dependency object that owns this data.
+
+
+
+
+
+
public sealed class FanucPositionVariableLookup : IRuntimeVariableLookup
Returns the value of the variable identified by key
+in the context of node and
+dependencies, or null if the key is outside
+this lookup's range or the value is vacant.
+
+
+
+
+
public double? Get(string key, LazyLinkedListNode<SyntaxPiece> node, IReadOnlyList<INcDependency> dependencies)
Fanuc-side adapter that exposes a wrapped ToolOffsetTable
+as an IVariableLookup following Fanuc Memory C tool offset
+addressing: #2001+N → effective height of offset N
+(geometry − wear).
+
+The underlying ToolOffsetTable stays brand-neutral —
+Heidenhain / Siemens can use the same storage with different addressing
+by registering their own adapter alongside the table. Holds a reference
+to the table rather than owning data so writes through the table show
+up immediately in lookups via this adapter.
+
+
+
+
+
+
public class FanucToolOffsetVariableLookup : INcDependency, IMakeXmlSource, IVariableLookup
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Fanuc-style ISO controller common variable table for the retained range
+#500-#999. These variables survive a power cycle (in real hardware
+they live in NV-RAM) and are serialised into the project file.
+
+Excluded by design:
+
Local #1-#33Call-frame scoped (Fanuc local variables); lives in the SyntaxPiece JSON dataflow, not here.
Non-retained common #100-#499Cleared by program-end / power reset; lives in the SyntaxPiece JSON dataflow as well, not in this table.
System #1000+Read-only or computed from runtime state; resolved by dedicated reading syntaxes against other dependencies (e.g. FanucParameterTable, tool offset / WCS tables).
+
+
+Vacant (Fanuc <vacant>) is represented by null: either the dictionary
+has no entry for the key, or the entry maps to null. Both are treated identically by GetVariable(int).
+
+
+Naming rationale: Fanuc official documentation calls #500-#999 "retained common variables"
+(and #100-#499 "non-retained common variables"). The umbrella term "macro variable" was
+avoided because it conflicts with Custom Macro B's call-frame concept (G65/G66 push a frame
+containing the local #1-#33); using RetainedCommonVariableTable reserves "macro"
+for the call-frame topic.
+
+
+
+
+
+
public class RetainedCommonVariableTable : INcDependency, IMakeXmlSource, IVariableLookup
Backing store. Key = variable number (e.g. 500). Value null = vacant.
+A missing key is also treated as vacant. Keys are constrained to
+RetainedCommonMin..RetainedCommonMax; out-of-range writes are silently ignored.
+
+
+
+
+
public Dictionary<int, double?> Variables { get; set; }
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Fanuc controller parameter table.
Stores system parameters (single value) and axis parameters (per-axis value)
following real Fanuc parameter numbering.
#5041-#5043Current absolute position X/Y/Z → previous block's ProgramXyz.
+
+Stateless. Configured on
+VariableEvaluatorSyntax.RuntimeVariableLookups rather than
+NcDependencyList because the read needs the block node for
+Previous access — there is no
+long-lived dependency object that owns this data.
+
Fanuc-side adapter that exposes a wrapped ToolOffsetTable
+as an IVariableLookup following Fanuc Memory C tool offset
+addressing: #2001+N → effective height of offset N
+(geometry − wear).
+
+The underlying ToolOffsetTable stays brand-neutral —
+Heidenhain / Siemens can use the same storage with different addressing
+by registering their own adapter alongside the table. Holds a reference
+to the table rather than owning data so writes through the table show
+up immediately in lookups via this adapter.
+
Fanuc-style ISO controller common variable table for the retained range
+#500-#999. These variables survive a power cycle (in real hardware
+they live in NV-RAM) and are serialised into the project file.
+
+Excluded by design:
+
Local #1-#33Call-frame scoped (Fanuc local variables); lives in the SyntaxPiece JSON dataflow, not here.
Non-retained common #100-#499Cleared by program-end / power reset; lives in the SyntaxPiece JSON dataflow as well, not in this table.
System #1000+Read-only or computed from runtime state; resolved by dedicated reading syntaxes against other dependencies (e.g. FanucParameterTable, tool offset / WCS tables).
+
+
+Vacant (Fanuc <vacant>) is represented by null: either the dictionary
+has no entry for the key, or the entry maps to null. Both are treated identically by GetVariable(int).
+
+
+Naming rationale: Fanuc official documentation calls #500-#999 "retained common variables"
+(and #100-#499 "non-retained common variables"). The umbrella term "macro variable" was
+avoided because it conflicts with Custom Macro B's call-frame concept (G65/G66 push a frame
+containing the local #1-#33); using RetainedCommonVariableTable reserves "macro"
+for the call-frame topic.
+
Default IBlockSkipConfig. Mirrors the typical Fanuc
+factory default: layer 1 (bare / prefix) is ON, other layers
+are OFF. Each layer can be toggled individually.
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
+
+
+
+
+
+
+
+
+ SetLayerEnabled(int, bool)
+
+
+
+
Enables / disables a specific skip layer.
+
+
+
+
+
public void SetLayerEnabled(int layer, bool enabled)
Coordinate table for NC controller.
The dictionary key is a G-code coordinate name (e.g. “G54”, “G59.2”);
the dictionary value is machine coordinate offset.
+
+Brand-agnostic standalone implementation of IIsoCoordinateConfig.
+Brand parameter tables (Fanuc, Syntec, Siemens, Heidenhain) provide
+hardware-faithful alternatives that map to real controller parameters.
+
Gets the offset for the given G-code coordinate id.
+Returns null when no offset is configured for that id by this provider
+(callers iterate the next provider, or fall back to Zero).
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.NcKinematicsDependency.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.NcKinematicsDependency.html
index 5f5fa275..f7deb4f7 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.NcKinematicsDependency.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.NcKinematicsDependency.html
@@ -542,6 +542,56 @@ the solution only fit the orientation part of the tiltMat
+
+
+
+ OrientationToMcAbc(Vec3d, out Vec3d)
+
+
+
+
Converts a target tool axial direction (endpoint orientation) to machine ABC coordinates.
+Only the axial alignment is constrained; rotation about the tool axis is free.
+
+Use this in place of OrientationToMcAbc(Mat4d, out Vec3d) when the
+rotation about the tool axis is irrelevant (e.g. G53.1 rotary positioning). The
+axial-only solve avoids the redundant 6-target full-matrix constraint and is more
+likely to converge for tilt configurations such as G68.2 I180 J90 K0.
+
+
+
+
+
+
public bool OrientationToMcAbc(Vec3d toolAxialNormal, out Vec3d mcAbc_rad)
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.ToolingMcConfig.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.ToolingMcConfig.html
index eb6a0cea..10df1a79 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.ToolingMcConfig.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.ToolingMcConfig.html
@@ -314,6 +314,39 @@ Each axis value: a position to move to, or
+
+
+ ToolingTime
+
+
+
+
Duration of the tool changer mechanism (arm swap, magazine rotation, etc.).
+Does not include axis motion time to/from the tooling position.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.html
index 8c08ee76..92ac0aa2 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.Generic.html
@@ -111,6 +111,20 @@ This class serves as a safety net for brands that do not define
certain parameters (e.g., Siemens/Heidenhain have no system
parameter for G83 peck retraction — it is per-call).
+
+
+
Default IBlockSkipConfig. Mirrors the typical Fanuc
+factory default: layer 1 (bare / prefix) is ON, other layers
+are OFF. Each layer can be toggled individually.
+When EnabledLayers is absent the default is layer 1 only.
+
@@ -118,6 +132,11 @@ parameter for G83 peck retraction — it is per-call).
Coordinate table for NC controller.
The dictionary key is a G-code coordinate name (e.g. “G54”, “G59.2”);
the dictionary value is machine coordinate offset.
+
+Brand-agnostic standalone implementation of IIsoCoordinateConfig.
+Brand parameter tables (Fanuc, Syntec, Siemens, Heidenhain) provide
+hardware-faithful alternatives that map to real controller parameters.
+
public class HeidenhainParameterTable : ControllerParameterTableBase, IHomeMcConfig, IMachineAxisConfig, IRapidFeedrateConfig, INcDependency, IMakeXmlSource
+
public class HeidenhainParameterTable : ControllerParameterTableBase, IHomeMcConfig, IMachineAxisConfig, IRapidFeedrateConfig, IStrokeLimitConfig, INcDependency, IMakeXmlSource
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.HeidenhainDatumTable.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.HeidenhainDatumTable.html
index b2b911d7..4ff2854c 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.HeidenhainDatumTable.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Dependencys.HeidenhainDatumTable.html
@@ -6,7 +6,7 @@
-
+
@@ -101,11 +101,23 @@ Class HeidenhainDatumTable
CYCL DEF 247 Q339=N reads from DatumPresetTable,
CYCL DEF 7 #N reads from DatumShiftTable.
Each table maps an integer ID (1–20) to a Vec3d offset.
+
+On real Heidenhain controllers, preset and datum tables are separate
+disk files (e.g. TNC:\table\preset.pr, *.d) — distinct
+from MP-prefixed Machine Parameters (held by
+HeidenhainParameterTable). HiNC mirrors that separation
+by keeping this dependency independent of HeidenhainParameterTable.
+
+
+Implements IIsoCoordinateConfig by mapping the ISO/DIN
+G54–G59 codes to preset rows 1–6, the conventional Heidenhain
+compatibility mapping for ISO/DIN programs running on a Heidenhain.
+
-
public class HeidenhainDatumTable : INcDependency, IMakeXmlSource
+
public class HeidenhainDatumTable : IIsoCoordinateConfig, INcDependency, IMakeXmlSource
@@ -122,6 +134,7 @@ Each table maps an integer ID (1–20) to a Vec3d offset.
@@ -346,6 +391,45 @@ Each table maps an integer ID (1–20) to a Vec3d offset.
+
+
+
+ GetCoordinateOffset(string)
+
+
+
+
Gets the offset for the given G-code coordinate id.
+Returns null when no offset is configured for that id by this provider
+(callers iterate the next provider, or fall back to Zero).
Runtime state of the controller's Block Delete / Block Skip switches.
+Present in NcDependencyList exposes this to
+the runner so that blocks whose head carries / or /N
+(parsed by BlockSkipSyntax into
+BlockSkip) are skipped at semantic time.
+
+Layers are 1..9; Layer 1 corresponds to the bare / prefix.
+Controllers (Fanuc / Syntec / Mazak / Siemens) let each layer be
+toggled independently via panel switches or system parameters.
+
+
+When this dependency is absent from
+NcDependencyList, no block is skipped
+(safest default: simulate the full machining). The syntax still
+consumes the / prefix so no UnparsedText--Remaining
+diagnostic is produced.
+
+
+
+
+
+
public interface IBlockSkipConfig : INcDependency, IMakeXmlSource
Gets the offset for the given G-code coordinate id.
+Returns null when no offset is configured for that id by this provider
+(callers iterate the next provider, or fall back to Zero).
Marks an INcDependency that holds volatile state which must be cleared
+when the controller performs a power reset (power off then on).
+
+Implementers should clear only the volatile subset they own (e.g. Fanuc common volatile
+macro variables #100-#499), and leave persistent state untouched
+(e.g. #500-#999, controller parameters).
+
+
+Call-frame local state (Fanuc #1-#33, Heidenhain Q200-Q1199) is NOT in scope —
+that lives in the SyntaxPiece JSON dataflow and is bounded by call activation, not power cycle.
+
+
+
+
+
+
public interface IPowerResettable : INcDependency, IMakeXmlSource
Per-axis stroke (travel) limits.
+Unit is mm for linear axes, deg for rotary axes.
+Implemented by ControllerParameterTableBase using
+brand-specific parameter numbers (e.g., Fanuc #1300/#1320,
+Siemens MD36100/MD36110, Heidenhain MP420/MP430).
+
+
+
+
+
public interface IStrokeLimitConfig : INcDependency, IMakeXmlSource
Fanuc-style ISO coordinate parameter address mapping.
+G54–G59 → #5221+ (stride 20, three consecutive numbers per entry for X/Y/Z),
+G54.1 P1–P48 → #7001+ (stride 20).
+Shared between FanucParameterTable (which calls these
+“ParamId”) and SyntecParameterTable (which calls them
+“PrId”) because both follow the same numeric scheme.
Reads X/Y/Z from systemParams at consecutive addresses
+starting at baseAddr. Returns null when none of the
+three addresses are present (i.e. the entry is unmanaged).
+
+
+
+
+
public static Vec3d Read(IDictionary<int, double> systemParams, int baseAddr)
Seeds all G54–G59 and G54.1 P1–P48 entries with zero.
+Total 162 SystemParams entries (6×3 + 48×3). Used by brand
+parameter tables to satisfy the “managed parameter must have default”
+invariant — real Fanuc on a fresh-battery controller also reads 0
+for these addresses, so the model matches hardware.
+
+
+
+
+
public static void SeedAllDefaults(IDictionary<int, double> systemParams)
Resolves a coordinate id to its 3-axis base address (X address; Y at +1, Z at +2),
+or null if the id is outside the Fanuc-mapped set (G54–G59, G54.1P1–G54.1P48).
+On real Sinumerik, $P_UIFR is a frame array containing translation,
+rotation, scale and mirror per entry. HiNC currently consumes only the
+translation component, so this table stores Vec3d per id.
+$P_UIFR is NOT in the machine data table — therefore this is a separate
+dependency from SiemensMachineDataTable (which holds
+MD-prefixed OEM machine data such as MD30300 axis type, MD34010 reference
+position, etc.).
+
+
+
+
+
+
public class SiemensFrameTable : IIsoCoordinateConfig, INcDependency, IMakeXmlSource
Gets the offset for the given G-code coordinate id.
+Returns null when no offset is configured for that id by this provider
+(callers iterate the next provider, or fall back to Zero).
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
+
+
+
+
+
+
+
+
+ SetCoordinateOffset(string, Vec3d)
+
+
+
+
Sets the offset for the given G-code coordinate id.
+
+
+
+
+
public void SetCoordinateOffset(string coordId, Vec3d offset)
public class SiemensMachineDataTable : ControllerParameterTableBase, IHomeMcConfig, IMachineAxisConfig, IRapidFeedrateConfig, INcDependency, IMakeXmlSource
+
public class SiemensMachineDataTable : ControllerParameterTableBase, IHomeMcConfig, IMachineAxisConfig, IRapidFeedrateConfig, IStrokeLimitConfig, INcDependency, IMakeXmlSource
@@ -129,6 +129,7 @@ MD30000–MD39999: Axis-specific machine data (extended).
+On real Sinumerik, $P_UIFR is a frame array containing translation,
+rotation, scale and mirror per entry. HiNC currently consumes only the
+translation component, so this table stores Vec3d per id.
+$P_UIFR is NOT in the machine data table — therefore this is a separate
+dependency from SiemensMachineDataTable (which holds
+MD-prefixed OEM machine data such as MD30300 axis type, MD34010 reference
+position, etc.).
+
Pr5221: Base address (X) of G54 work coordinate offset.
+G54.Y at +1 (Pr5222), G54.Z at +2 (Pr5223). G55..G59 follow at stride 20.
+Syntec follows Fanuc-compatible numbering — see IsoCoordinateAddressMap.
@@ -1118,6 +1305,45 @@ Null if not defined for this controller brand.
+
+
+
+ GetCoordinateOffset(string)
+
+
+
+
Gets the offset for the given G-code coordinate id.
+Returns null when no offset is configured for that id by this provider
+(callers iterate the next provider, or fall back to Zero).
Base class for brand-specific controller parameter tables.
@@ -111,11 +119,54 @@ and derived convenience properties.
CYCL DEF 247 Q339=N reads from DatumPresetTable,
CYCL DEF 7 #N reads from DatumShiftTable.
Each table maps an integer ID (1–20) to a Vec3d offset.
+
+On real Heidenhain controllers, preset and datum tables are separate
+disk files (e.g. TNC:\table\preset.pr, *.d) — distinct
+from MP-prefixed Machine Parameters (held by
+HeidenhainParameterTable). HiNC mirrors that separation
+by keeping this dependency independent of HeidenhainParameterTable.
+
+
+Implements IIsoCoordinateConfig by mapping the ISO/DIN
+G54–G59 codes to preset rows 1–6, the conventional Heidenhain
+compatibility mapping for ISO/DIN programs running on a Heidenhain.
+
Fanuc-style ISO coordinate parameter address mapping.
+G54–G59 → #5221+ (stride 20, three consecutive numbers per entry for X/Y/Z),
+G54.1 P1–P48 → #7001+ (stride 20).
+Shared between FanucParameterTable (which calls these
+“ParamId”) and SyntecParameterTable (which calls them
+“PrId”) because both follow the same numeric scheme.
Runtime state of the controller's Block Delete / Block Skip switches.
+Present in NcDependencyList exposes this to
+the runner so that blocks whose head carries / or /N
+(parsed by BlockSkipSyntax into
+BlockSkip) are skipped at semantic time.
+
+Layers are 1..9; Layer 1 corresponds to the bare / prefix.
+Controllers (Fanuc / Syntec / Mazak / Siemens) let each layer be
+toggled independently via panel switches or system parameters.
+
+
+When this dependency is absent from
+NcDependencyList, no block is skipped
+(safest default: simulate the full machining). The syntax still
+consumes the / prefix so no UnparsedText--Remaining
+diagnostic is produced.
+
Marks an INcDependency that holds volatile state which must be cleared
+when the controller performs a power reset (power off then on).
+
+Implementers should clear only the volatile subset they own (e.g. Fanuc common volatile
+macro variables #100-#499), and leave persistent state untouched
+(e.g. #500-#999, controller parameters).
+
+
+Call-frame local state (Fanuc #1-#33, Heidenhain Q200-Q1199) is NOT in scope —
+that lives in the SyntaxPiece JSON dataflow and is bounded by call activation, not power cycle.
+
Per-axis stroke (travel) limits.
+Unit is mm for linear axes, deg for rotary axes.
+Implemented by ControllerParameterTableBase using
+brand-specific parameter numbers (e.g., Fanuc #1300/#1320,
+Siemens MD36100/MD36110, Heidenhain MP420/MP430).
Sets the initial MachineCoordinateState on the first
+SyntaxPiece from IHomeMcConfig and
+IMachineAxisConfig. Only configured linear axes are
+written; rotary axes (which typically have no home) are omitted —
+downstream readers must tolerate missing axis keys.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Initializers.StaticInitializer.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Initializers.StaticInitializer.html
index 1065260a..36e39d63 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Initializers.StaticInitializer.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Initializers.StaticInitializer.html
@@ -346,7 +346,7 @@ Class StaticInitializer
-
Sets the initial MachineCoordinateState on the first
+SyntaxPiece from IHomeMcConfig and
+IMachineAxisConfig. Only configured linear axes are
+written; rotary axes (which typically have no home) are omitted —
+downstream readers must tolerate missing axis keys.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Syntaxs.CleanupSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.InspectionSyntaxs.CleanupSyntax.html
similarity index 83%
rename from App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Syntaxs.CleanupSyntax.html
rename to App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.InspectionSyntaxs.CleanupSyntax.html
index 2e37456e..f8295cd4 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Syntaxs.CleanupSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.InspectionSyntaxs.CleanupSyntax.html
@@ -84,16 +84,16 @@
@@ -397,9 +398,9 @@ Place at the end of the syntax list, after all consumers have read the keys.
-
+
-
+
MakeXmlSource(string, string, bool)
@@ -439,7 +440,7 @@ This method may also generate additional resources such as related files.
-
Remarks
+
Remarks
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
The baseDirectory is typically the folder at the nearest configuration file folder.
Since the folder can be moving with the configuration file.
Debug / observability back-fill: writes
+ProgramXyz onto blocks that did not have it
+written by upstream logic syntaxes (e.g. HomeMcInitializer
+block, chain-change blocks that only updated MC via a rotary-only path),
+only when the effective program position has changed from the
+last block that stored a ProgramXyz.
+
+Skips the block entirely when either of these holds:
+
The effective value equals the last stored value (modal-only
+ block such as pure F / S / M / plane-select — no program motion).
+
+
+Only back-fills the root block; ItemsKey
+items are intentionally skipped (they are managed by
+Hi.NcParsers.LogicSyntaxs.CompoundMotionSyntaxUtil and per-cycle
+syntaxes that already write the right per-item ProgramXyz).
+
+
+Placement: end of NcSyntaxList, after
+UnconsumedCheckSyntax. Runs purely as a
+bookkeeping pass — no other syntax / semantic in the default pipeline
+reads the additional back-fill values it emits, so the runtime output
+(IAct stream) is unchanged whether
+this syntax is present or not. The only observable effect is
+additional ProgramXyz entries in the cached
+syntax-pieces dump, which makes block-to-block debugging
+and diffing easier.
+
+
+
+
+
+
public class ProgramXyzBackfillSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
+Purely informational — no downstream syntax / semantic reads
+this marker. Intended for cache-file diffing: its presence
+means "this block did not originally command program motion;
+the value is a modal back-fill to make debug dumps more complete".
+
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Debug-time JsonObject capture: deep-clones every key on the current
+JsonObject (except the
+SnapshotKey envelope itself) into
+json[SnapshotKey][SectionName],
+leaving the rest of the block untouched.
+
+Insertable at any position in NcSyntaxList —
+placement determines what stage the dump captures (e.g. drop after
+the Parsing bundle for "after-parsing", drop after the Logic bundle
+for "after-logic"). Two instances with different
+SectionName values can coexist on the same pipeline and
+their dumps end up under sibling keys of the same
+SnapshotKey envelope, so a single cache file shows the
+data at every captured stage in one place.
+
+
+Excluding the SnapshotKey envelope from the clone keeps
+each captured section flat: it reflects "everything else on the block
+at that stage", and re-running through additional
+SnapshotSyntax instances never nests past one level.
+
+
+Set IsEnabled = false to keep the configuration
+in place but skip the capture (no JSON mutation, no allocation) —
+convenient for toggling a debug pipeline without removing the entries.
+
+
+
+
+
+
public class SnapshotSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
Top-level JSON envelope key under which captured sections are
+stored. Each SnapshotSyntax instance writes a
+sibling key (named by SectionName) inside this
+envelope.
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Emits diagnostic warnings for content remaining after all upstream
+syntaxes have run: unconsumed Parsing entries
+and non-empty UnparsedText.
+Flags listed in ExcludedFlags are silently ignored.
+Must be placed at the end of NcSyntaxList.
+
+
+
+
+
public class UnconsumedCheckSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Removes indicated JSON keys from JsonObject
+after upstream syntaxes have consumed them.
+Useful for cleaning up runtime-derived intermediate data
+(e.g., ProgramToMcTransform)
+that should not persist in the final output.
+
+Place at the end of the syntax list, after all consumers have read the keys.
+
Debug / observability back-fill: writes
+ProgramXyz onto blocks that did not have it
+written by upstream logic syntaxes (e.g. HomeMcInitializer
+block, chain-change blocks that only updated MC via a rotary-only path),
+only when the effective program position has changed from the
+last block that stored a ProgramXyz.
+
+Skips the block entirely when either of these holds:
+
The effective value equals the last stored value (modal-only
+ block such as pure F / S / M / plane-select — no program motion).
+
+
+Only back-fills the root block; ItemsKey
+items are intentionally skipped (they are managed by
+Hi.NcParsers.LogicSyntaxs.CompoundMotionSyntaxUtil and per-cycle
+syntaxes that already write the right per-item ProgramXyz).
+
+
+Placement: end of NcSyntaxList, after
+UnconsumedCheckSyntax. Runs purely as a
+bookkeeping pass — no other syntax / semantic in the default pipeline
+reads the additional back-fill values it emits, so the runtime output
+(IAct stream) is unchanged whether
+this syntax is present or not. The only observable effect is
+additional ProgramXyz entries in the cached
+syntax-pieces dump, which makes block-to-block debugging
+and diffing easier.
+
Debug-time JsonObject capture: deep-clones every key on the current
+JsonObject (except the
+SnapshotKey envelope itself) into
+json[SnapshotKey][SectionName],
+leaving the rest of the block untouched.
+
+Insertable at any position in NcSyntaxList —
+placement determines what stage the dump captures (e.g. drop after
+the Parsing bundle for "after-parsing", drop after the Logic bundle
+for "after-logic"). Two instances with different
+SectionName values can coexist on the same pipeline and
+their dumps end up under sibling keys of the same
+SnapshotKey envelope, so a single cache file shows the
+data at every captured stage in one place.
+
+
+Excluding the SnapshotKey envelope from the clone keeps
+each captured section flat: it reflects "everything else on the block
+at that stage", and re-running through additional
+SnapshotSyntax instances never nests past one level.
+
+
+Set IsEnabled = false to keep the configuration
+in place but skip the capture (no JSON mutation, no allocation) —
+convenient for toggling a debug pipeline without removing the entries.
+
Emits diagnostic warnings for content remaining after all upstream
+syntaxes have run: unconsumed Parsing entries
+and non-empty UnparsedText.
+Flags listed in ExcludedFlags are silently ignored.
+Must be placed at the end of NcSyntaxList.
Optional block skip marker extracted from the head of an NC block.
+ISO 6983 / Fanuc calls this feature Block Delete (BDT switch);
+Siemens / Syntec / Mazak use the same / prefix with matching
+behaviour.
+
+The section is only present on blocks that carry a / prefix.
+Whether the block's NC commands are actually skipped at runtime
+depends on IBlockSkipConfig:
+
Config absent or the Layer bit OFF → the /
+prefix is consumed, Body is left null, and the rest of
+the line parses as a regular NC block (comments still take effect).
Config present and the Layer bit ON → the rest
+of the line is moved into Body and cleared from
+UnparsedText, so downstream parsing syntaxes see nothing and
+no NC action is emitted. Comment syntaxes run before this one so
+comments (and any embedded CsScript) still take effect.
+
+Not a comment: a comment is static metadata, block skip is a runtime
+toggle that can change per machine/operator setting.
+
NC commands from the block that were moved out of
+UnparsedText because the skip took effect (after comment
+and CsScript extraction, with surrounding whitespace trimmed).
+Represents the semantic payload of the skipped block — not a
+verbatim snapshot; recover human-readable NC text with a
+dedicated formatter if needed.
+
+null when the skip did not take effect (no IBlockSkipConfig
+or its layer bit was OFF); in that case the block's commands are
+still in UnparsedText and parse normally.
+
Resolved absolute cycle parameters: X, Y, Z, R, Q, F, P, K.
+Used for modal lookback so the next repeat block can merge its
+own overrides with the previously-resolved values. Absent on
+G80 blocks.
NC term of the canned-cycle-group code on this block
+(“G81”, “G82”, ..., “G89”, or “G80”
+for explicit cancel). Modal-repeat blocks carry the same term
+as the most recent active cycle.
Comment extracted from an NC block.
+Symbol identifies the comment style;
+Text holds the content without the symbol.
+Downstream syntaxes (e.g., CsScript) may
+further trim Text after extracting embedded markers.
Inch unit mode — axis values and feedrates are interpreted in inches (inch/inch-per-min). Not supported by the HiNC pipeline; emits an Unsupported Error.
Canned cycle modal state (Group 09). Captures which cycle is
+currently active, its return mode (G98/G99), and the resolved
+absolute parameter set used for modal lookback.
+
+Written by CannedCycleResolveSyntax on
+every block that belongs to the canned-cycle group:
+cycle code present (G81/G82/G83/G73/G84/G74/G85/G86/G89/G76/G87),
+modal repeat (cycle still active, only coordinates given), or
+explicit cancel (G80).
+
Resolved absolute cycle parameters: X, Y, Z, R, Q, F, P, K.
+Used for modal lookback so the next repeat block can merge its
+own overrides with the previously-resolved values. Absent on
+G80 blocks.
NC term of the canned-cycle-group code on this block
+(“G81”, “G82”, ..., “G89”, or “G80”
+for explicit cancel). Modal-repeat blocks carry the same term
+as the most recent active cycle.
Coolant state (M07 mist / M08 flood / M09 off).
+Written by CoolantSyntax.
+Modal — persists until changed.
+
+IsOn is the on/off convenience flag (true for M07 and
+M08, false for M09). Mode carries the abstract kind
+(Flood / Mist /
+Off) for consumers that need to distinguish
+flood vs mist.
+
Dwell/pause section definition for use inside Sequence items.
-Resolved by Semantics.SequenceUtil into
+Resolved by Hi.NcParsers.Semantics.CompoundMotionSemanticUtil into
ActDelay.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.IFeedrateDef.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.IFeedrateDef.html
index 138d94e4..2cd4e6be 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.IFeedrateDef.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.IFeedrateDef.html
@@ -147,7 +147,7 @@ Supported by all major CNC brands.
+Only configured axes appear as keys (X/Y/Z/A/B/C). Non-existent axes
+(e.g., A/B/C on a 3-axis machine) are omitted rather than written
+as NaN sentinels.
+
Motion state written by LogicSyntaxs.MotionSyntax.
-Property names are used as JSON keys via nameof.
-
-ISO standard: G00 (rapid) / G01 (linear feed) are Group 01 modal codes.
-
+
One-shot motion event — present only on blocks that actually issue a
+motion command. Used by motion semantics (McLinearMotionSemantic,
+McArcMotionSemantic, ClLinearMotionSemantic)
+as the trigger to emit motion IAct. NOT carried
+forward across blocks. Property names are used as JSON keys via nameof.
-
public interface IMotionDef
+
public interface IMotionEventDef
@@ -143,12 +143,8 @@ ISO standard: G00 (rapid) / G01 (linear feed) are Group 01 modal codes.
-
Modal motion state — Group 01 G-code mode (G00 / G01 / G02 / G03 ...).
+Written on every block by LinearMotionSyntax /
+CircularMotionSyntax; carried across non-motion
+blocks by ModalCarrySyntax. Property names are
+used as JSON keys via nameof.
+
+Unlike sibling modal sections (Unit, PlaneSelect,
+Positioning) which carry both a brand-specific Term
+and a brand-neutral conventional field, MotionState intentionally
+keeps only Term: the brand-neutral semantic ("what kind of
+motion happened") lives on the sibling one-shot MotionEvent
+(Form = McLinear / McArc / ClLinear / ClArc).
+State here is purely the modal latch of the last Group-01 G-code so
+downstream FindPrevious* can resume motion-mode bookkeeping.
+
+ISO/Fanuc G05.1 Q1 (enable) / G05.1 Q0 (disable):
+high-precision contour control / AICC / Nano Smoothing.
+Controller-internal interpolation black box — simulation records
+the state but does not alter the tool path.
+
Program end marker (M02/M30).
+Written by ProgramEndSyntax.
+Other syntaxes (e.g. IsoLocalCoordinateOffsetSyntax)
+read this section to reset modal state instead of detecting M30 directly.
Program-stop marker (M00 unconditional / M01 optional).
+Written by ProgramStopSyntax on each
+block that carries an M00/M01 flag. Non-modal: the section appears
+only on the exact block where the stop code is present.
+
+Distinct from IProgramEndDef (M02/M30, end of program).
+
+
+M00 halts execution unconditionally; the operator must press Cycle
+Start to resume. M01 is an optional stop gated by the operator's
+"Optional Stop" panel switch — ignored when the switch is off.
+This parsing-layer section records the NC intent; runtime /
+semantic layers decide whether to actually pause.
+
Offset number (Fanuc D number) selecting the radius in the tool offset table.
+Modal — preserved across G40 blocks so the next G41/G42 without an explicit
+D continues to reference the same row, matching real Fanuc/Siemens behaviour.
Unsigned compensation radius in mm, looked up from the tool offset table.
+Real controller tool tables hold the radius as a non-negative geometry
+value (wear/delta sits in a separate column); this property mirrors that
+convention. Direction is encoded by Side.
+Omitted from the JSON section when Side is
+SideNone.
RTCP-rotary-dynamic state (whether the per-step MC path is non-linear
+while CL is commanded linearly) is signalled by a
+KindDynamic entry in the
+ProgramToMcTransform chain rather than
+by a flag on this section, so consumers detect it via
+HasDynamicEntry(JsonObject) without needing
+brand-specific strings.
+
Properties
-
-
-
- Mode
-
-
-
-
Active G-code mode: “G43”, “G43.4”, “G44”, “G49”.
-Brand-specific syntaxes may write equivalent mode strings
-(e.g., “TRAORI” for Siemens, “M128” for Heidenhain).
CNC term for tool height compensation: “G43”, “G43.4”, “G44”, “G49”.
+Brand-specific syntaxes may write equivalent terms
+(e.g., “TRAORI” for Siemens, “M128” for Heidenhain).
Chain of named ProgramXyz → MachineCoordinate transformation entries.
-Stored as a JsonArray of entries, each with “Source” and “Mat4d” keys.
-Each contributing INcSyntax adds or replaces its own entry by source name.
-ProgramXyzSyntax composes all entries in order:
-McXyz = ProgramXyz * T[0] * T[1] * ... * T[n].
+Stored as a JsonArray of entries, each with
+“Source”, “Kind”, and “Mat4d” keys.
+Each contributing INcSyntax adds or replaces its own
+entry by source name.
+GetComposedTransform(JsonObject)
+composes entries in order: McXyz = ProgramXyz * T[0] * T[1] * ... * T[n].
+
+Kind contour-validity classification. Each entry is either:
+
"Static" — the Mat4d is valid for any point along the contour.
+Tilt, coord-offset, and the kinematic pivot in non-RTCP / rotary-stable
+blocks are all Static.
"Dynamic" — the Mat4d is a block-endpoint snapshot of a
+rotary-state-dependent transform (RTCP rotary-dynamic). Composition still
+yields a correct endpoint MC, but the matrix is not contour-valid:
+intermediate CL-point positions cannot be derived by applying it to an
+interpolated ProgramXyz. The semantic layer
+(ClLinearMotionSemantic) handles per-step IK
+separately.
Unit-system state (ISO Group 06: G20 inch / G21 metric).
+Written by UnitModeSyntax. Modal.
+
+HiNC's NC pipeline works exclusively in millimetres. G21 is therefore
+a no-op confirmation of the default; G20 is reported as an
+Unsupported Error and callers are expected to pre-convert the NC
+program to metric before loading.
+
+
+
+
+
+
+
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.LocalCoordinateOffset.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.IsoLocalCoordinateOffset.html
similarity index 75%
rename from App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.LocalCoordinateOffset.html
rename to App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.IsoLocalCoordinateOffset.html
index d046e438..dbd40145 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.LocalCoordinateOffset.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.Keywords.IsoLocalCoordinateOffset.html
@@ -2,11 +2,11 @@
- Class LocalCoordinateOffset | HiAPI-C# 2025
+ Class IsoLocalCoordinateOffset | HiAPI-C# 2025
-
+
-
+
@@ -84,12 +84,12 @@
-
+
-
-Class LocalCoordinateOffset
+
+Class IsoLocalCoordinateOffset
@@ -97,19 +97,28 @@ Class LocalCoordinateOffset
Assembly
HiMech.dll
-
Local coordinate offset state (G52) written by
+
ISO/Fanuc-family local coordinate offset state (G52) written by
IsoLocalCoordinateOffsetSyntax.
Property names are used as JSON keys via nameof.
-ISO: G52 X Y Z (local coordinate system shift, additive to G54 series).
-Cancelled by G52 X0 Y0 Z0 or M30 (program end).
-Siemens equivalent: TRANS / ATRANS (handled by separate syntax).
+G52 X Y Z installs a local coordinate-system shift that stacks on top of
+the active G54-G59 work offset. The cancel mechanism is to write
+G52 X0 Y0 Z0 (or hit M30 / reset) — there is no separate G code
+for "cancel". The offset vector is therefore always modal: zero is a
+valid modal value, not a "disabled" state, so the section is recorded
+on every block.
+
+
+Brand-specific kin: Siemens TRANS/ATRANS (which can also
+carry rotation/scale/mirror) and Heidenhain TRANS DATUM are
+handled by their own syntaxes and write to their own sections — they
+do not share this key, because their data shapes are richer.
-
public class LocalCoordinateOffset
+
public class IsoLocalCoordinateOffset
@@ -119,7 +128,7 @@ Siemens equivalent: TRANS / ATRANS (handled by separate syntax).
Program start/end delimiter line (e.g., % in Fanuc/Mazak/Syntec,
+%_N_xxx_MPF in Siemens).
+Not a comment — the controller uses it as a tape/file boundary marker.
Offset number (Fanuc D number) selecting the radius in the tool offset table.
+Modal — preserved across G40 blocks so the next G41/G42 without an explicit
+D continues to reference the same row, matching real Fanuc/Siemens behaviour.
Unsigned compensation radius in mm, looked up from the tool offset table.
+Real controller tool tables hold the radius as a non-negative geometry
+value (wear/delta sits in a separate column); this property mirrors that
+convention. Direction is encoded by Side.
+Omitted from the JSON section when Side is
+SideNone.
CNC term for tool height compensation: “G43”, “G43.4”, “G44”, “G49”.
+Brand-specific syntaxes may write equivalent terms
+(e.g., “TRAORI” for Siemens, “M128” for Heidenhain).
Optional block skip marker extracted from the head of an NC block.
+ISO 6983 / Fanuc calls this feature Block Delete (BDT switch);
+Siemens / Syntec / Mazak use the same / prefix with matching
+behaviour.
+
+The section is only present on blocks that carry a / prefix.
+Whether the block's NC commands are actually skipped at runtime
+depends on IBlockSkipConfig:
+
Config absent or the Layer bit OFF → the /
+prefix is consumed, Body is left null, and the rest of
+the line parses as a regular NC block (comments still take effect).
Config present and the Layer bit ON → the rest
+of the line is moved into Body and cleared from
+UnparsedText, so downstream parsing syntaxes see nothing and
+no NC action is emitted. Comment syntaxes run before this one so
+comments (and any embedded CsScript) still take effect.
+
+Not a comment: a comment is static metadata, block skip is a runtime
+toggle that can change per machine/operator setting.
+
Comment extracted from an NC block.
+Symbol identifies the comment style;
+Text holds the content without the symbol.
+Downstream syntaxes (e.g., CsScript) may
+further trim Text after extracting embedded markers.
ISO/Fanuc-family local coordinate offset state (G52) written by
IsoLocalCoordinateOffsetSyntax.
Property names are used as JSON keys via nameof.
-ISO: G52 X Y Z (local coordinate system shift, additive to G54 series).
-Cancelled by G52 X0 Y0 Z0 or M30 (program end).
-Siemens equivalent: TRANS / ATRANS (handled by separate syntax).
+G52 X Y Z installs a local coordinate-system shift that stacks on top of
+the active G54-G59 work offset. The cancel mechanism is to write
+G52 X0 Y0 Z0 (or hit M30 / reset) — there is no separate G code
+for "cancel". The offset vector is therefore always modal: zero is a
+valid modal value, not a "disabled" state, so the section is recorded
+on every block.
+
+
+Brand-specific kin: Siemens TRANS/ATRANS (which can also
+carry rotation/scale/mirror) and Heidenhain TRANS DATUM are
+handled by their own syntaxes and write to their own sections — they
+do not share this key, because their data shapes are richer.
Program start/end delimiter line (e.g., % in Fanuc/Mazak/Syntec,
+%_N_xxx_MPF in Siemens).
+Not a comment — the controller uses it as a tape/file boundary marker.
Canned cycle modal state (Group 09). Captures which cycle is
+currently active, its return mode (G98/G99), and the resolved
+absolute parameter set used for modal lookback.
+
+Written by CannedCycleResolveSyntax on
+every block that belongs to the canned-cycle group:
+cycle code present (G81/G82/G83/G73/G84/G74/G85/G86/G89/G76/G87),
+modal repeat (cycle still active, only coordinates given), or
+explicit cancel (G80).
+
Coolant state (M07 mist / M08 flood / M09 off).
+Written by CoolantSyntax.
+Modal — persists until changed.
+
+IsOn is the on/off convenience flag (true for M07 and
+M08, false for M09). Mode carries the abstract kind
+(Flood / Mist /
+Off) for consumers that need to distinguish
+flood vs mist.
+
Dwell/pause section definition for use inside Sequence items.
-Resolved by Semantics.SequenceUtil into
+Resolved by Hi.NcParsers.Semantics.CompoundMotionSemanticUtil into
ActDelay.
@@ -219,15 +351,49 @@ Supported by all major CNC brands.
+Only configured axes appear as keys (X/Y/Z/A/B/C). Non-existent axes
+(e.g., A/B/C on a 3-axis machine) are omitted rather than written
+as NaN sentinels.
+
One-shot motion event — present only on blocks that actually issue a
+motion command. Used by motion semantics (McLinearMotionSemantic,
+McArcMotionSemantic, ClLinearMotionSemantic)
+as the trigger to emit motion IAct. NOT carried
+forward across blocks. Property names are used as JSON keys via nameof.
Modal motion state — Group 01 G-code mode (G00 / G01 / G02 / G03 ...).
+Written on every block by LinearMotionSyntax /
+CircularMotionSyntax; carried across non-motion
+blocks by ModalCarrySyntax. Property names are
+used as JSON keys via nameof.
-ISO standard: G00 (rapid) / G01 (linear feed) are Group 01 modal codes.
+Unlike sibling modal sections (Unit, PlaneSelect,
+Positioning) which carry both a brand-specific Term
+and a brand-neutral conventional field, MotionState intentionally
+keeps only Term: the brand-neutral semantic ("what kind of
+motion happened") lives on the sibling one-shot MotionEvent
+(Form = McLinear / McArc / ClLinear / ClArc).
+State here is purely the modal latch of the last Group-01 G-code so
+downstream FindPrevious* can resume motion-mode bookkeeping.
@@ -236,17 +402,88 @@ ISO standard: G00 (rapid) / G01 (linear feed) are Group 01 modal codes.
+ISO/Fanuc G05.1 Q1 (enable) / G05.1 Q0 (disable):
+high-precision contour control / AICC / Nano Smoothing.
+Controller-internal interpolation black box — simulation records
+the state but does not alter the tool path.
+
Program end marker (M02/M30).
+Written by ProgramEndSyntax.
+Other syntaxes (e.g. IsoLocalCoordinateOffsetSyntax)
+read this section to reset modal state instead of detecting M30 directly.
Program-stop marker (M00 unconditional / M01 optional).
+Written by ProgramStopSyntax on each
+block that carries an M00/M01 flag. Non-modal: the section appears
+only on the exact block where the stop code is present.
+
+Distinct from IProgramEndDef (M02/M30, end of program).
+
+
+M00 halts execution unconditionally; the operator must press Cycle
+Start to resume. M01 is an optional stop gated by the operator's
+"Optional Stop" panel switch — ignored when the switch is off.
+This parsing-layer section records the NC intent; runtime /
+semantic layers decide whether to actually pause.
+
Chain of named ProgramXyz → MachineCoordinate transformation entries.
-Stored as a JsonArray of entries, each with “Source” and “Mat4d” keys.
-Each contributing INcSyntax adds or replaces its own entry by source name.
-ProgramXyzSyntax composes all entries in order:
-McXyz = ProgramXyz * T[0] * T[1] * ... * T[n].
+Stored as a JsonArray of entries, each with
+“Source”, “Kind”, and “Mat4d” keys.
+Each contributing INcSyntax adds or replaces its own
+entry by source name.
+GetComposedTransform(JsonObject)
+composes entries in order: McXyz = ProgramXyz * T[0] * T[1] * ... * T[n].
+
+Kind contour-validity classification. Each entry is either:
+
"Static" — the Mat4d is valid for any point along the contour.
+Tilt, coord-offset, and the kinematic pivot in non-RTCP / rotary-stable
+blocks are all Static.
"Dynamic" — the Mat4d is a block-endpoint snapshot of a
+rotary-state-dependent transform (RTCP rotary-dynamic). Composition still
+yields a correct endpoint MC, but the matrix is not contour-valid:
+intermediate CL-point positions cannot be derived by applying it to an
+interpolated ProgramXyz. The semantic layer
+(ClLinearMotionSemantic) handles per-step IK
+separately.
Unit-system state (ISO Group 06: G20 inch / G21 metric).
+Written by UnitModeSyntax. Modal.
+
+HiNC's NC pipeline works exclusively in millimetres. G21 is therefore
+a no-op confirmation of the default; G20 is reported as an
+Unsupported Error and callers are expected to pre-convert the NC
+program to metric before loading.
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.BoringCycleSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.BoringCycleSyntax.html
index 27e758ce..239cea4d 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.BoringCycleSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.BoringCycleSyntax.html
@@ -275,7 +275,8 @@ the previous direction was CW (M03), which is the typical boring setup.
-
+
Syntax kind name (typically the concrete type name).
Resolves canned cycle parameters for the current block:
-modal repetition detection, G91 incremental-to-absolute conversion,
-and missing-axis fallback from last known position.
+
Resolves the canned-cycle Group-09 state for the current block
+and writes the result to the CannedCycle section.
+
Active cycle (direct G81..G89 or modal repeat): merges
+Parsing overrides with previous-cycle stored params, applies
+G91 incremental-to-absolute conversion and missing-axis fallback,
+writes CannedCycle with Term,
+ReturnMode, and
+Params. The resolved cycle sub-section
+is left in Parsing under the cycle code for downstream cycle
+syntaxes (DrillingCycleSyntax, etc.) to read.
Explicit cancel (G80 flag present on a non-cycle block):
+consumes the G80 flag and writes
+CannedCycle = { Term: "G80" }, acting as a hard
+sentinel for Hi.NcParsers.LogicSyntaxs.CannedCycleSyntaxUtil modal lookback.
No Group-09 activity: leaves the block untouched.
-After this syntax, the cycle sub-section in Parsing
-(e.g., Parsing.G83) contains fully resolved absolute
-coordinates — downstream cycle syntaxes
-(DrillingCycleSyntax, PeckDrillingCycleSyntax)
-can read them directly without incremental or modal logic.
-
-
-For modal repetition (no cycle G-code in the current block),
-merges stored parameters from the previous block's
-CompoundMotion.Hi.NcParsers.LogicSyntaxs.CannedCycleSyntaxUtil.ResolvedParamsKey
-with current-block overrides from Parsing root, removes
-consumed keys from Parsing root, and writes the merged
-section to Parsing under the cycle code key.
-
@@ -245,7 +240,8 @@ the individual cycle syntaxes in the chain.
-
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CircularMotionSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CircularMotionSyntax.html
index 066960da..1a042ff1 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CircularMotionSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CircularMotionSyntax.html
@@ -6,7 +6,7 @@
-
+
@@ -101,17 +101,18 @@ Class CircularMotionSyntax
(ISO G02/G03).
Detects motion mode from Flags, reads
I/J/K center offsets or R radius from Parsing,
-computes arc center in program coordinates, and writes
-IMotionDef + IArcMotionDef data.
+computes arc center in program coordinates, and writes a one-shot
+MotionEvent (form + arc params) plus a modal
+MotionState (Term).
-G02/G03 mode is modal (Group 01) — persists via backward lookback.
-Arc parameters (I/J/K/R) are per-block and must be present
-in every arc block.
+G02/G03 mode is modal (Group 01) — persists across blocks via
+Term. Arc parameters (I/J/K/R) are
+per-block and must be present in every arc block.
Must be placed before LinearMotionSyntax in the
-syntax chain. Both share the Group 01 Hi.Motion slot;
-whichever writes first claims it.
+syntax chain. Both share the Group 01 motion slot; whichever
+writes a MotionEvent first claims it.
@@ -269,7 +270,8 @@ whichever writes first claims it.
-
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.Common.RoutineBlocker0.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CoolantSyntax.html
similarity index 63%
rename from App/wwwroot/HiAPI-docsite/api/Hi.Common.RoutineBlocker0.html
rename to App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CoolantSyntax.html
index d8f43f68..f67b9af6 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.Common.RoutineBlocker0.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CoolantSyntax.html
@@ -2,11 +2,11 @@
- Class RoutineBlocker0 | HiAPI-C# 2025
+ Class CoolantSyntax | HiAPI-C# 2025
-
+
-
+
@@ -84,25 +84,31 @@
Block the thread to the given delay from the previous block.
+
Consumes M07 (mist ON), M08 (flood ON), and M09 (coolant OFF) from
+Flags and writes the ICoolantDef
+section with both IsOn (convenience flag)
+and Mode (abstract mode name:
+Flood / Mist /
+Off).
+Modal — persists via backward lookback.
-
public class RoutineBlocker0 : IMakeXmlSource
+
public class CoolantSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
Delay the thread. The delay time is Period, counted from the previous Block() to the current Block().
-The first function call does no delay.
-If the time between two Block() is over Period, the function call does no delay.
+
Build syntax arrangement into the
+syntaxPieceNode in-place.
-
public void Block()
+
public void Build(LazyLinkedListNode<SyntaxPiece> syntaxPieceNode, List<INcDependency> ncDependencyList, NcDiagnosticProgress ncDiagnosticProgress)
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- HasToBlock()
-
-
-
-
If calling Block() make thread delay, return true; otherwise, false.
@@ -464,7 +399,7 @@ This method may also generate additional resources such as related files.
-
Remarks
+
Remarks
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
The baseDirectory is typically the folder at the nearest configuration file folder.
Since the folder can be moving with the configuration file.
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CoordinateOffsetUtil.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CoordinateOffsetUtil.html
index f0907415..187315aa 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CoordinateOffsetUtil.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.CoordinateOffsetUtil.html
@@ -296,6 +296,54 @@ backward lookback, and
+
+
Resolves the offset for coordId by scanning every
+IIsoCoordinateConfig in ncDependencyList
+and returning the first non-null result. Returns null when no provider
+has data for this id (callers should fall back to Zero).
+
+Multi-provider iteration lets a brand parameter table cover the
+hardware-mapped subset (e.g. Fanuc G54–G59, G54.1 P1–P48 backed by
+real parameter numbers) while a standalone IsoCoordinateTable
+covers HiNC-extension ids the brand table does not handle (e.g. G59.1–G59.9).
+
+
+
+
+
+
public static Vec3d ResolveOffset(IEnumerable<INcDependency> ncDependencyList, string coordId)
Outcome of evaluating an NcExpr. Either a successful
+numeric value, or a failure with an error code matching the diagnostic
+catalogue used by reading / evaluator syntaxes.
+
+
+
+
+
public readonly record struct EvalResult : IEquatable<EvalResult>
Outcome of evaluating an NcExpr. Either a successful
+numeric value, or a failure with an error code matching the diagnostic
+catalogue used by reading / evaluator syntaxes.
+
+
+
+
+
public EvalResult(double? Value, string ErrorCode, string ErrorMessage)
Stateless variable lookup that needs per-block runtime context — the
+current SyntaxPiece node (for Previous
+traceback into runtime-state sections like MachineCoordinateState
+/ ProgramXyz) and the dependency list (so the lookup can read
+from sibling dependencies without holding a static reference).
+
+Distinguished from IVariableLookup: that one is for
+long-lived dependencies that already hold their own data (parameter
+tables, tool-offset wrappers, retained-variable tables) and need no
+block context. IRuntimeVariableLookup is for context-sensitive
+resolutions configured declaratively on
+RuntimeVariableLookups.
+
+
+Implementations should be brand-specific (e.g. Fanuc #5001-#5043
+position reads) and return null for keys outside their range so
+the evaluator's chain can fall through to the next lookup.
+
Returns the value of the variable identified by key
+in the context of node and
+dependencies, or null if the key is outside
+this lookup's range or the value is vacant.
Resolves a Custom Macro B variable reference to its current numeric value,
+or null for vacant (Fanuc <vacant>) and out-of-scope alike.
+
+The key is the raw source token — Fanuc "#124", Heidenhain
+"Q1", Siemens "R1" — so the interface itself is brand-agnostic.
+Implementations are typically narrow (one per id range / per brand prefix)
+and parse the prefix locally; chain them at the call site by trying each
+in priority order until one returns a non-null value.
+
+
+A returned null is treated by NcExpressionEvaluator
+as vacant and surfaces as a Variable--Vacant failure when the
+value is consumed in arithmetic context.
+
AST root for a Fanuc Custom Macro B value expression. Concrete leaves
+and combinators sit alongside NcExpressionParser; walking
+is the job of NcExpressionEvaluator.
+
+
+
+
+
public abstract record NcExpr : IEquatable<NcExpr>
Walks an NcExpr AST and produces an EvalResult.
+Resolves #nnn via an IVariableLookup; built-in function
+names are matched case-insensitively against a fixed table.
+
+Phase-1 supports: SIN COS TAN ASIN ACOS ATAN SQRT ABS ROUND FIX FUP LN
+EXP POW. Trigonometric arguments and results are in degrees, matching
+Fanuc Custom Macro B convention. Unknown function names surface as
+UnsupportedFunctionCode; arity mismatches as
+ArgumentMismatchCode; division / MOD by zero and domain
+errors (e.g. SQRT[-1]) as MathErrorCode; vacant
+operands as VacantErrorCode.
+
Recursive-descent parser for Fanuc Custom Macro B value expressions.
+Pure: takes a string, produces an NcExpr AST. Performs no
+variable lookup and no evaluation.
+Function names are case-insensitive (SIN = sin); whitespace
+is skipped between tokens. The '/' '[' expr ']' tail captures the
+dual-bracket form Fanuc uses for ATAN[a]/[b]; non-ATAN callers that
+happen to use it produce a function with an extra arg, which the evaluator
+rejects with an arity error.
+
Indirect variable reference #[expr]. The inner expression is
+evaluated and truncated toward zero to obtain an integer; the lookup key
+is then Prefix concatenated with that integer
+(e.g. Prefix="#", computed 124 → "#124").
+
+
+
+
+
public sealed record NcIndirectVariableExpr : NcExpr, IEquatable<NcExpr>, IEquatable<NcIndirectVariableExpr>
Indirect variable reference #[expr]. The inner expression is
+evaluated and truncated toward zero to obtain an integer; the lookup key
+is then Prefix concatenated with that integer
+(e.g. Prefix="#", computed 124 → "#124").
+
+
+
+
+
public NcIndirectVariableExpr(string Prefix, NcExpr Index)
AST root for a Fanuc Custom Macro B value expression. Concrete leaves
+and combinators sit alongside NcExpressionParser; walking
+is the job of NcExpressionEvaluator.
Walks an NcExpr AST and produces an EvalResult.
+Resolves #nnn via an IVariableLookup; built-in function
+names are matched case-insensitively against a fixed table.
+
+Phase-1 supports: SIN COS TAN ASIN ACOS ATAN SQRT ABS ROUND FIX FUP LN
+EXP POW. Trigonometric arguments and results are in degrees, matching
+Fanuc Custom Macro B convention. Unknown function names surface as
+UnsupportedFunctionCode; arity mismatches as
+ArgumentMismatchCode; division / MOD by zero and domain
+errors (e.g. SQRT[-1]) as MathErrorCode; vacant
+operands as VacantErrorCode.
+
Recursive-descent parser for Fanuc Custom Macro B value expressions.
+Pure: takes a string, produces an NcExpr AST. Performs no
+variable lookup and no evaluation.
+Function names are case-insensitive (SIN = sin); whitespace
+is skipped between tokens. The '/' '[' expr ']' tail captures the
+dual-bracket form Fanuc uses for ATAN[a]/[b]; non-ATAN callers that
+happen to use it produce a function with an extra arg, which the evaluator
+rejects with an arity error.
+
Indirect variable reference #[expr]. The inner expression is
+evaluated and truncated toward zero to obtain an integer; the lookup key
+is then Prefix concatenated with that integer
+(e.g. Prefix="#", computed 124 → "#124").
Outcome of evaluating an NcExpr. Either a successful
+numeric value, or a failure with an error code matching the diagnostic
+catalogue used by reading / evaluator syntaxes.
Stateless variable lookup that needs per-block runtime context — the
+current SyntaxPiece node (for Previous
+traceback into runtime-state sections like MachineCoordinateState
+/ ProgramXyz) and the dependency list (so the lookup can read
+from sibling dependencies without holding a static reference).
+
+Distinguished from IVariableLookup: that one is for
+long-lived dependencies that already hold their own data (parameter
+tables, tool-offset wrappers, retained-variable tables) and need no
+block context. IRuntimeVariableLookup is for context-sensitive
+resolutions configured declaratively on
+RuntimeVariableLookups.
+
+
+Implementations should be brand-specific (e.g. Fanuc #5001-#5043
+position reads) and return null for keys outside their range so
+the evaluator's chain can fall through to the next lookup.
+
Resolves a Custom Macro B variable reference to its current numeric value,
+or null for vacant (Fanuc <vacant>) and out-of-scope alike.
+
+The key is the raw source token — Fanuc "#124", Heidenhain
+"Q1", Siemens "R1" — so the interface itself is brand-agnostic.
+Implementations are typically narrow (one per id range / per brand prefix)
+and parse the prefix locally; chain them at the call site by trying each
+in priority order until one returns a non-null value.
+
+
+A returned null is treated by NcExpressionEvaluator
+as vacant and surfaces as a Variable--Vacant failure when the
+value is consumed in arithmetic context.
+
+The RTCP kinematic rotary part (Pn→MC rigid transform) is orthogonal
+to this syntax and is written by PivotTransformationSyntax
+on every block, because rotary state remains in effect beyond
+the RTCP modal (e.g. a non-RTCP G01 after G49 still
+inherits the last ABC from the program).
+
+G43.4 is used by Fanuc, Mazak, Syntec, and Okuma. Siemens (TRAORI) and
+Heidenhain (M128) are handled by separate syntaxes. Must be placed
+afterToolHeightOffsetSyntax (to override the
+ToolHeightCompensation entry when RTCP is active) and before
+PivotTransformationSyntax (which runs last in the chain).
+
+
+
+
+
+
public class G43p4RtcpSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.G53p1RotaryPositionSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.G53p1RotaryPositionSyntax.html
index ba6792ec..57f5a11f 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.G53p1RotaryPositionSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.G53p1RotaryPositionSyntax.html
@@ -110,7 +110,7 @@ to solve for the target A/B/C via inverse kinematics.
Must be placed afterIsoG68p2TiltSyntax
(needs tilt data) and beforeProgramXyzSyntax
in the syntax chain. Writes A/B/C into
-MachineCoordinate.
+MachineCoordinateState.
Motion is handled by LinearMotionSyntax via modal G00/G01.
@@ -205,7 +205,7 @@ When G68.2 is not active, a validation error is reported.
Optional explicit A/B/C on the G53.1 line (post-processor hints)
override the IK result. These are read from
Parsing via
-RotaryAxisUtil.ReadAndConsumeAxis and consumed
+ConsumeAxis(JsonObject, string, Sentence, NcDiagnosticProgress) and consumed
to prevent McAbcSyntax from double-processing.
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.Heidenhain.HeidenhainCoordinateOffsetSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.Heidenhain.HeidenhainCoordinateOffsetSyntax.html
index 49d12343..cff8e7bf 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.Heidenhain.HeidenhainCoordinateOffsetSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.Heidenhain.HeidenhainCoordinateOffsetSyntax.html
@@ -264,7 +264,8 @@ so both syntaxes can coexist without double-composing.
-
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.HighSpeedPeckCycleSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.HighSpeedPeckCycleSyntax.html
index 5ebd8e38..f0a85c04 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.HighSpeedPeckCycleSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.HighSpeedPeckCycleSyntax.html
@@ -268,7 +268,8 @@ Must be placed after
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IncrementalResolveSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IncrementalResolveSyntax.html
index b0c2bed8..db033bbe 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IncrementalResolveSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IncrementalResolveSyntax.html
@@ -99,8 +99,8 @@ Class IncrementalResolveSyntax
ISO/Fanuc/Mazak/Okuma/Syntec: resolves G54–G59.9 work coordinate offset.
Reads G54/G55/.../G59.9 from Flags,
-looks up offset Vec3d from IsoCoordinateTable dependency,
+looks up offset Vec3d via IIsoCoordinateConfig dependencies
+(e.g. brand parameter table or IsoCoordinateTable),
composes into ProgramToMcTransform.
Modal — active coordinate persists via backward lookback.
Default coordinate ID is set by StaticInitializer.
@@ -259,7 +260,8 @@ Default coordinate ID is set by
+
Syntax kind name (typically the concrete type name).
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IsoG68p2TiltSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IsoG68p2TiltSyntax.html
index 9a82d342..3d7ca318 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IsoG68p2TiltSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IsoG68p2TiltSyntax.html
@@ -275,7 +275,8 @@ preserves the exact IJK orientation while aligning with the post-processor's sol
-
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IsoLocalCoordinateOffsetSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IsoLocalCoordinateOffsetSyntax.html
index 1eb2789e..500124de 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IsoLocalCoordinateOffsetSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.IsoLocalCoordinateOffsetSyntax.html
@@ -6,7 +6,7 @@
-
+
@@ -104,8 +104,8 @@ Class IsoLocalCoordinateOffsetSyntax
M30 (program end) → also cancels.
Reads Parsing.G52 (from G52Syntax),
-writes LocalCoordinateOffset section,
-and adds a "LocalCoordinateOffset" entry to the transformation chain.
+writes IsoLocalCoordinateOffset section,
+and adds an "IsoLocalCoordinateOffset" entry to the transformation chain.
Modal — persists via backward lookback until changed or cancelled.
@@ -266,7 +266,7 @@ Modal — persists via backward lookback until changed or cancelled.
-
public const string TransformSource = "LocalCoordinateOffset"
+
public const string TransformSource = "IsoLocalCoordinateOffset"
@@ -297,7 +297,8 @@ Modal — persists via backward lookback until changed or cancelled.
-
+
Syntax kind name (typically the concrete type name).
Writes McLinear motion for linear commands
-(ISO G00/G01, Heidenhain L/LN).
-Detects motion mode from Flags, writes
-IMotionDef section when
-MachineCoordinate exists.
+(ISO G00/G01, Heidenhain L/LN). Detects motion mode from
+Flags, writes a one-shot
+MotionEvent section (form + isRapid) plus a modal
+MotionState section (Term) when
+MachineCoordinateState exists on the block.
-Modal — persists across blocks via backward node lookback.
Must be placed after McAbcSyntax in the syntax chain.
@@ -265,7 +265,8 @@ Must be placed after
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.MachineCoordSelectSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.MachineCoordSelectSyntax.html
index 100d7ae9..4f0dadf8 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.MachineCoordSelectSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.MachineCoordSelectSyntax.html
@@ -106,7 +106,7 @@ If G91 (incremental) is active, G53 is ignored per ISO standard.
Must be placed beforeProgramXyzSyntax in the
syntax chain. When G53 is active, this syntax consumes X/Y/Z from
Parsing and writes
-MachineCoordinate directly,
+MachineCoordinateState directly,
preventing ProgramXyzSyntax from processing them
as program coordinates.
@@ -276,7 +276,8 @@ Output: MachineCoordinate = (prevMcX, prevMcY, 0)
-
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.McAbcCyclicPathSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.McAbcCyclicPathSyntax.html
index ebcc1dee..73793bdf 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.McAbcCyclicPathSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.McAbcCyclicPathSyntax.html
@@ -99,7 +99,7 @@ Class McAbcCyclicPathSyntax
Only active when IMachineAxisConfig declares rotary axes.
Works for both 3+2-axis (no IMachineKinematics)
and simultaneous 5-axis configurations.
-When MachineCoordinate does not exist
-(e.g., rotary-only blocks like G00 A30. with no X/Y/Z),
-the section is created with XYZ filled from lookback.
+This syntax is intentionally ABC-only. When the block is rotary-only
+(no ProgramXyz, e.g. G00 A30.) the section is created
+with ABC but without X/Y/Z. McAbcXyzFallbackSyntax
+— placed after McXyzSyntax — copies X/Y/Z from the
+previous block's MachineCoordinateState
+to finish the section. Splitting the XYZ fill out lets this syntax
+run beforeMcXyzSyntax (and before
+G43p4RtcpSyntax) without accidentally filling X/Y/Z
+from prev and thereby short-circuiting
+DeriveMcXyz(JsonObject, Mat4d).
+Non-dynamic (no RTCP or RTCP with ABC stable) — the
+programmed tool tip stays put in MC while rotary axes (if any) are
+unchanged, so we simply copy X/Y/Z from the previous block's
+MachineCoordinateState. This matches
+NC modal XYZ carry-forward for rotary-only blocks such as
+G00 A30. (non-RTCP pivoting).
+
+Dynamic (RTCP active + ABC changing) — the programmed tool tip
+must stay fixed in program coordinates while MC XYZ shifts to
+compensate the new rotary state. Looks up the last
+ProgramXyz and re-derives
+MC = inheritedProgramXyz × composedTransform, where the
+composed transform is the block's endpoint chain (now including
+PivotTransformSource as a full
+rotation+translation Mat4d, so the chain already encodes the
+kinematic IK). The carried ProgramXyz is also stamped onto
+the current block so downstream consumers see a consistent
+ProgramXyz + MC pair.
+
+
+Pair with McAbcSyntax, which runs early to write ABC
+but deliberately leaves X/Y/Z empty so McXyzSyntax can
+still derive MC XYZ from ProgramXyz via the transform chain
+when the block carries linear motion. If McXyzSyntax
+has nothing to derive (no ProgramXyz), this syntax completes
+the MC section as described above.
+
+
+Does nothing when the section already carries all three of X/Y/Z
+(normal linear-motion blocks), or when there is no section at all
+(pure parse-only block that introduces no MC). Must be placed
+afterMcXyzSyntax and before
+McAbcCyclicPathSyntax / LinearMotionSyntax.
+
+
+
+
+
+
public class McAbcXyzFallbackSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Consumes G05.1 (high-precision contour / path smoothing) and records
+its modal state. Q1 enables, Q0 disables. The simulation does not alter
+the tool path — this is a controller-internal interpolation black box.
+
-
public class HeadPercentCommentSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
+
public class PathSmoothingSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
@@ -111,7 +114,7 @@ Class HeadPercentCommentSyntax
@@ -349,9 +353,9 @@ Class HeadPercentCommentSyntax
-
+
-
+
MakeXmlSource(string, string, bool)
@@ -391,7 +395,7 @@ This method may also generate additional resources such as related files.
-
Remarks
+
Remarks
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
The baseDirectory is typically the folder at the nearest configuration file folder.
Since the folder can be moving with the configuration file.
Writes the PivotTransformSource entry
+into ProgramToMcTransform
+on every block, capturing the Pn→MC kinematic rigid transform
+for the block's endpoint rotary state. Mirrors legacy
+HardNcLine.GetProgramXyz's use of
+McToPn(DVec3d) — without this entry, the
+transform chain would miss the rotary rotation on any block whose
+MachineCoordinate.ABC is non-zero, and McXyzSyntax (and
+ProgramXyzSyntax's inverse lookback) would silently drift.
+
+Scope is not limited to RTCP modal: as long as rotary axes are
+physically at a non-zero position (e.g. after a non-RTCP G00 B90
+plus any subsequent motion), the kinematic chain still contributes a
+non-identity rigid transform that must appear in the endpoint chain.
+G43p4RtcpSyntax is orthogonal and only governs the
+dynamic-rotary KindKey tagging used by
+LinearMotionSyntax to pick the motion form.
+
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.PositioningModeSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.PositioningSyntax.html
similarity index 79%
rename from App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.PositioningModeSyntax.html
rename to App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.PositioningSyntax.html
index de2c24d2..f4ace5fa 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.PositioningModeSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.PositioningSyntax.html
@@ -2,11 +2,11 @@
- Class PositioningModeSyntax | HiAPI-C# 2025
+ Class PositioningSyntax | HiAPI-C# 2025
-
+
-
+
@@ -84,12 +84,12 @@
-
+
-
-Class PositioningModeSyntax
+
+Class PositioningSyntax
@@ -98,8 +98,9 @@ Class PositioningModeSyntax
Detects G90/G91 positioning mode from Flags
-(or by modal lookback) and writes
-PositioningMode to the block JSON.
+(or by modal lookback) and writes a Positioning section
+(Term, Mode)
+to the block JSON.
Fanuc/ISO: reads G90/G91 from Flags (global modal).
Heidenhain: would need a separate implementation reading I-prefix per axis.
@@ -115,7 +116,7 @@ their parameters with cycle-specific G91 semantics.
-
public class PositioningModeSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
+
public class PositioningSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
@@ -125,7 +126,7 @@ their parameters with cycle-specific G91 semantics.
@@ -333,9 +335,9 @@ their parameters with cycle-specific G91 semantics.
-
+
-
+
MakeXmlSource(string, string, bool)
@@ -375,7 +377,7 @@ This method may also generate additional resources such as related files.
-
Remarks
+
Remarks
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
The baseDirectory is typically the folder at the nearest configuration file folder.
Since the folder can be moving with the configuration file.
Clears the per-block Vars.Volatile dictionary on blocks that
+triggered program end (M02 / M30, identified by the
+ProgramEnd section written by ProgramEndSyntax).
+
+Real Fanuc clears non-retained common variables (#100-#499) on program
+end + reset; this syntax models that behaviour at the simulator level.
+The clear happens on the same block that carried M02/M30 — the next
+block's VolatileVariableReadingSyntax carry then sees an
+empty dictionary on the predecessor and starts fresh.
+
+
+Pipeline placement: must run after both ProgramEndSyntax
+(which writes the ProgramEnd section this syntax checks)
+and VolatileVariableReadingSyntax (so the carry has
+already happened on this block; this syntax overwrites the result).
+
+
+Retained common variables (#500-#999, owned by
+RetainedCommonVariableTable) are
+untouched — they survive program end on real hardware (NV-RAM).
+Local variables (#1-#33, scope: macro call frame) are also
+untouched here; their lifecycle belongs to G65/G66/M99 push/pop, not
+program end.
+
+
+
+
+
+
public class ProgramEndCleanSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Consumes M02/M30 (program end) from Flags
+and writes IProgramEndDef section.
+
+Downstream syntaxes that need to reset modal state on program end
+(e.g. IsoLocalCoordinateOffsetSyntax for G52 reset)
+should read the ProgramEnd section rather than
+scanning for M30 in Flags directly.
+
+Must be placed before syntaxes that depend on the ProgramEnd section.
+
+
+
+
+
public class ProgramEndSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Consumes M00 (unconditional stop) and M01 (optional stop) from
+Flags and writes a
+IProgramStopDef section on the block that carried the
+flag. Non-modal: the section is written only on the exact block
+where the stop code appears.
+
+Siblings with ProgramEndSyntax (M02/M30) which handles
+end-of-program, not in-program stops.
+
+
+The parsing layer only records NC intent. Whether M01 actually
+pauses the run is a runtime/semantic decision gated by the operator's
+"Optional Stop" switch (analogous to
+IBlockSkipConfig for block skip).
+
+
+
+
+
+
public class ProgramStopSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.ProgramXyzSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.ProgramXyzSyntax.html
index 0a1a13bd..c1a02013 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.ProgramXyzSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.ProgramXyzSyntax.html
@@ -105,7 +105,7 @@ cross-node lookback for last position.
+Two strategies for "what's the program coordinate at a block's
+endpoint?" — both invert an MC value through an
+ProgramToMcTransform chain,
+but they pick the chain from different nodes:
+
+
+By current-state transform
+(ComputeProgramXyzByCurrentTransform(LazyLinkedListNode<SyntaxPiece>, Vec3d)) — modal anchor is
+MachineCoordinateState. Re-expresses an
+MC value (typically a predecessor's modal MC) into the current
+block's program frame using the current block's chain. Suitable for
+chain-change blocks where the spindle physically stays put while the
+chain (G54 swap, G68.2 activation, G43.4 toggle, tool-height change,
+...) re-anchors the program frame; mirrors legacy
+HardNcLine.RebuildProgramXyzByMc.
+
+By corresponding-state transform
+(ComputeProgramXyzByCorrespondingTransform(LazyLinkedListNode<SyntaxPiece>)) — modal
+anchor is ProgramXyz. Recovers the
+program coordinate that nodeCarryingMc was originally commanded
+at, by inverting that same node's own transform on its own MC.
+Suitable for RTCP rotary-dynamic inheritance, where the modal
+invariant is "tool tip in workpiece frame stays put while rotary axes
+turn" — the recovered Vec3d carries forward as the next rotary block's
+modal ProgramXyz unchanged, regardless of how its
+PivotTransform differs.
+
+
+Both strategies yield the same Vec3d when prev and current share the
+same chain modal state; they only diverge across chain boundaries
+(RTCP toggle, coord-system swap, tilt activation) and at rotary motion
+(PivotTransform difference). Pick the wrong one and the result lands
+in a stale frame:
+
+
+Non-RTCP using "corresponding" — leaves the pre-chain-change values,
+so a block emitted right after G43.4 H03 would inherit
+ProgramXyz still in the G49 frame and the next motion's MC.Z drifts
+by the introduced tool-height offset. (This was the 2026-04-25
+SoftNc / HardNc divergence on DemoPmcAirPlane/NC/02-ED6L20.NC.)
+
+RTCP using "current" — double-counts the rotary
+PivotTransform difference, so the inherited workpiece anchor
+rotates by the C delta on every rotary block.
+
+Modal invariant: ProgramXyz carries
+forward (RTCP rotary modal) — the workpiece-frame anchor survives
+downstream rotary motion regardless of how the next block's
+PivotTransform differs, so the next rotary-dynamic block
+can adopt this Vec3d unchanged as its modal ProgramXyz.
+
Strategy: by current-state transform. Re-expresses
+mc into currentNode's program
+frame by inverting currentNode's own
+ProgramToMcTransform
+chain.
+
+Modal invariant: MachineCoordinateState
+carries forward — between the source of mc and
+currentNode, the spindle physically stays put
+while the chain (G54 swap, G68.2 activation, G43.4 toggle,
+tool-height change, ...) re-anchors the program frame. Result is
+the program coordinate that, when transformed by
+currentNode's chain, yields
+mc back.
+
Finds the most recent MachineCoordinateState
XYZABC from previous nodes as DVec3d.
-Point = XYZ (mm), Normal = ABC (radians, converted from degrees in JSON).
-Returns null if no previous position found.
+Point = XYZ (mm), Normal = ABC (radians, converted from degrees in JSON).
+
+XYZ is taken from the first previous block whose MC has any of
+X/Y/Z set (typical motion-emitting block). ABC is then backfilled
+per axis for axes the machine actually has: if the
+XYZ-carrying block lacks a particular rotary value, we continue
+walking back to find the last block that wrote that axis (modal
+rotary state). This matches NC semantics — unchanged rotary axes
+carry forward silently — and prevents NaN rotary deltas from
+stopping ClLinearMotionSemantic's
+duration computation in RTCP contours where the XYZ block right
+before the current one didn't record ABC.
+
+
+axisConfig scopes the rotary-backfill to the
+machine's declared rotary axes (via
+GetRotaryAxes(IMachineAxisConfig)): non-rotary axes stay
+NaN and skip backward walking entirely. When
+axisConfig is null (callers without the
+dependency — e.g. legacy tests), all three A/B/C are attempted,
+matching the pre-axisConfig behaviour.
+
+
+Returns null if no previous MC with XYZ is found at all.
+Axes that have never been set stay NaN.
+
-
public static DVec3d FindPreviousMcXyzabc(LazyLinkedListNode<SyntaxPiece> node)
+
public static DVec3d FindPreviousMcXyzabc(LazyLinkedListNode<SyntaxPiece> node, IMachineAxisConfig axisConfig = null)
Finds the most recent storedProgramXyz
+from previous SyntaxPiece nodes — a raw-value lookback
+that returns whatever was written on disk, without MC-inversion or
+frame-change reconstruction.
@@ -242,9 +485,35 @@ Returns null if no previous position found.
-
Gets the last ProgramXyz using the composed transform found from
-previous nodes (FindPrevious pattern). Use when current node's
-transform is not yet available.
+When prev and current share the same chain modal state both
+strategies agree, so the discriminator only matters at chain
+boundaries / rotary motion.
+
+
+Returns Zero only when no predecessor has a
+usable MC (i.e. the start of the program with no motion emitted).
+
@@ -274,47 +543,6 @@ transform is not yet available.
-
-
-
Gets the last ProgramXyz by finding the last MachineCoordinate from
-backward nodes and inverse-transforming with the given Transformation.
-This handles Transformation changes between blocks correctly.
-
-
-
-
-
public static Vec3d GetLastProgramXyz(LazyLinkedListNode<SyntaxPiece> node, Mat4d currentTransformation)
Reads XYZABC from a MachineCoordinateState
section as DVec3d. Point = XYZ (mm),
Normal = ABC (radians, converted from degrees in JSON).
Missing axes are NaN.
@@ -356,10 +584,88 @@ Returns null if the section doesn't exist or has no XYZ.
Resolves the ProgramXyz at
+node's endpoint — i.e. what
+ProgramXyzBackfillSyntax would write on
+node. Dispatcher; the actual inversion math runs
+inside one of the two strategy helpers documented on the class
+summary:
+Both empty → return null; callers must not fabricate a spurious
+origin on the very first block.
+
+
+Shared by ProgramXyzBackfillSyntax
+(computing the snapshot value to write on node)
+and McAbcXyzFallbackSyntax (computing
+Previous's would-be snapshot
+to inherit on the current rotary-dynamic block — the Logic-stage
+caller cannot read prev's stored ProgramXyz because PostSyntaxs
+run after the whole Logic chain finishes).
+
Item 0 uses ProgramXyz (intermediate point from NC program);
+
Only axes present in the G28 block move to home; others keep previous MC value.
+Item 0 uses ProgramXyz (intermediate point from NC program);
McXyzSyntax derives its MachineCoordinate.
-Item 1 uses MachineCoordinate directly (reference point from config).
-Root ProgramXyz is overwritten to the reference position;
+Item 1 uses MachineCoordinate directly (selective home per axis).
+Root ProgramXyz is overwritten to the final position;
McXyzSyntax derives the root MachineCoordinate.
@@ -287,7 +288,8 @@ Root ProgramXyz is overwritten to the reference position;
-
+
Syntax kind name (typically the concrete type name).
Obtains values for Fanuc-style retained common variables (#500-#999)
+by consuming literal numeric assignments from Parsing.Assignments.#nnn
+and writing them straight to a registered
+RetainedCommonVariableTable.
+
+No SyntaxPiece JSON mirror is created — the table is the single source of
+truth for retained values, and VariableEvaluatorSyntax reads
+from the table directly. The hincproj round-trip preserves writes across
+project sessions.
+
+
+Only literal numeric RHS values are consumed by this syntax
+(#500 = 1.234 ✓; #600 = #500 + 1 ✗). Non-literal RHS entries
+are left untouched in Parsing.Assignments; VariableEvaluatorSyntax
+resolves them and writes the result through the same table. The two
+syntaxes are decoupled.
+
+
+If no RetainedCommonVariableTable is registered on the
+runner's NcDependencyList, this syntax is a no-op.
+
+
+
+
+
+
public class RetainedCommonVariableReadingSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.RotaryAxisUtil.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.RotaryAxisUtil.html
index cde768d1..9097a181 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.RotaryAxisUtil.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.RotaryAxisUtil.html
@@ -158,8 +158,8 @@ and other syntaxes that read or write rotary axis values.
-
@@ -167,11 +167,18 @@ and other syntaxes that read or write rotary axis values.
Post-processor hints (e.g., A/B/C on G68.2 or G53.1 lines) are
parsed by FloatTagSetupSyntax into Parsing as doubles.
Returns the value and removes the key, or null if not present.
+
+A non-numeric value (e.g. "#124" left by the parser stage)
+raises VariableExpression--Unevaluated via
+GetParsedDouble(JsonObject, string, Sentence, NcDiagnosticProgress) instead of silently dropping
+the post-processor hint. The key is consumed regardless so downstream
+syntaxes do not re-process it.
+
-
public static double? ConsumeAxis(JsonObject parsing, string axisName)
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.Siemens.SiemensCoordinateOffsetSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.Siemens.SiemensCoordinateOffsetSyntax.html
index fe26b55e..dd08c944 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.Siemens.SiemensCoordinateOffsetSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.Siemens.SiemensCoordinateOffsetSyntax.html
@@ -258,7 +258,8 @@ composes into
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.SpindleSpeedSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.SpindleSpeedSyntax.html
index f252ff8d..f36f0ca0 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.SpindleSpeedSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.SpindleSpeedSyntax.html
@@ -259,7 +259,8 @@ Direction is converted from ISO M-codes to the conventional
-
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.TappingCycleSyntax.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.TappingCycleSyntax.html
index 8fe4050a..952e9f61 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.TappingCycleSyntax.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.TappingCycleSyntax.html
@@ -270,7 +270,8 @@ Must be placed after
+
Syntax kind name (typically the concrete type name).
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.TiltTransformUtil.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.TiltTransformUtil.html
index 6b4563a1..ba341ac7 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.TiltTransformUtil.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.TiltTransformUtil.html
@@ -232,7 +232,9 @@ Shared by all tilt syntaxes (G68, G68.2, CYCLE800, PLANE SPATIAL).
-
Composes the tilt rotation into ProgramToMcTransform.
+Tilt is a fixed geometric rotation per block, so the entry is always
+KindStatic.
@@ -266,8 +268,12 @@ Shared by all tilt syntaxes (G68, G68.2, CYCLE800, PLANE SPATIAL).
-
Finds the previous tilt mode from backward nodes.
-Returns null if no tilt section found.
+
Returns the tilt mode written on the immediately previous block, or
+null when none. Each prior block is guaranteed to carry a
+TiltTransform section (LogicSyntax-stage authored,
+or PostSyntax-stage carried by ModalCarrySyntax),
+so a single-step lookup replaces the legacy
+EnumerateBack() walk.
@@ -304,8 +310,8 @@ Returns null if no tilt section found.
-
Finds the previous tilt Mat4d from the ProgramToMcTransform chain.
-Returns identity if not found.
+
Returns the tilt Mat4d stored on the immediately previous
+block's transform list, or Idt when none.
Consumes T (tool number) and M06 (tool change) from
+Parsing.
+T is modal — persists across blocks. M06 triggers the change.
+Writes resolved state to a ToolChange section:
+{ “ToolId”: 1, “IsChange”: true, “Term”: “M06” }.
+TermKey records the trigger command and is only written
+when IsChangeKey is true (i.e. the block actually carried
+the tool-change M code); modal-only blocks omit it.
+
+
+
+
+
public class ToolChangeSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Resolves tool height offset ID to the effective offset value (mm)
-and composes the offset as a translation into the accumulated
+
Resolves ISO tool height offset (G43/G44/G49) to the effective offset
+value (mm) and composes the offset as a translation into the accumulated
ProgramToMcTransform matrix.
-Reads parsed G43/G43.4/G44/G49 flags and H numbers from upstream parsing syntaxes,
-looks up the offset value from IToolOffsetConfig dependency,
-writes the resolved state to a IToolHeightCompensationDef
-section for debuggability, and composes
-ProgramToMcTransform.Trans += toolOrientation * height_mm.
-
-
-The tool orientation direction is read from a "ToolOrientation" key in JSON
-(written by a prior syntax, e.g., ToolOrientationSyntax). If absent, falls back
-to the current ProgramToMcTransform's
-AxialNormal (rotated Z). If no transformation exists yet,
-defaults to UnitZ.
+RTCP modes (G43.4, TRAORI, M128) are handled by separate brand-specific
+syntaxes (e.g., G43p4RtcpSyntax).
Detects the unit-system code (ISO Group 06: G20 inch / G21 metric)
+from Flags and writes a Unit
+section (Term, System).
+Modal — absence of an explicit flag inherits the previous block's
+unit, defaulting to Metric at program start.
+
+The HiNC pipeline works exclusively in millimetres. When
+G20 is detected this syntax emits an
+Unit--InchNotSupported Unsupported Error so upstream callers
+are forced to pre-convert the NC program to metric.
+G21 is accepted as a no-op confirmation of
+the default.
+
+
+
+
+
+
public class UnitModeSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Resolves Custom Macro B variable references and bracket expressions on
+a single block by walking the parser-stage residue and replacing each
+reference with its evaluated numeric value.
+
+Two passes per block:
+
+
+Parsing.Assignments.#nnn entries with a non-literal RHS are
+evaluated in iteration order. Successful results are written to
+Vars.Volatile for #100-#499 or to the registered
+RetainedCommonVariableTable for #500-#999, and the
+entry is removed. Iteration order matters: an earlier RHS may set a
+variable that a later RHS reads. Failures (vacant operand, unsupported
+function, parse error) emit a VariableExpression--Unevaluated
+error and leave the entry in place; out-of-range ids are likewise left
+in place.
+
+Every string-typed value reachable from Parsing.<tag>
+(axis tags, canned-cycle sub-objects like Parsing.G81,
+Parsing.G54.1, etc.) is parsed; on a successful evaluation the
+string is replaced with a numeric JsonValue. Failures
+silently leave the original string and rely on downstream
+GetParsedDouble(JsonObject, string, Sentence, NcDiagnosticProgress) at consumer sites to surface
+VariableExpression--Unevaluated only if the tag is actually read.
+
+
+Lookup chain (first non-null wins):
+
+
Block-local Vars.Local with Previous traceback (#1-#33).
Block-local Vars.Volatile with traceback (#100-#499).
Each IVariableLookup in the runner's NcDependencyList, in registration order (e.g. RetainedCommonVariableTable, FanucParameterTable, FanucToolOffsetTable).
+Each lookup is responsible for its own id-range gating — id ranges are
+not hard-coded inside this syntax. Adding a new variable surface
+(Heidenhain Q parameters, Siemens GUDs, modal G/F/T reads) is additive:
+register an IVariableLookup on a dependency or push an
+IRuntimeVariableLookup onto the per-preset list.
+
+
+
+
+
+
public class VariableEvaluatorSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
Per-preset list of context-sensitive lookups (typically position
+reads that need Previous). Walked
+in list order after all dependency-bound IVariableLookups.
+
+
+
+
+
public List<IRuntimeVariableLookup> RuntimeVariableLookups { get; set; }
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
Obtains values for Fanuc-style non-retained common variables
+(#100-#499). Reads literal numeric assignments from
+Parsing.Assignments.#nnn, dict-merges them with the previous block's
+volatile state, and writes the resulting per-block dictionary into
+Vars.Volatile.
+
+Lifetime is bounded by MachiningSession: within one session the
+dictionary carries forward block-by-block via this syntax; session restart
+abandons the SyntaxPiece JSON dataflow and starts fresh. Program-end
+(M02/M30) clearing is handled by ProgramEndCleanSyntax.
+
+
+Only literal numeric RHS values are consumed by this syntax
+(#124 = 15. ✓; #100 = #1 + 5 ✗). Non-literal RHS entries
+are left untouched in Parsing.Assignments; VariableEvaluatorSyntax
+resolves them and writes the result into the same per-block dictionary.
+The two syntaxes are decoupled — the evaluator's lookup tracebacks via
+SyntaxPiece linkage so it does not depend on having run before
+or after this syntax.
+
+
+
+
+
+
public class VolatileVariableReadingSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.html b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.html
index b940968b..1380d524 100644
--- a/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.html
+++ b/App/wwwroot/HiAPI-docsite/api/Hi.NcParsers.LogicSyntaxs.html
@@ -137,26 +137,21 @@ Must be placed after
Resolves canned cycle parameters for the current block:
-modal repetition detection, G91 incremental-to-absolute conversion,
-and missing-axis fallback from last known position.
+
Resolves the canned-cycle Group-09 state for the current block
+and writes the result to the CannedCycle section.
+
Active cycle (direct G81..G89 or modal repeat): merges
+Parsing overrides with previous-cycle stored params, applies
+G91 incremental-to-absolute conversion and missing-axis fallback,
+writes CannedCycle with Term,
+ReturnMode, and
+Params. The resolved cycle sub-section
+is left in Parsing under the cycle code for downstream cycle
+syntaxes (DrillingCycleSyntax, etc.) to read.
Explicit cancel (G80 flag present on a non-cycle block):
+consumes the G80 flag and writes
+CannedCycle = { Term: "G80" }, acting as a hard
+sentinel for Hi.NcParsers.LogicSyntaxs.CannedCycleSyntaxUtil modal lookback.
No Group-09 activity: leaves the block untouched.
-After this syntax, the cycle sub-section in Parsing
-(e.g., Parsing.G83) contains fully resolved absolute
-coordinates — downstream cycle syntaxes
-(DrillingCycleSyntax, PeckDrillingCycleSyntax)
-can read them directly without incremental or modal logic.
-
-
-For modal repetition (no cycle G-code in the current block),
-merges stored parameters from the previous block's
-CompoundMotion.Hi.NcParsers.LogicSyntaxs.CannedCycleSyntaxUtil.ResolvedParamsKey
-with current-block overrides from Parsing root, removes
-consumed keys from Parsing root, and writes the merged
-section to Parsing under the cycle code key.
-
@@ -167,18 +162,30 @@ the individual cycle syntaxes in the chain.
(ISO G02/G03).
Detects motion mode from Flags, reads
I/J/K center offsets or R radius from Parsing,
-computes arc center in program coordinates, and writes
-IMotionDef + IArcMotionDef data.
+computes arc center in program coordinates, and writes a one-shot
+MotionEvent (form + arc params) plus a modal
+MotionState (Term).
-G02/G03 mode is modal (Group 01) — persists via backward lookback.
-Arc parameters (I/J/K/R) are per-block and must be present
-in every arc block.
+G02/G03 mode is modal (Group 01) — persists across blocks via
+Term. Arc parameters (I/J/K/R) are
+per-block and must be present in every arc block.
Must be placed before LinearMotionSyntax in the
-syntax chain. Both share the Group 01 Hi.Motion slot;
-whichever writes first claims it.
+syntax chain. Both share the Group 01 motion slot; whichever
+writes a MotionEvent first claims it.
Consumes M07 (mist ON), M08 (flood ON), and M09 (coolant OFF) from
+Flags and writes the ICoolantDef
+section with both IsOn (convenience flag)
+and Mode (abstract mode name:
+Flood / Mist /
+Off).
+Modal — persists via backward lookback.
@@ -230,6 +237,39 @@ Reads absolute coordinates from the cycle section, which is
resolved by CannedCycleResolveSyntax before this
syntax runs.
+
+
+The RTCP kinematic rotary part (Pn→MC rigid transform) is orthogonal
+to this syntax and is written by PivotTransformationSyntax
+on every block, because rotary state remains in effect beyond
+the RTCP modal (e.g. a non-RTCP G01 after G49 still
+inherits the last ABC from the program).
+
+G43.4 is used by Fanuc, Mazak, Syntec, and Okuma. Siemens (TRAORI) and
+Heidenhain (M128) are handled by separate syntaxes. Must be placed
+afterToolHeightOffsetSyntax (to override the
+ToolHeightCompensation entry when RTCP is active) and before
+PivotTransformationSyntax (which runs last in the chain).
+
ISO/Fanuc/Mazak/Okuma/Syntec: resolves G54–G59.9 work coordinate offset.
Reads G54/G55/.../G59.9 from Flags,
-looks up offset Vec3d from IsoCoordinateTable dependency,
+looks up offset Vec3d via IIsoCoordinateConfig dependencies
+(e.g. brand parameter table or IsoCoordinateTable),
composes into ProgramToMcTransform.
Modal — active coordinate persists via backward lookback.
Default coordinate ID is set by StaticInitializer.
@@ -347,24 +388,24 @@ Heidenhain equivalent: PLANE SPATIAL (separate syntax).
M30 (program end) → also cancels.
Reads Parsing.G52 (from G52Syntax),
-writes LocalCoordinateOffset section,
-and adds a "LocalCoordinateOffset" entry to the transformation chain.
+writes IsoLocalCoordinateOffset section,
+and adds an "IsoLocalCoordinateOffset" entry to the transformation chain.
Modal — persists via backward lookback until changed or cancelled.
Writes McLinear motion for linear commands
-(ISO G00/G01, Heidenhain L/LN).
-Detects motion mode from Flags, writes
-IMotionDef section when
-MachineCoordinate exists.
+(ISO G00/G01, Heidenhain L/LN). Detects motion mode from
+Flags, writes a one-shot
+MotionEvent section (form + isRapid) plus a modal
+MotionState section (Term) when
+MachineCoordinateState exists on the block.
-Modal — persists across blocks via backward node lookback.
Must be placed after McAbcSyntax in the syntax chain.
@@ -379,7 +420,7 @@ If G91 (incremental) is active, G53 is ignored per ISO standard.
Must be placed beforeProgramXyzSyntax in the
syntax chain. When G53 is active, this syntax consumes X/Y/Z from
Parsing and writes
-MachineCoordinate directly,
+MachineCoordinateState directly,
preventing ProgramXyzSyntax from processing them
as program coordinates.
@@ -389,7 +430,7 @@ as program coordinates.
Only active when IMachineAxisConfig declares rotary axes.
Works for both 3+2-axis (no IMachineKinematics)
and simultaneous 5-axis configurations.
-When MachineCoordinate does not exist
-(e.g., rotary-only blocks like G00 A30. with no X/Y/Z),
-the section is created with XYZ filled from lookback.
+This syntax is intentionally ABC-only. When the block is rotary-only
+(no ProgramXyz, e.g. G00 A30.) the section is created
+with ABC but without X/Y/Z. McAbcXyzFallbackSyntax
+— placed after McXyzSyntax — copies X/Y/Z from the
+previous block's MachineCoordinateState
+to finish the section. Splitting the XYZ fill out lets this syntax
+run beforeMcXyzSyntax (and before
+G43p4RtcpSyntax) without accidentally filling X/Y/Z
+from prev and thereby short-circuiting
+DeriveMcXyz(JsonObject, Mat4d).
+Non-dynamic (no RTCP or RTCP with ABC stable) — the
+programmed tool tip stays put in MC while rotary axes (if any) are
+unchanged, so we simply copy X/Y/Z from the previous block's
+MachineCoordinateState. This matches
+NC modal XYZ carry-forward for rotary-only blocks such as
+G00 A30. (non-RTCP pivoting).
+
+Dynamic (RTCP active + ABC changing) — the programmed tool tip
+must stay fixed in program coordinates while MC XYZ shifts to
+compensate the new rotary state. Looks up the last
+ProgramXyz and re-derives
+MC = inheritedProgramXyz × composedTransform, where the
+composed transform is the block's endpoint chain (now including
+PivotTransformSource as a full
+rotation+translation Mat4d, so the chain already encodes the
+kinematic IK). The carried ProgramXyz is also stamped onto
+the current block so downstream consumers see a consistent
+ProgramXyz + MC pair.
+
+
+Pair with McAbcSyntax, which runs early to write ABC
+but deliberately leaves X/Y/Z empty so McXyzSyntax can
+still derive MC XYZ from ProgramXyz via the transform chain
+when the block carries linear motion. If McXyzSyntax
+has nothing to derive (no ProgramXyz), this syntax completes
+the MC section as described above.
+
+
+Does nothing when the section already carries all three of X/Y/Z
+(normal linear-motion blocks), or when there is no section at all
+(pure parse-only block that introduces no MC). Must be placed
+afterMcXyzSyntax and before
+McAbcCyclicPathSyntax / LinearMotionSyntax.
Consumes G05.1 (high-precision contour / path smoothing) and records
+its modal state. Q1 enables, Q0 disables. The simulation does not alter
+the tool path — this is a controller-internal interpolation black box.
@@ -451,7 +551,7 @@ Cycle sequence (per stroke):
Retraction distance is read from ICannedCycleConfig
-(Fanuc #4002 / Syntec Pr4002, or Generic.FallbackConfig
+(Fanuc #4002 / Syntec Pr4002, or FallbackConfig
fallback).
Writes the PivotTransformSource entry
+into ProgramToMcTransform
+on every block, capturing the Pn→MC kinematic rigid transform
+for the block's endpoint rotary state. Mirrors legacy
+HardNcLine.GetProgramXyz's use of
+McToPn(DVec3d) — without this entry, the
+transform chain would miss the rotary rotation on any block whose
+MachineCoordinate.ABC is non-zero, and McXyzSyntax (and
+ProgramXyzSyntax's inverse lookback) would silently drift.
+
+Scope is not limited to RTCP modal: as long as rotary axes are
+physically at a non-zero position (e.g. after a non-RTCP G00 B90
+plus any subsequent motion), the kinematic chain still contributes a
+non-identity rigid transform that must appear in the endpoint chain.
+G43p4RtcpSyntax is orthogonal and only governs the
+dynamic-rotary KindKey tagging used by
+LinearMotionSyntax to pick the motion form.
+
Detects G90/G91 positioning mode from Flags
-(or by modal lookback) and writes
-PositioningMode to the block JSON.
+(or by modal lookback) and writes a Positioning section
+(Term, Mode)
+to the block JSON.
Fanuc/ISO: reads G90/G91 from Flags (global modal).
Heidenhain: would need a separate implementation reading I-prefix per axis.
@@ -479,6 +628,66 @@ Does NOT convert incremental values — that is handled by
in the syntax chain, after canned cycle syntaxes have consumed
their parameters with cycle-specific G91 semantics.
Clears the per-block Vars.Volatile dictionary on blocks that
+triggered program end (M02 / M30, identified by the
+ProgramEnd section written by ProgramEndSyntax).
+
+Real Fanuc clears non-retained common variables (#100-#499) on program
+end + reset; this syntax models that behaviour at the simulator level.
+The clear happens on the same block that carried M02/M30 — the next
+block's VolatileVariableReadingSyntax carry then sees an
+empty dictionary on the predecessor and starts fresh.
+
+
+Pipeline placement: must run after both ProgramEndSyntax
+(which writes the ProgramEnd section this syntax checks)
+and VolatileVariableReadingSyntax (so the carry has
+already happened on this block; this syntax overwrites the result).
+
+
+Retained common variables (#500-#999, owned by
+RetainedCommonVariableTable) are
+untouched — they survive program end on real hardware (NV-RAM).
+Local variables (#1-#33, scope: macro call frame) are also
+untouched here; their lifecycle belongs to G65/G66/M99 push/pop, not
+program end.
+
Consumes M02/M30 (program end) from Flags
+and writes IProgramEndDef section.
+
+Downstream syntaxes that need to reset modal state on program end
+(e.g. IsoLocalCoordinateOffsetSyntax for G52 reset)
+should read the ProgramEnd section rather than
+scanning for M30 in Flags directly.
+
+Must be placed before syntaxes that depend on the ProgramEnd section.
+
Consumes M00 (unconditional stop) and M01 (optional stop) from
+Flags and writes a
+IProgramStopDef section on the block that carried the
+flag. Non-modal: the section is written only on the exact block
+where the stop code appears.
+
+Siblings with ProgramEndSyntax (M02/M30) which handles
+end-of-program, not in-program stops.
+
+
+The parsing layer only records NC intent. Whether M01 actually
+pauses the run is a runtime/semantic decision gated by the operator's
+"Optional Stop" switch (analogous to
+IBlockSkipConfig for block skip).
+
@@ -491,16 +700,70 @@ cross-node lookback for last position.
+Two strategies for "what's the program coordinate at a block's
+endpoint?" — both invert an MC value through an
+ProgramToMcTransform chain,
+but they pick the chain from different nodes:
+
+
+By current-state transform
+(ComputeProgramXyzByCurrentTransform(LazyLinkedListNode<SyntaxPiece>, Vec3d)) — modal anchor is
+MachineCoordinateState. Re-expresses an
+MC value (typically a predecessor's modal MC) into the current
+block's program frame using the current block's chain. Suitable for
+chain-change blocks where the spindle physically stays put while the
+chain (G54 swap, G68.2 activation, G43.4 toggle, tool-height change,
+...) re-anchors the program frame; mirrors legacy
+HardNcLine.RebuildProgramXyzByMc.
+
+By corresponding-state transform
+(ComputeProgramXyzByCorrespondingTransform(LazyLinkedListNode<SyntaxPiece>)) — modal
+anchor is ProgramXyz. Recovers the
+program coordinate that nodeCarryingMc was originally commanded
+at, by inverting that same node's own transform on its own MC.
+Suitable for RTCP rotary-dynamic inheritance, where the modal
+invariant is "tool tip in workpiece frame stays put while rotary axes
+turn" — the recovered Vec3d carries forward as the next rotary block's
+modal ProgramXyz unchanged, regardless of how its
+PivotTransform differs.
+
+
+Both strategies yield the same Vec3d when prev and current share the
+same chain modal state; they only diverge across chain boundaries
+(RTCP toggle, coord-system swap, tilt activation) and at rotary motion
+(PivotTransform difference). Pick the wrong one and the result lands
+in a stale frame:
+
+
+Non-RTCP using "corresponding" — leaves the pre-chain-change values,
+so a block emitted right after G43.4 H03 would inherit
+ProgramXyz still in the G49 frame and the next motion's MC.Z drifts
+by the introduced tool-height offset. (This was the 2026-04-25
+SoftNc / HardNc divergence on DemoPmcAirPlane/NC/02-ED6L20.NC.)
+
+RTCP using "current" — double-counts the rotary
+PivotTransform difference, so the inherited workpiece anchor
+rotates by the C delta on every rotary block.
+
Obtains values for Fanuc-style retained common variables (#500-#999)
+by consuming literal numeric assignments from Parsing.Assignments.#nnn
+and writing them straight to a registered
+RetainedCommonVariableTable.
+
+No SyntaxPiece JSON mirror is created — the table is the single source of
+truth for retained values, and VariableEvaluatorSyntax reads
+from the table directly. The hincproj round-trip preserves writes across
+project sessions.
+
+
+Only literal numeric RHS values are consumed by this syntax
+(#500 = 1.234 ✓; #600 = #500 + 1 ✗). Non-literal RHS entries
+are left untouched in Parsing.Assignments; VariableEvaluatorSyntax
+resolves them and writes the result through the same table. The two
+syntaxes are decoupled.
+
+
+If no RetainedCommonVariableTable is registered on the
+runner's NcDependencyList, this syntax is a no-op.
+
@@ -564,26 +852,109 @@ Must be placed after ProgramToMcTransform composition.
+
+
Consumes T (tool number) and M06 (tool change) from
+Parsing.
+T is modal — persists across blocks. M06 triggers the change.
+Writes resolved state to a ToolChange section:
+{ “ToolId”: 1, “IsChange”: true, “Term”: “M06” }.
+TermKey records the trigger command and is only written
+when IsChangeKey is true (i.e. the block actually carried
+the tool-change M code); modal-only blocks omit it.
Resolves tool height offset ID to the effective offset value (mm)
-and composes the offset as a translation into the accumulated
+
Resolves ISO tool height offset (G43/G44/G49) to the effective offset
+value (mm) and composes the offset as a translation into the accumulated
ProgramToMcTransform matrix.
-Reads parsed G43/G43.4/G44/G49 flags and H numbers from upstream parsing syntaxes,
-looks up the offset value from IToolOffsetConfig dependency,
-writes the resolved state to a IToolHeightCompensationDef
-section for debuggability, and composes
-ProgramToMcTransform.Trans += toolOrientation * height_mm.
+RTCP modes (G43.4, TRAORI, M128) are handled by separate brand-specific
+syntaxes (e.g., G43p4RtcpSyntax).
+
Detects the unit-system code (ISO Group 06: G20 inch / G21 metric)
+from Flags and writes a Unit
+section (Term, System).
+Modal — absence of an explicit flag inherits the previous block's
+unit, defaulting to Metric at program start.
+
+The HiNC pipeline works exclusively in millimetres. When
+G20 is detected this syntax emits an
+Unit--InchNotSupported Unsupported Error so upstream callers
+are forced to pre-convert the NC program to metric.
+G21 is accepted as a no-op confirmation of
+the default.
+
Resolves Custom Macro B variable references and bracket expressions on
+a single block by walking the parser-stage residue and replacing each
+reference with its evaluated numeric value.
+
+Two passes per block:
+
+
+Parsing.Assignments.#nnn entries with a non-literal RHS are
+evaluated in iteration order. Successful results are written to
+Vars.Volatile for #100-#499 or to the registered
+RetainedCommonVariableTable for #500-#999, and the
+entry is removed. Iteration order matters: an earlier RHS may set a
+variable that a later RHS reads. Failures (vacant operand, unsupported
+function, parse error) emit a VariableExpression--Unevaluated
+error and leave the entry in place; out-of-range ids are likewise left
+in place.
+
+Every string-typed value reachable from Parsing.<tag>
+(axis tags, canned-cycle sub-objects like Parsing.G81,
+Parsing.G54.1, etc.) is parsed; on a successful evaluation the
+string is replaced with a numeric JsonValue. Failures
+silently leave the original string and rely on downstream
+GetParsedDouble(JsonObject, string, Sentence, NcDiagnosticProgress) at consumer sites to surface
+VariableExpression--Unevaluated only if the tag is actually read.
+
+
+Lookup chain (first non-null wins):
+
+
Block-local Vars.Local with Previous traceback (#1-#33).
Block-local Vars.Volatile with traceback (#100-#499).
Each IVariableLookup in the runner's NcDependencyList, in registration order (e.g. RetainedCommonVariableTable, FanucParameterTable, FanucToolOffsetTable).
+Each lookup is responsible for its own id-range gating — id ranges are
+not hard-coded inside this syntax. Adding a new variable surface
+(Heidenhain Q parameters, Siemens GUDs, modal G/F/T reads) is additive:
+register an IVariableLookup on a dependency or push an
+IRuntimeVariableLookup onto the per-preset list.
+
Obtains values for Fanuc-style non-retained common variables
+(#100-#499). Reads literal numeric assignments from
+Parsing.Assignments.#nnn, dict-merges them with the previous block's
+volatile state, and writes the resulting per-block dictionary into
+Vars.Volatile.
+
+Lifetime is bounded by MachiningSession: within one session the
+dictionary carries forward block-by-block via this syntax; session restart
+abandons the SyntaxPiece JSON dataflow and starts fresh. Program-end
+(M02/M30) clearing is handled by ProgramEndCleanSyntax.
-The tool orientation direction is read from a "ToolOrientation" key in JSON
-(written by a prior syntax, e.g., ToolOrientationSyntax). If absent, falls back
-to the current ProgramToMcTransform's
-AxialNormal (rotated Z). If no transformation exists yet,
-defaults to UnitZ.
+Only literal numeric RHS values are consumed by this syntax
+(#124 = 15. ✓; #100 = #1 + 5 ✗). Non-literal RHS entries
+are left untouched in Parsing.Assignments; VariableEvaluatorSyntax
+resolves them and writes the result into the same per-block dictionary.
+The two syntaxes are decoupled — the evaluator's lookup tracebacks via
+SyntaxPiece linkage so it does not depend on having run before
+or after this syntax.
Parses the ISO 6983 / Fanuc Block Delete (a.k.a. Block Skip) prefix
+/ or /N (N = 1..9) at the head of an NC block.
+
+Behaviour:
+
No leading / → no-op, no BlockSkip section
+is written.
/ with IBlockSkipConfig layer OFF (or the
+dependency absent) → prefix is consumed, BlockSkip
+Symbol/Layer recorded
+for audit, Body stays null; the rest of the
+block stays in UnparsedText and parses normally.
/ with layer ON → the remaining block text is moved
+from UnparsedText into Body and
+UnparsedText is cleared. Downstream parsing syntaxes see no
+NC text so they emit nothing; semantics therefore produce no act.
+Must run after comment / CsScript syntaxes so that comments
+(and CsScript embedded in comments) continue to take effect
+regardless of the skip switch.
+
+
+
+
+
+
public class BlockSkipSyntax : ISituNcSyntax, INcSyntax, IMakeXmlSource
For the demand of easy moving source folder (especially project folder) without configuration file path corruption, the relative file path is applied.
+The baseDirectory is typically the folder at the nearest configuration file folder.
+Since the folder can be moving with the configuration file.
In-situ syntax that strips a trailing comment from the NC line: text from a configured
+TailSymbol to end-of-line is moved into Comment on the block JSON.
+
@@ -192,7 +194,8 @@ Class TailCommentSyntax
-
+
Creates syntax with the given tail marker; used from code or tests without XML.
In-situ syntax that strips a trailing comment from the NC line: text from a configured
+TailSymbol to end-of-line is moved into Comment on the block JSON.
Extracts C# script markers from the oral content of a comment.
+PreMarker marks a script that runs before the NC block;
+PostMarker marks a script that runs after.
+The symbols are configurable and serialized to XML.