Custom GCode – allow variable substitution inside Tool Change comments

Hi team,

I’ve been experimenting with the Custom GCode “Tool Change” template and ran into a limitation that I think would be a nice quality‑of‑life improvement for anyone running manual tool changes.

Setup

  • Device type: X‑Carve‑style router using GRBL/grblHAL

  • Using MillMage’s Custom GCode device profile

  • gSender as the sender (which displays tool‑change comments nicely in its UI)

My current Tool Change template is:

T{tool} M6 {tool_name} S{spindlespeed}

The Example preview shows:

T3 M6 2F 1/8 Endmill S50

So {tool}, {tool_name}, and {spindlespeed} all substitute correctly in this field.

What I’m trying to do

For manual tool changes, it’s very helpful if the sender UI can show a human‑readable description of the expected tool and RPM at the M6 point. GRBL‑style controllers accept comments in parentheses, so a line like:

T1 M6 (Whiteside RD2100 1/4 Upcut S18300)

is valid and displays perfectly in gSender’s tool‑change UI, telling the operator:

  • Which tool to insert

  • The description of that tool

  • The spindle RPM to dial in manually

If I hand‑edit my GCode to that format, it works exactly as intended.

Where the problem appears

If I try to express this in MillMage’s Tool Change template, for example:

T{tool} M6 ({tool_name} S{spindlespeed})

or split across lines:

T{tool} M6 ({tool_name}
S{spindlespeed})

the Example preview and generated GCode look like:

T3 M6 ({tool_name} S{spindlespeed})

In other words:

  • The parentheses appear correctly,

  • But any variables inside () in this field are not substituted – they’re emitted literally as {tool_name} and {spindlespeed}.

Outside parentheses in Tool Change, the variables work; inside parentheses in Tool Change, they don’t.

Why this matters

This is not a blocker—it’s a “tinkerer / ergonomics” enhancement—but it has real value for manual operators:

  • Comments at the tool‑change point give a clear, at‑a‑glance reminder of which tool and RPM the CAM expects.

  • Senders like gSender surface those comments directly in the UI during an M6, which is ideal when there’s no ATC or when the spindle speed is set by hand.

Right now the only way to get that behavior is to:

  • Let MillMage output a plain T… M6 … line, then

  • Manually edit the GCode to add the comment with expanded text.

Enhancement request

It would be great if the Custom GCode engine for the Tool Change field allowed variable substitution inside comment regions as well, so that templates like:

T{tool} M6 ({tool_name} S{spindlespeed})

could produce:

T3 M6 (2F 1/8 Endmill S50)

That GCode is already valid and works correctly on my controller and sender; the missing piece is just being able to generate it directly from MillMage instead of hand‑editing.

Even if this behavior only applied to the Tool Change field (where comments are commonly used to describe the tool), it would make Custom GCode more expressive for manual workflows without affecting existing templates.

Thanks for considering it—and for MillMage in general. I’m really enjoying CAD/CAM, and this is the kind of small feature that would make it even nicer for users who like to tinker.

I read your posting about 3 times, and it appears the only difference between what you get and what you want is the parenthesis, right?

Pretty much, yes – the only technical difference is the parentheses.

The reason I care about them is that in standard G‑code, anything in ( … ) is a comment, and my sender (gSender) actually surfaces those comments in the UI during a tool change. When I hand‑edit a line like

T1 M6 (Whiteside RD2100 1/4 Upcut S18300)

it runs fine on the controller and gSender shows that text to the operator at the M6 point.

In the Tool Change template, {tool}, {tool_name}, and {spindlespeed} all substitute correctly until they’re inside (), at which point they’re emitted literally. So the enhancement request is just: allow the same variable substitution inside comments in that field, so MillMage can generate the same valid G‑code I can already get by hand‑editing.

Seconding this request.

I’m also doing manual toolchanges.
If I add something like this as my custom gcode for tool change:

M5
; SWAP IN {tool_name}
M0

It will result in exactly that being output to the gcode itself. Macro not filled.
I also tested the () commenting style but it appears that if the macro is inside any form of comment it prevents the macro from filling.

I’m currently working around this by doing

M5
@P SWAP IN {tool_name}
M0

And then manually doing a search-replace in the resulting gcode for @P => ;
In this workflow, the toolname is indeed correctly populated in the gcode but it necessitates a manual extra step.

I’m using Millmage purely for creating the workpaths I then run through UGS on a different pc in the workspace. As such, I’m hoping to keep the gcode files as vanilla as possible.

Also, thanks for the great software. I recently got my first cnc, coming from 3d printing background. Millmage was by far the easiest for me to grok and get productive with.

curious why do you run through ugs , and not MM to your machine

Machine in separate building, pc there is thinkpad x220 running linux mint

I was actually coming here to request this as well - I’ve been testing some of the beta features with multi tool relief/vcarves using the ATC in-house and while it was very easy to customize the toolchange output to include the tool number, neither comment style ; or (…) results in the tool_name getting populated correctly.

Not a blocker, but obviously it’d be nice to be able to include that meta-data.

We do similar on our public toolchange postprocessors for Vectric - any M6 includes the tool name which is populated into gSender on file parse. It’s very handy for not having to cross-reference design vs gcode when setting up tools.

We do not support variables in comments at this time. I’ve put it on the task list for MillMage 1.0

Will MillMage have Custom codes for the pendant or we have to assign the keyboard shortcuts to the keys/knobs?