Machsupport Forum

Mach Discussion => Mach4 General Discussion => Topic started by: ysymidi on February 07, 2018, 11:47:11 AM

Title: M6 Doesn't work...
Post by: ysymidi on February 07, 2018, 11:47:11 AM
Hello Members,

I so much appreciate your help. ;)
I have almost no chance to get a help like this in my country...

I'm trying to run a manual tool change macro in Mach4.

I use ESS + MB2(ver2.0) + 4 step motors(Y axis has 2 motors, I configured B as Y-Slave in ESS plugin, so MACH4 doesn't know there is a slaved motor.)


When I put "T3 M6" in MDI and click on Cycle Start, nothing happens....
And I captured log as below.


Quote
2018-02-08 01:19:05.002 - API: mcCntlMdiExecute(inst = 0, commands = 't2 m6') (Mach4GUI)
2018-02-08 01:19:05.104 - Attempt transition from "Idle" on event "MDI Start" Controller.cpp:1875
2018-02-08 01:19:05.104 - S_IDLE_on_exit
2018-02-08 01:19:05.104 - ACTION_start_mdi
2018-02-08 01:19:05.104 - S_MDI_RUNNING_on_entry
2018-02-08 01:19:05.104 - S_MDI_RUNNING2_on_entry
2018-02-08 01:19:05.105 - Signal id 1114, (Gcode Running), changed from LOW to HIGH.
2018-02-08 01:19:05.115 - Signal id 1121, (Tool Change), changed from LOW to HIGH.
2018-02-08 01:19:05.116 - >>>>> ESS received a Tool Change Required notification.

2018-02-08 01:19:05.120 - >>>>> ESS received a Tool Change Done notification.

2018-02-08 01:19:05.121 - Signal id 1121, (Tool Change), changed from HIGH to LOW.
2018-02-08 01:19:05.121 - >>>>> ESS received a Tool Change Done notification.

2018-02-08 01:19:05.241 - Attempt transition from "MDI Running" on event "Stop" GcodeExec.cpp:1179
2018-02-08 01:19:05.241 - S_MDI_RUNNING2_on_exit
2018-02-08 01:19:05.241 - Signal id 1114, (Gcode Running), changed from HIGH to LOW.
2018-02-08 01:19:05.241 - S_MDI_RUNNING_on_exit
2018-02-08 01:19:05.241 - ACTION_stop
2018-02-08 01:19:05.265 - S_IDLE_on_entry


Following is the code that I want to use with my machine. But nothing happens...
(I got it from DAZ part3 code, and only modified XY position and Spindle On/Off)
Code: [Select]
function M6()
    local inst = mc.mcGetInstance();
    local selectedtool = mc.mcToolGetSelected(inst)
    local currenttool = mc.mcToolGetCurrent(inst)
    local xstart = mc.mcAxisGetPos(inst,0)
    local ystart = mc.mcAxisGetPos(inst,1)

    if selectedtool == currenttool then
    return
    mc.mcCntlSetLastError(inst, "ToolChange Activated But Not Required")
    else
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G0 Z0.0 \n X25.0 Y352.5")
--    wx.wxMessageBox("Please turn off spindle and click ok to continue") --can be removed if required
    RunProbe(currenttool)
    local toolz = mc.mcAxisGetPos(inst,2)
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G0 Z0.0")
    local changetoo = mc.mcToolGetDesc(inst,selectedtool)
    wx.wxMessageBox("Please change to tool number "..selectedtool.." "..changetoo.." and press ok to continue")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G0 X25.0 Y352.5")
    RunProbe(selectedtool)
    mc.mcAxisSetPos(inst, 2 , toolz)
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G0 Z0.0")
--    wx.wxMessageBox("Please turn on spindle and click ok to continue") --can be removed if required
    mc.mcCntlGcodeExecuteWait(inst,"G90 G0 X"..xstart.." Y"..ystart)
    mc.mcToolSetCurrent(inst, selectedtool)
    mc.mcCntlSetLastError(inst, "ToolChange Finished")
    end
end

function RunProbe(tool)
    local inst = mc.mcGetInstance()
    toollen = mc.mcToolGetData(inst, mc.MTOOL_MILL_HEIGHT, tool)
    if toollen == 0 then toollen = 50 end -- User Preference
    mc.mcCntlSetLastError(inst, "Changing to Fallback Length")
    local probestart = -60 + toollen
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G0 Z"..probestart.."\nG91 G31 Z-60 F100")
end

if (mc.mcInEditor() == 1) then
    M6()
end





I don't think Mach4 correctly recognizes selectedtool and currenttool.
So... if I just get rid of the lines concerning selectedtool and currenttool from the code. M6 works...
But it always say... "Please change to tool number 2 and press OK to continue." always... number 2...... I don't know why...
This is always the same whatever tool number I put, such as T3, T4, T5.....

Code: [Select]
function m6()
    local inst = mc.mcGetInstance();
    local xstart = mc.mcAxisGetPos(inst,0)
    local ystart = mc.mcAxisGetPos(inst,1)
    local guesslen = -100
    local selectedtool = mc.mcToolGetSelected(inst)
    local currenttool = mc.mcToolGetCurrent(inst)
    local toollen = mc.mcToolGetData(inst, mc.MTOOL_MILL_HEIGHT, currenttool)
    if toollen == 0 then toollen = 50 end
    local probestart = guesslen + toollen

--if selectedtool == currenttool then
--return
mc.mcCntlSetLastError(inst, "Toolchange Activated")
--else
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Z0.000")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 X25.000")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Y352.500")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Z"..probestart)
    mc.mcCntlGcodeExecuteWait(inst,"G91 G31 Z-60 F100")
    local toolz = mc.mcAxisGetPos(inst,2)
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z0.000")
local changetoo = mc.mcToolGetDesc(inst, selectedtool)
wx.wxMessageBox("Please change to tool number "..selectedtool.." "..changetoo.." and press OK to continue")
    currenttool = selectedtool
    toollen = mc.mcToolGetData(inst, mc.MTOOL_MILL_HEIGHT, currenttool)
    if toollen == 0 then toollen = 50 end
    probestart = guesslen + toollen
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 X25.000")
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Y352.500")
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z"..probestart)
    mc.mcCntlGcodeExecuteWait(inst, "G91 G31 Z-60 F100")
    mc.mcAxisSetPos(inst, 2 , toolz)
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z0.000")
    mc.mcCntlGcodeExecuteWait(inst, "G90 G00 Y"..ystart)
    mc.mcCntlGcodeExecuteWait(inst, "G90 G00 X"..xstart)
    mc.mcToolSetCurrent(inst, selectedtool)
mc.mcCntlSetLastError(inst, "Toolchange Finished")
    --wx.wxMessageBox('Toolchange Finished')
end
   
--end


if (mc.mcInEditor() == 1) then
    m6()

end



What should I do....?
I'm desperately hopeless.... ;(
Title: Re: M6 Doesn't work...
Post by: DazTheGas on February 07, 2018, 01:13:26 PM
In the mach4 config/tools section, have you set this to T on M6 line is tool to use??

DazTheGas
Title: Re: M6 Doesn't work...
Post by: ysymidi on February 07, 2018, 01:42:26 PM
I changed the setting as you told me but still nothing happens.
(I closed M4 and re-started it to make it sure the new configuration applied.)


Title: Re: M6 Doesn't work...
Post by: ysymidi on February 07, 2018, 02:00:51 PM
In the mach4 config/tools section, have you set this to T on M6 line is tool to use??

DazTheGas


DAZ,

I you almost solved the problem. ;)

Now I got a Macro that perfectly works..
This is almost the same as the code I followed to your Video Part2.

But.. I don't still understand why the code in Part3 doesn't work....

Code: [Select]
function m6()
    local inst = mc.mcGetInstance();
    local xstart = mc.mcAxisGetPos(inst,0)
    local ystart = mc.mcAxisGetPos(inst,1)
    local guesslen = -100
    local selectedtool = mc.mcToolGetSelected(inst)
    local currenttool = mc.mcToolGetCurrent(inst)
    local toollen = mc.mcToolGetData(inst, mc.MTOOL_MILL_HEIGHT, currenttool)
    if toollen == 0 then toollen = 50 end
    local probestart = guesslen + toollen

    if selectedtool == currenttool then
    return
    mc.mcCntlSetLastError(inst, "Toolchange Activated")
    else
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Z0.000")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 X25.000")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Y352.500")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Z"..probestart)
    mc.mcCntlGcodeExecuteWait(inst,"G91 G31 Z-60 F100")
    local toolz = mc.mcAxisGetPos(inst,2)
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z0.000")
local changetoo = mc.mcToolGetDesc(inst, selectedtool)
wx.wxMessageBox("Please change to tool number "..selectedtool.." "..changetoo.." and press OK to continue")
    currenttool = selectedtool
    toollen = mc.mcToolGetData(inst, mc.MTOOL_MILL_HEIGHT, currenttool)
    if toollen == 0 then toollen = 50 end
    probestart = guesslen + toollen
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 X25.000")
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Y352.500")
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z"..probestart)
    mc.mcCntlGcodeExecuteWait(inst, "G91 G31 Z-60 F100")
    mc.mcAxisSetPos(inst, 2 , toolz)
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z0.000")
    mc.mcCntlGcodeExecuteWait(inst, "G90 G00 Y"..ystart)
    mc.mcCntlGcodeExecuteWait(inst, "G90 G00 X"..xstart)
    mc.mcToolSetCurrent(inst, selectedtool)
mc.mcCntlSetLastError(inst, "Toolchange Finished")
    --wx.wxMessageBox('Toolchange Finished')
end
   
end


if (mc.mcInEditor() == 1) then
    m6()

end
Title: Re: M6 Doesn't work...
Post by: joeaverage on February 07, 2018, 03:30:06 PM
Hi,
if I'm not mistaken it is not permissable to have multiple GcodeExecuteWait() statements one after the other.

You'll have to rewrite them as a single call with line characters beteewn lines.

Craig
Title: Re: M6 Doesn't work...
Post by: Walternut on February 07, 2018, 10:33:15 PM
I do not work as well. What do I need to do to fix it?
Title: Re: M6 Doesn't work...
Post by: joeaverage on February 08, 2018, 01:35:44 AM
Hi,
I haven't really studied the code but I can see that certain parts of it are wrong and will not work. As I posted earlier it is not permissible to have multiple
GcodeExecutWait() statements one after another. I don't know why, I have a guess, but lets not complicate the issue with trying to discern the inner workings
of Lua.

As an example, this section:
Code: [Select]
mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Z0.000")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 X25.000")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Y352.500")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Z"..probestart)
    mc.mcCntlGcodeExecuteWait(inst,"G91 G31 Z-60 F100")

will need to be written:
Code: [Select]
mc.mcCntlGcodeExecuteWait(inst,'g90 g53 g0 z0.0\n
                                      g53 x25\n
                                      g53 y325.5\n
                                      g53 z'..probestart\n..
                                      'g91 g31 z-60 f100')

As you can see I've reduced all of the GcodeExecuteWait() statements to just one by concatenating all the original lines with a '\n', linefeed character.
There are some simplifications that I have made also.
G90 is modal and need not be on every line whereas G53 is not modal and MUST be on every line that you wish it to apply. Likewise G00 is modal and need not be mentioned
on every line although it does no harm. There are some modal commands where that is not the case.
The last thing, that I have used all lowercase...why?. Machs Gcode interpreter when it parses the Gcode presented to it converts all letters to lowercase and also strips
out the leading zero. Thus G00 becomes g0. Under most circumstances Windows is fairly tolerant and no fault is generated but not always. Thus when I code I now
use lowercase without leading zeros and have avoided a few traps. What you choose to do is up to you.

Craig
Title: Re: M6 Doesn't work...
Post by: ysymidi on February 08, 2018, 02:41:20 AM
Hi Craig,

The way it works differs from various versions of LUA.

In my case, multiple GcodeExecutWait() statements perfectly work without any trouble.

Code: [Select]
function m6()
    local inst = mc.mcGetInstance();
    local xstart = mc.mcAxisGetPos(inst,0)
    local ystart = mc.mcAxisGetPos(inst,1)
    local guesslen = -100
    local selectedtool = mc.mcToolGetSelected(inst)
    local currenttool = mc.mcToolGetCurrent(inst)
    local toollen = mc.mcToolGetData(inst, mc.MTOOL_MILL_HEIGHT, currenttool)
    if toollen == 0 then toollen = 50 end
    local probestart = guesslen + toollen

if selectedtool == currenttool then
return
mc.mcCntlSetLastError(inst, "Selected Tool = Current Tool")
else
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Z0.000")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 X25.000 Y352.500")
--    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Y352.500")
    mc.mcCntlGcodeExecuteWait(inst,"G90 G53 G00 Z"..probestart)
    mc.mcCntlGcodeExecuteWait(inst,"G91 G31 Z-60 F100")
    local toolz = mc.mcAxisGetPos(inst,2)
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z0.000")
local changetoo = mc.mcToolGetDesc(inst, selectedtool)
wx.wxMessageBox("Please change to tool number "..selectedtool.." "..changetoo.." and press OK to continue")
    currenttool = selectedtool
    toollen = mc.mcToolGetData(inst, mc.MTOOL_MILL_HEIGHT, currenttool)
    if toollen == 0 then toollen = 50 end
    probestart = guesslen + toollen
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 X25.000 Y352.500")
--    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Y352.500")
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z"..probestart)
    mc.mcCntlGcodeExecuteWait(inst, "G91 G31 Z-60 F100")
    mc.mcAxisSetPos(inst, 2 , toolz)
    mc.mcCntlGcodeExecuteWait(inst, "G90 G53 G00 Z0.000")
    mc.mcCntlGcodeExecuteWait(inst, "G90 G00 X"..xstart.." Y"..ystart)
--    mc.mcCntlGcodeExecuteWait(inst, "G90 G00 Y"..ystart)
    mc.mcToolSetCurrent(inst, selectedtool)
mc.mcCntlSetLastError(inst, "Toolchange Finished")
    --wx.wxMessageBox('Toolchange Finished')
end
   
end


if (mc.mcInEditor() == 1) then
    m6()

end

Above is the code that I use now.


But... for me I got one more need lol~


That is,

When I load the first tool in the beginning of the G codes, I want to make Mach4 memorize the tool height and length(?) automatically.

This will give 2 advantages.

1> I can easily replace a broken tool.
2> I can save time when changing to another tool.


Have you applied this to your code?

Give me some info~ ;)




P.S. M6 Macro code from DAZ video part 3 still doesn't work... I don't know why... But it doesn't matter because it would do the same thing as my M6 code does. ;)
Title: Re: M6 Doesn't work...
Post by: joeaverage on February 08, 2018, 03:27:16 AM
Hi,
I change all tools manually.....so long as Mach pauses for me to change the tool and touch off I'm good...don't need anything else.

I used to have a somewhat more sophisticated m6 routine but it didn't give me any advantage. I still have to clamp the tool in the toolholder so its no
problem for me to touch off either. The biggest crashes I've had is where my brains gone to sleep or I expected some automatic or semi automatic function
to work just so which lulls my brain to sleep....

Craig
Title: Re: M6 Doesn't work...
Post by: thosj on February 08, 2018, 09:29:03 AM
Hi,
I change all tools manually.....so long as Mach pauses for me to change the tool and touch off I'm good...don't need anything else.


Hey Craig,

Minor distraction from the thread  >:D

I'm new to Mach4. When Mach4 is in M6 and pauses waiting for me to change tools, can I jog around, to set a tool, and press Cycle Start and go?

I have a Bridgeport clone, Z is the quill, and A is the knee. So what I like to do is use the A to offset tool lengths!! Not "normal", perhaps, but A has 16" of travel and Z only 4.5" limiting tool lengths in order to stay in the Z axis' constraints doing it the "normal" way.  In Mach3 I had macros to gage tools and move the A axis the amount stored in Tx in the tool table. I haven't figured out how to do this in Mach4, but if I can jog any/all axes while stopped in M6, all I'd need to do is jog the A to the new tool length and go. That would be OK if that's the way it works! I never even THOUGHT about doing that, jogging while stopped in M6, but that's just my narrow vision!!

Thanks,
Tom
Title: Re: M6 Doesn't work...
Post by: joeaverage on February 08, 2018, 12:52:54 PM
Hi,
when executing a manual M6 the macro will have to include a CycleStop or equivalent. The control state then goes to Idle and so you can jog or MDI.
Once you've finished clamping the tool in place you can continue to jog and or MDI. Alternately you could have a screen button that takes you to a touch
off location.

Note that all these jogs, MDIs or Button moves can only occur when the control state is Idle. When you are done hit <cycle start> and the Gcode file takes over,
of course the control state is no longer Idle.

A statement like GcodeExecuteWait() executes its line or lines of code as if they were entered as MDI.

You may have noticed in another thread when I was doing something similar I 'ran aground' where even though the control state was Idle the GcodeExecuteWait()
call didn't progress and would return MERROR_NOT_NOW. Exactly what circumstances that an API fails to progress are not clear to me yet.

What that experience has taught me is that you should always test the return codes of any API if you expect your code to be robust.

Craig
Title: Re: M6 Doesn't work...
Post by: thosj on February 08, 2018, 01:49:52 PM
What is "manual M6"? Something other than an M6 in gcode running?

I understand that if I MDI T2 M6 it will be idle at the end of that. Is that the same in gcode running along, T2 M6 happens, machine stops waiting for me to change the tool, I put in the new tool then I can jog around, set my A, and press cycle start and off she goes?

Perhaps that's gcode behavior since time began, but I've never thought to do it or did it!! Cool if that's they way it works. Maybe you CAN teach a 70 year old dog new tricks.
Title: Re: M6 Doesn't work...
Post by: joeaverage on February 08, 2018, 06:12:08 PM
Hi,
not quite. When Mach encounters an M code in a Gcode job it executes it as Gcode from the interpreter and you will
not be able to jog or MDI while its happening.

If however that macro has a CycleStop command embedded in it it would allow you to jog etc.

'Manual M6' means that the M6 macro contains a CycleStop and requires you to fit the tool and touch off by hand as it were.
Only when you are finished do you <cycle start> and the Gcode interpreter regains control of the motion planner.

Craig