private bool QueueBeforeIfNeedToSwitchExtruders(string lineIn, string lineNoComment) { // check if there is a travel if (sendState == SendStates.WaitingForMove && activeTool != RequestedTool && // is different than the last extruder set (lineNoComment.StartsWith("G0 ") || lineNoComment.StartsWith("G1 ")) && // is a G1 or G0 (lineNoComment.Contains("X") || lineNoComment.Contains("Y") || lineNoComment.Contains("Z"))) // has a move axis in it { postSwitchLine = lineIn; string beforeGcodeToQueue = ""; switch (RequestedTool) { case 0: beforeGcodeToQueue = printer.Settings.GetValue(SettingsKey.before_toolchange_gcode).Replace("\\n", "\n"); break; case 1: beforeGcodeToQueue = printer.Settings.GetValue(SettingsKey.before_toolchange_gcode_1).Replace("\\n", "\n"); break; } preSwitchPosition = lastDestination.position; if (lastDestination.feedRate != double.PositiveInfinity) { preSwitchFeedRate = lastDestination.feedRate; } else { preSwitchFeedRate = lastSeenFeedRate; } // put together the output we want to send var gcode = new StringBuilder(); if (beforeGcodeToQueue.Trim().Length > 0) { gcode.Append(printer.Settings.ReplaceMacroValues(beforeGcodeToQueue)); } gcode.Append("\n"); ManageCoolDownAndOffTemps(gcode); // send the actual tool change gcode.AppendLine($"T{RequestedTool}"); // send the marker to let us know we have sent the before gcode gcode.AppendLine(completedBeforeGCodeString); queuedCommandsStream.Add(gcode.ToString()); sendState = SendStates.SendingBefore; return(true); } return(false); }
public override string ReadLine() { if (queuedCommands.Count > 0) { return(queuedCommands.Dequeue()); } string lineToSend = base.ReadLine(); if (lineToSend == null) { return(null); } if (lineToSend.EndsWith("; NO_PROCESSING")) { return(lineToSend); } GCodeFile.GetFirstNumberAfter("F", lineToSend, ref lastSeenFeedRate); var requestedToolForTempChange = -1; // if we see a temp command remember what heat we are setting if (lineToSend.StartsWith("M109") || lineToSend.StartsWith("M104")) { int toolTemp = 0; // get the temp we are setting GCodeFile.GetFirstNumberAfter("S", lineToSend, ref toolTemp); // set it to the tool we will be changing to requestedToolForTempChange = RequestedTool; // check if this command contains a tool specification GCodeFile.GetFirstNumberAfter("T", lineToSend, ref requestedToolForTempChange); if (!lineToSend.Contains("; INACTIVE_COOL_DOWN")) { if (targetTemps[requestedToolForTempChange] != toolTemp) { targetTemps[requestedToolForTempChange] = toolTemp; } } } // check if any of the heaters we will be switching to need to start heating ManageReHeating(lineToSend); if (lineToSend == completedBeforeGCodeString && sendState != SendStates.Normal) { activeTool = RequestedTool; sendState = SendStates.Normal; QueueAfterGCode(); } var lineNoComment = lineToSend.Split(';')[0]; if (lineNoComment == "G28" || lineNoComment == "G28 Z0") { sendState = SendStates.Normal; RequestedTool = activeTool = 0; } // if this command is a temperature change request if (requestedToolForTempChange != -1) { if (requestedToolForTempChange != activeTool) { if (DoSmoothieCorrections) { // For smoothie, switch back to the extrude we were using before the temp change (smoothie switches to the specified extruder, marlin repetier do not) queuedCommands.Enqueue($"T{activeTool}"); } var temp = GetNextToolTemp(requestedToolForTempChange); if (temp > 0) { return($"{lineToSend.Substring(0, 4)} T{requestedToolForTempChange} S{temp}"); } else // send the temp as requested { return(lineToSend); } } // if we are waiting to switch to the next tool else if (activeTool != RequestedTool) { // if this command does not include the extruder to switch to, than we need to switch before sending it if (!lineNoComment.Contains("T")) { queuedCommands.Enqueue($"T{RequestedTool}"); } if (DoSmoothieCorrections) { // For smoothie, switch back to the extrude we were using before the temp change (smoothie switches to the specified extruder, marlin repetier do not) queuedCommands.Enqueue($"T{activeTool}"); } // then send the heat command return(lineToSend); } } // if this is a tool change request else if (lineToSend.StartsWith("T")) { int changeCommandTool = -1; if (GCodeFile.GetFirstNumberAfter("T", lineToSend, ref changeCommandTool)) { if (changeCommandTool == activeTool) { if (sendState == SendStates.WaitingForMove) { // we have to switch back to our starting tool without a move // change back to normal processing and don't change tools sendState = SendStates.Normal; var lastRequestedTool = RequestedTool; // set the requested tool RequestedTool = changeCommandTool; // don't send the change we are on the right tool now return($"; switch back without move from T{lastRequestedTool} to T{activeTool}"); } } else // we are switching tools { if (sendState == SendStates.Normal) { sendState = SendStates.WaitingForMove; // set the requested tool RequestedTool = changeCommandTool; // don't queue the tool change until after the before gcode has been sent return($"; waiting for move on T{RequestedTool}"); } } } } // if it is only an extrusion move if (sendState == SendStates.WaitingForMove && activeTool != RequestedTool && // is different than the last extruder set (lineNoComment.StartsWith("G0 ") || lineNoComment.StartsWith("G1 ")) && // is a G1 or G0 lineNoComment.Contains("E") // it is an extrusion move // and have no other position information && !lineNoComment.Contains("X") && !lineNoComment.Contains("Y") && !lineNoComment.Contains("Z")) { double ePosition = 0; if (GCodeFile.GetFirstNumberAfter("E", lineNoComment, ref ePosition)) { // switch extruders queuedCommands.Enqueue($"T{RequestedTool}"); if (DoSmoothieCorrections) { // if we know the current E position before the switch // set the E value to the previous E value. if (lastDestination.extrusion != double.PositiveInfinity) { // On Marlin E position is shared between extruders and this code has no utility // On Smoothie E is stored per extruder and this makes it behave the same as Marlin queuedCommands.Enqueue($"G92 E{lastDestination.extrusion}"); } } // send the extrusion queuedCommands.Enqueue(lineNoComment + " ; NO_PROCESSING"); lastDestination.extrusion = ePosition; if (DoSmoothieCorrections) { // switch back queuedCommands.Enqueue($"T{activeTool}"); queuedCommands.Enqueue($"G92 E{lastDestination.extrusion}"); } return(""); } } if (QueueBeforeIfNeedToSwitchExtruders(lineToSend, lineNoComment)) { return(""); } if (LineIsMovement(lineToSend)) { lastDestination = GetPosition(lineToSend, lastDestination); } return(lineToSend); }
public override string ReadLine() { string lineToSend = base.ReadLine(); if (lineToSend == null) { return(null); } if (lineToSend.EndsWith("; NO_PROCESSING")) { return(lineToSend); } // check if any of the heaters we will be switching to need to start heating ManageReHeating(lineToSend); if (lineToSend == compleatedBeforeGCodeString) { activeTool = requestedTool; SendState = SendStates.Normal; QueueAfterGCode(); } // track the tool state if (lineToSend.StartsWith("T")) { int changeCommandTool = -1; if (GCodeFile.GetFirstNumberAfter("T", lineToSend, ref changeCommandTool) && changeCommandTool != activeTool) { requestedTool = changeCommandTool; if (SendState == SendStates.Normal) { SendState = SendStates.WaitingForMove; // don't queue the tool change until after the before gcode has been sent return($"; waiting for move on T{requestedTool}"); } } } // check if there is a temperature change request else if (lineToSend.StartsWith("M104") || lineToSend.StartsWith("M109")) { double toolBeingSet = -1; // if there is a tool specification if (GCodeFile.GetFirstNumberAfter("T", lineToSend, ref toolBeingSet)) { if (toolBeingSet != activeTool) { // For smoothie, switch back to the extrude we were using before the temp change (smoothie switches to the specified extruder, marlin repetier do not) queuedCommandsStream.Add("T{0} ; NO_PROCESSING".FormatWith(activeTool)); } } } if (QueueBeforeIfNeedToSwitchExtruders(lineToSend)) { return(""); } if (LineIsMovement(lineToSend)) { lastDestination = GetPosition(lineToSend, lastDestination); } return(lineToSend); }