public override RobotProgram UNSAFEFullProgramFromBuffer(string programName, RobotCursor writer, bool block, bool inlineTargets, bool humanComments) { // The program files to be returned RobotProgram robotProgram = new RobotProgram(programName, CC); // Which pending Actions are used for this program? // Copy them without flushing the buffer. List <Action> actions = block ? writer.actionBuffer.GetBlockPending(false) : writer.actionBuffer.GetAllPending(false); // ACTION LINES GENERATION List <string> actionLines = new List <string>(); // DATA GENERATION // Use the write RobotCursor to generate the data int it = 0; string line = null; foreach (Action a in actions) { // Move writerCursor to this action state writer.ApplyNextAction(); // for the buffer to correctly manage them line = string.Format("[{0}] {1}", it, a.ToString()); actionLines.Add(line); // Move on it++; } // PROGRAM ASSEMBLY // Initialize a module list List <string> module = new List <string>(); // Banner module.AddRange(GenerateDisclaimerHeader(programName)); module.Add(""); // Code lines module.AddRange(actionLines); // MAIN file RobotProgramFile pFile = new RobotProgramFile(programName, "txt", Encoding, CC); pFile.SetContent(module); robotProgram.Add(pFile); return(robotProgram); }
public override List <string> UNSAFEProgramFromBuffer(string programName, RobotCursor writer, bool block, bool inlineTargets, bool humanComments) { // Which pending Actions are used for this program? // Copy them without flushing the buffer. List <Action> actions = block ? writer.actionBuffer.GetBlockPending(false) : writer.actionBuffer.GetAllPending(false); // ACTION LINES GENERATION List <string> actionLines = new List <string>(); // DATA GENERATION // Use the write RobotCursor to generate the data int it = 0; string line = null; foreach (Action a in actions) { // Move writerCursor to this action state writer.ApplyNextAction(); // for the buffer to correctly manage them line = a.ToInstruction(); actionLines.Add(line); // Move on it++; } // PROGRAM ASSEMBLY // Initialize a module list List <string> module = new List <string>(); // Banner module.AddRange(GenerateDisclaimerHeader(programName)); module.Add(""); // Code lines module.AddRange(actionLines); return(module); }
/// <summary> /// Creates a textual program representation of a set of Actions using native RAPID Laguage. /// WARNING: this method is EXTREMELY UNSAFE; it performs no IK calculations, assigns default [0,0,0,0] /// robot configuration and assumes the robot controller will figure out the correct one. /// </summary> /// <param name="programName"></param> /// <param name="writePointer"></param> /// <param name="block">Use actions in waiting queue or buffer?</param> /// <returns></returns> //public override List<string> UNSAFEProgramFromBuffer(string programName, RobotCursor writePointer, bool block) public override RobotProgram UNSAFEFullProgramFromBuffer(string programName, RobotCursor writer, bool block, bool inlineTargets, bool humanComments) { // The program files to be returned RobotProgram robotProgram = new RobotProgram(programName, CC); // HEADER file RobotProgramFile pgfFile = new RobotProgramFile(programName, "pgf", Encoding, CC); List <string> header = new List <string>(); header.Add("<?xml version=\"1.0\" encoding=\"ISO-8859-1\" ?>"); header.Add("<Program>"); header.Add($" <Module>{programName}.mod</Module>"); header.Add("</Program>"); pgfFile.SetContent(header); robotProgram.Add(pgfFile); // PROGRAM FILE addActionString = humanComments; // Which pending Actions are used for this program? // Copy them without flushing the buffer. List <Action> actions = block ? writer.actionBuffer.GetBlockPending(false) : writer.actionBuffer.GetAllPending(false); // CODE LINES GENERATION // VELOCITY & ZONE DECLARATIONS // Amount of different VZ types var velNames = new Dictionary <double, string>(); var velDecs = new Dictionary <double, string>(); var zoneNames = new Dictionary <double, string>(); var zoneDecs = new Dictionary <double, string>(); var zonePredef = new Dictionary <double, bool>(); // TOOL DECLARATIONS Dictionary <Tool, string> toolNames = new Dictionary <Tool, string>(); Dictionary <Tool, string> toolDecs = new Dictionary <Tool, string>(); // Intro List <string> introLines = new List <string>(); // Declarations List <string> velocityLines = new List <string>(); List <string> zoneLines = new List <string>(); List <string> toolLines = new List <string>(); List <string> customLines = new List <string>(); // TARGETS AND INSTRUCTIONS List <string> variableLines = new List <string>(); List <string> instructionLines = new List <string>(); // DATA GENERATION // Use the write robot pointer to generate the data int it = 0; string line = null; bool usesIO = false; foreach (Action a in actions) { // Move writerCursor to this action state writer.ApplyNextAction(); // for the buffer to correctly manage them // For ABB robots, check if any IO command is issued, and display a warning about configuring their names in the controller. if (!usesIO && (writer.lastAction.Type == ActionType.IODigital || writer.lastAction.Type == ActionType.IOAnalog)) { usesIO = true; } // Check velocity + zone and generate data accordingly if (!velNames.ContainsKey(writer.speed)) { velNames.Add(writer.speed, "vel" + SafeDoubleName(writer.speed)); velDecs.Add(writer.speed, GetSpeedValue(writer)); } if (!zoneNames.ContainsKey(writer.precision)) { // If precision is very close to an integer, make it integer and/or use predefined zones bool predef = false; int roundZone = 0; if (Math.Abs(writer.precision - Math.Round(writer.precision)) < Geometry.EPSILON) { roundZone = (int)Math.Round(writer.precision); predef = PredefinedZones.Contains(roundZone); } zonePredef.Add(writer.precision, predef); zoneNames.Add(writer.precision, predef ? "z" + roundZone : "zone" + SafeDoubleName(writer.precision)); // use predef syntax or clean new one zoneDecs.Add(writer.precision, predef ? "" : GetZoneValue(writer)); } if (writer.tool != null && !toolNames.ContainsKey(writer.tool)) { toolNames.Add(writer.tool, writer.tool.name); toolDecs.Add(writer.tool, GetToolValue(writer)); } if (a.Type == ActionType.CustomCode && (a as ActionCustomCode).isDeclaration) { customLines.Add($" {(a as ActionCustomCode).statement}"); } // Generate program if (inlineTargets) { // Generate lines of code if (GenerateInstructionDeclaration(a, writer, velNames, zoneNames, toolNames, out line)) { instructionLines.Add(line); } } else { // Generate lines of code if (GenerateVariableDeclaration(a, writer, it, out line)) // there will be a number jump on target-less instructions, but oh well... { variableLines.Add(line); } if (GenerateInstructionDeclarationFromVariable(a, writer, it, velNames, zoneNames, toolNames, out line)) // there will be a number jump on target-less instructions, but oh well... { instructionLines.Add(line); } } // Move on it++; } // Generate V+Z+T foreach (Tool t in toolNames.Keys) { toolLines.Add(string.Format(CultureInfo.InvariantCulture, " PERS tooldata {0} := {1};", toolNames[t], toolDecs[t])); } foreach (var v in velNames.Keys) { velocityLines.Add(string.Format(CultureInfo.InvariantCulture, " CONST speeddata {0} := {1};", velNames[v], velDecs[v])); } foreach (var z in zoneNames.Keys) { if (!zonePredef[z]) // no need to add declarations for predefined zones { zoneLines.Add(string.Format(CultureInfo.InvariantCulture, " CONST zonedata {0} := {1};", zoneNames[z], zoneDecs[z])); } } // Generate IO warning if (usesIO) { introLines.Add(string.Format(" {0} NOTE: your program is interfacing with the robot's IOs. Make sure to properly configure their names/properties through system preferences in the ABB robot controller.", CC)); } // PROGRAM ASSEMBLY // Initialize a module list List <string> module = new List <string>(); // MODULE HEADER module.Add("MODULE " + programName); module.Add(""); // Banner (must go after MODULE, or will yield RAPID syntax errors) module.AddRange(GenerateDisclaimerHeader(programName)); module.Add(""); // INTRO LINES if (introLines.Count != 0) { module.AddRange(introLines); module.Add(""); } // VARIABLE DECLARATIONS // Tools if (toolLines.Count != 0) { module.AddRange(toolLines); module.Add(""); } // Velocities if (velocityLines.Count != 0) { module.AddRange(velocityLines); module.Add(""); } // Zones if (zoneLines.Count != 0) { module.AddRange(zoneLines); module.Add(""); } // Custom code if (customLines.Count != 0) { module.AddRange(customLines); module.Add(""); } // Targets if (variableLines.Count != 0) { module.AddRange(variableLines); module.Add(""); } // MAIN PROCEDURE module.Add(" PROC main()"); module.Add(@" ConfJ \Off;"); module.Add(@" ConfL \Off;"); module.Add(""); // Instructions if (instructionLines.Count != 0) { module.AddRange(instructionLines); module.Add(""); } module.Add(" ENDPROC"); module.Add(""); // MODULE FOOTER module.Add("ENDMODULE"); RobotProgramFile modFile = new RobotProgramFile(programName, "mod", Encoding, CC); modFile.SetContent(module); robotProgram.Add(modFile); return(robotProgram); }
/// <summary> /// Creates a textual program representation of a set of Actions using native RAPID Laguage. /// WARNING: this method is EXTREMELY UNSAFE; it performs no IK calculations, assigns default [0,0,0,0] /// robot configuration and assumes the robot controller will figure out the correct one. /// </summary> /// <param name="programName"></param> /// <param name="writePointer"></param> /// <param name="block">Use actions in waiting queue or buffer?</param> /// <returns></returns> //public override List<string> UNSAFEProgramFromBuffer(string programName, RobotCursor writePointer, bool block) public override List <string> UNSAFEProgramFromBuffer(string programName, RobotCursor writer, bool block, bool inlineTargets, bool humanComments) { ADD_ACTION_STRING = humanComments; // Which pending Actions are used for this program? // Copy them without flushing the buffer. List <Action> actions = block ? writer.actionBuffer.GetBlockPending(false) : writer.actionBuffer.GetAllPending(false); // CODE LINES GENERATION // TARGETS AND INSTRUCTIONS this.initializationLines = new List <string>(); this.customDeclarationLines = new List <string>(); this.instructionLines = new List <string>(); this.closingLines = new List <string>(); // --> MOVED TO CUSTOM ACTION `Initialize()` //// SOME INITIAL BOILERPLATE TO HEAT UP THE PRINTER, CALIBRATE IT, ETC. //// ZMorph boilerplate //// HEATUP -> For the user, may not want to use the printer as printer... //initializationLines.Add("M140 S60"); // set bed temp and move on to next inst //initializationLines.Add("M109 S200"); // set extruder bed temp and wait till heat up //initializationLines.Add("M190 S60"); // set bed temp and wait till heat up //// HOMING //this.initializationLines.Add("G91"); // set rel motion //this.initializationLines.Add("G1 Z1.000 F200.000"); // move up 1mm and accelerate printhead to 200 mm/min //this.initializationLines.Add("G90"); // set absolute positioning //this.initializationLines.Add("G28 X0.000 Y0.00"); // home XY axes //this.initializationLines.Add("G1 X117.500 Y125.000 F8000.000"); // move to bed center for Z homing //this.initializationLines.Add("G28 Z0.000"); // home Z //this.initializationLines.Add("G92 E0.00000"); // set filament position to zero //// Machina bolierplate //this.initializationLines.Add("M82"); // set extruder to absolute mode (this is actually ZMorph, but useful here //this.initializationLines.Add($"G1 F{Math.Round(writer.speed * 60.0, Geometry.STRING_ROUND_DECIMALS_MM)}"); // initialize feed speed to the writer's state this.initializationLines.AddRange(GenerateDisclaimerHeader(programName)); // DATA GENERATION // Use the write RobotCursor to generate the data //int it = 0; string line = null; foreach (Action a in actions) { // Move writerCursor to this action state writer.ApplyNextAction(); // for the buffer to correctly manage them if (a.Type == ActionType.CustomCode && (a as ActionCustomCode).isDeclaration) { customDeclarationLines.Add((a as ActionCustomCode).statement); } // GCode is super straightforward, so no need to pre-declare anything if (GenerateInstructionDeclaration(a, writer, out line)) { this.instructionLines.Add(line); } //// Move on //it++; } // --> MOVED TO CUSTOM ACTION `Terminate()` //// END THE PROGRAM AND LEAVE THE PRINTER READY //// ZMorph boilerplate //this.closingLines.Add("G92 E0.0000"); //this.closingLines.Add("G91"); //this.closingLines.Add("G1 E-3.00000 F1800.000"); //this.closingLines.Add("G90"); //this.closingLines.Add("G92 E0.00000"); //this.closingLines.Add("G1 X117.500 Y220.000 Z30.581 F300.000"); //this.closingLines.Add("T0"); // choose tool 0: is this for multihead? //this.closingLines.Add("M104 S0"); // set extruder temp and move on //this.closingLines.Add("T1"); // choose tool 1 //this.closingLines.Add("M104 S0"); // ibid //this.closingLines.Add("M140 S0"); // set bed temp and move on //this.closingLines.Add("M106 S0"); // fan speed 0 (off) //this.closingLines.Add("M84"); // stop idle hold (?) //this.closingLines.Add("M220 S100"); // set speed factor override percentage // PROGRAM ASSEMBLY // Initialize a module list List <string> module = new List <string>(); // Initializations if (this.initializationLines.Count != 0) { module.AddRange(this.initializationLines); module.Add(""); } // Custom declarations if (this.customDeclarationLines.Count != 0) { module.AddRange(this.customDeclarationLines); module.Add(""); } // MAIN PROCEDURE // Instructions if (this.instructionLines.Count != 0) { module.AddRange(this.instructionLines); module.Add(""); } // Wrapping up if (this.closingLines.Count != 0) { module.AddRange(this.closingLines); module.Add(""); } return(module); }
/// <summary> /// Creates a textual program representation of a set of Actions using native KUKA Robot Language. /// </summary> /// <param name="programName"></param> /// <param name="writePointer"></param> /// <param name="block">Use actions in waiting queue or buffer?</param> /// <returns></returns> //public override List<string> UNSAFEProgramFromBuffer(string programName, RobotCursor writePointer, bool block) public override List <string> UNSAFEProgramFromBuffer(string programName, RobotCursor writer, bool block, bool inlineTargets, bool humanComments) { ADD_ACTION_STRING = humanComments; // Which pending Actions are used for this program? // Copy them without flushing the buffer. List <Action> actions = block ? writer.actionBuffer.GetBlockPending(false) : writer.actionBuffer.GetAllPending(false); // CODE LINES GENERATION // TARGETS AND INSTRUCTIONS List <string> declarationLines = new List <string>(); List <string> customDeclarationLines = new List <string>(); List <string> initializationLines = new List <string>(); List <string> instructionLines = new List <string>(); //KUKA INITIALIZATION BOILERPLATE declarationLines.Add(" ; @TODO: consolidate all same datatypes into single inline declarations..."); declarationLines.Add(" EXT BAS (BAS_COMMAND :IN, REAL :IN)"); // import BAS sys function initializationLines.Add(" GLOBAL INTERRUPT DECL 3 WHEN $STOPMESS==TRUE DO IR_STOPM()"); // legacy support for user-programming safety initializationLines.Add(" INTERRUPT ON 3"); initializationLines.Add(" BAS (#INITMOV, 0)"); // use base function to initialize sys vars to defaults initializationLines.Add(""); initializationLines.Add(" $TOOL = {X 0, Y 0, Z 0, A 0, B 0, C 0}"); // no tool initializationLines.Add(" $LOAD.M = 0"); // no mass initializationLines.Add(" $LOAD.CM = {X 0, Y 0, Z 0, A 0, B 0, C 0}"); // no CoG // DATA GENERATION // Use the write RobotCursor to generate the data int it = 0; string line = null; foreach (Action a in actions) { // Move writerCursor to this action state writer.ApplyNextAction(); // for the buffer to correctly manage them if (a.type == ActionType.CustomCode && (a as ActionCustomCode).isDeclaration) { customDeclarationLines.Add(" " + (a as ActionCustomCode).statement); } if (inlineTargets) { if (GenerateInstructionDeclaration(a, writer, out line)) { instructionLines.Add(line); } } else { if (GenerateVariableDeclaration(a, writer, it, out line)) // there will be a number jump on target-less instructions, but oh well... { declarationLines.Add(line); } if (GenerateVariableInitialization(a, writer, it, out line)) { initializationLines.Add(line); } if (GenerateInstructionDeclarationFromVariable(a, writer, it, out line)) // there will be a number jump on target-less instructions, but oh well... { instructionLines.Add(line); } } // Move on it++; } // PROGRAM ASSEMBLY // Initialize a module list List <string> module = new List <string>(); // Banner module.AddRange(GenerateDisclaimerHeader(programName)); module.Add(""); // SOME INTERFACE INITIALIZATION // These are all for interface handling, ignored by the compiler (?) module.Add(@"&ACCESS RVP"); // read-write permissions module.Add(@"&REL 1"); // release number (increments on file changes) module.Add(@"&COMMENT MACHINA PROGRAM"); module.Add(@"&PARAM TEMPLATE = C:\KRC\Roboter\Template\vorgabe"); module.Add(@"&PARAM EDITMASK = *"); module.Add(""); // MODULE HEADER module.Add("DEF " + programName + "()"); module.Add(""); // Declarations if (declarationLines.Count != 0) { module.AddRange(declarationLines); module.Add(""); } // Custom declarations if (customDeclarationLines.Count != 0) { module.AddRange(customDeclarationLines); module.Add(""); } // Initializations if (initializationLines.Count != 0) { module.AddRange(initializationLines); module.Add(""); } // MAIN PROCEDURE // Instructions if (instructionLines.Count != 0) { module.AddRange(instructionLines); module.Add(""); } module.Add("END"); module.Add(""); //// MODULE KICKOFF //module.Add(programName + "()"); // no need for this in KRL if file name is same as module name --> what if user exports them with different names? return(module); }
/// <summary> /// Creates a textual program representation of a set of Actions using native UR Script. /// </summary> /// <param name="programName"></param> /// <param name="writePointer"></param> /// <param name="block">Use actions in waiting queue or buffer?</param> /// <returns></returns> public override RobotProgram UNSAFEFullProgramFromBuffer(string programName, RobotCursor writer, bool block, bool inlineTargets, bool humanComments) { // The program files to be returned RobotProgram robotProgram = new RobotProgram(programName, CC); // Which pending Actions are used for this program? // Copy them without flushing the buffer. List <Action> actions = block ? writer.actionBuffer.GetBlockPending(false) : writer.actionBuffer.GetAllPending(false); // CODE LINES GENERATION // TARGETS AND INSTRUCTIONS List <string> customDeclarationLines = new List <string>(); List <string> variableLines = new List <string>(); List <string> instructionLines = new List <string>(); // DATA GENERATION // Use the write RobotCursor to generate the data int it = 0; string line = null; foreach (Action a in actions) { // Move writerCursor to this action state writer.ApplyNextAction(); // for the buffer to correctly manage them if (a.Type == ActionType.CustomCode && (a as ActionCustomCode).isDeclaration) { customDeclarationLines.Add(" " + (a as ActionCustomCode).statement); } if (inlineTargets) { if (GenerateInstructionDeclaration(a, writer, humanComments, out line)) // there will be a number jump on target-less instructions, but oh well... { instructionLines.Add(line); } } else { // Generate lines of code if (GenerateVariableDeclaration(a, writer, it, out line)) // there will be a number jump on target-less instructions, but oh well... { variableLines.Add(line); } if (GenerateInstructionDeclarationFromVariable(a, writer, it, humanComments, out line)) // there will be a number jump on target-less instructions, but oh well... { instructionLines.Add(line); } } // Move on it++; } // PROGRAM ASSEMBLY // Initialize a module list List <string> module = new List <string>(); // Banner module.AddRange(GenerateDisclaimerHeader(programName)); module.Add(""); // MODULE HEADER module.Add("def " + programName + "():"); module.Add(""); // Custom declarations if (customDeclarationLines.Count != 0) { module.AddRange(customDeclarationLines); module.Add(""); } // Targets if (variableLines.Count != 0) { module.AddRange(variableLines); module.Add(""); } // MAIN PROCEDURE // Instructions if (instructionLines.Count != 0) { module.AddRange(instructionLines); module.Add(""); } module.Add("end"); module.Add(""); // MODULE KICKOFF module.Add(programName + "()"); RobotProgramFile mainFile = new RobotProgramFile(programName, "script", Encoding, CC); mainFile.SetContent(module); robotProgram.Add(mainFile); return(robotProgram); }
/// <summary> /// Creates a textual program representation of a set of Actions using native UR Script. /// </summary> /// <param name="programName"></param> /// <param name="writePointer"></param> /// <param name="block">Use actions in waiting queue or buffer?</param> /// <returns></returns> public override List <string> UNSAFEProgramFromBuffer(string programName, RobotCursor writer, bool block, bool inlineTargets, bool humanComments) { // @TODO: deprecate all instantiation shit, and make compilers be mostly static //ADD_ACTION_STRING = humanComments; // Which pending Actions are used for this program? // Copy them without flushing the buffer. List <Action> actions = block ? writer.actionBuffer.GetBlockPending(false) : writer.actionBuffer.GetAllPending(false); // CODE LINES GENERATION // TARGETS AND INSTRUCTIONS List <string> variableLines = new List <string>(); List <string> instructionLines = new List <string>(); // DATA GENERATION // Use the write RobotCursor to generate the data int it = 0; string line = null; foreach (Action a in actions) { // Move writerCursor to this action state writer.ApplyNextAction(); // for the buffer to correctly manage them if (inlineTargets) { if (GenerateInstructionDeclaration(a, writer, humanComments, out line)) // there will be a number jump on target-less instructions, but oh well... { instructionLines.Add(line); } } else { // Generate lines of code if (GenerateVariableDeclaration(a, writer, it, out line)) // there will be a number jump on target-less instructions, but oh well... { variableLines.Add(line); } if (GenerateInstructionDeclarationFromVariable(a, writer, it, humanComments, out line)) // there will be a number jump on target-less instructions, but oh well... { instructionLines.Add(line); } } // Move on it++; } // PROGRAM ASSEMBLY // Initialize a module list List <string> module = new List <string>(); // Banner module.AddRange(GenerateDisclaimerHeader(programName)); module.Add(""); // MODULE HEADER module.Add("def " + programName + "():"); module.Add(""); // Targets if (variableLines.Count != 0) { module.AddRange(variableLines); module.Add(""); } // MAIN PROCEDURE // Instructions if (instructionLines.Count != 0) { module.AddRange(instructionLines); module.Add(""); } module.Add("end"); module.Add(""); // MODULE KICKOFF module.Add(programName + "()"); return(module); }
/// <summary> /// Creates a textual program representation of a set of Actions using native KUKA Robot Language. /// </summary> /// <param name="programName"></param> /// <param name="writePointer"></param> /// <param name="block">Use actions in waiting queue or buffer?</param> /// <returns></returns> public override RobotProgram UNSAFEFullProgramFromBuffer(string programName, RobotCursor writer, bool block, bool inlineTargets, bool humanComments) { // The program files to be returned RobotProgram robotProgram = new RobotProgram(programName, CC); // HEADER file RobotProgramFile datFile = new RobotProgramFile(programName, "dat", Encoding, CC); List <string> header = new List <string>(); header.AddRange(GenerateDisclaimerHeader(programName)); header.Add("&ACCESS RVP"); header.Add("& REL 1"); header.Add("& PARAM EDITMASK = *"); header.Add(@"&PARAM TEMPLATE = C:\KRC\Roboter\Template\vorgabe"); header.Add(@"& PARAM DISKPATH = KRC:\R1\Program"); // @TODO: this path should be programmatically generated... header.Add(string.Format("DEFDAT {0}", programName)); header.Add("EXT BAS (BAS_COMMAND: IN, REAL: IN)"); header.Add("DECL INT SUCCESS"); header.Add("ENDDAT"); datFile.SetContent(header); robotProgram.Add(datFile); // PROGRAM FILE addActionString = humanComments; // Which pending Actions are used for this program? // Copy them without flushing the buffer. List <Action> actions = block ? writer.actionBuffer.GetBlockPending(false) : writer.actionBuffer.GetAllPending(false); // CODE LINES GENERATION // TARGETS AND INSTRUCTIONS List <string> declarationLines = new List <string>(); List <string> customDeclarationLines = new List <string>(); List <string> initializationLines = new List <string>(); List <string> instructionLines = new List <string>(); //KUKA INITIALIZATION BOILERPLATE //declarationLines.Add(" ; @TODO: consolidate all same datatypes into single inline declarations..."); //declarationLines.Add(" EXT BAS (BAS_COMMAND :IN, REAL :IN)"); // import BAS sys function --> This needs to move to `.dat` file initializationLines.Add(" GLOBAL INTERRUPT DECL 3 WHEN $STOPMESS==TRUE DO IR_STOPM()"); // legacy support for user-programming safety initializationLines.Add(" INTERRUPT ON 3"); initializationLines.Add(" BAS (#INITMOV, 0)"); // use base function to initialize sys vars to defaults initializationLines.Add(""); // This was reported not to work //initializationLines.Add(" $TOOL = {X 0, Y 0, Z 0, A 0, B 0, C 0}"); // no tool //initializationLines.Add(" $LOAD.M = 0"); // no mass //initializationLines.Add(" $LOAD.CM = {X 0, Y 0, Z 0, A 0, B 0, C 0}"); // no CoG // This was reported to be needed initializationLines.Add(" BASE_DATA[1] = {X 0, Y 0, Z 0, A 0, B 0, C 0}"); // DATA GENERATION // Use the write RobotCursor to generate the data int it = 0; string line = null; foreach (Action a in actions) { // Move writerCursor to this action state writer.ApplyNextAction(); // for the buffer to correctly manage them if (a.Type == ActionType.CustomCode && (a as ActionCustomCode).isDeclaration) { customDeclarationLines.Add(" " + (a as ActionCustomCode).statement); } if (inlineTargets) { if (GenerateInstructionDeclaration(a, writer, out line)) { instructionLines.Add(line); } } else { if (GenerateVariableDeclaration(a, writer, it, out line)) // there will be a number jump on target-less instructions, but oh well... { declarationLines.Add(line); } if (GenerateVariableInitialization(a, writer, it, out line)) { initializationLines.Add(line); } if (GenerateInstructionDeclarationFromVariable(a, writer, it, out line)) // there will be a number jump on target-less instructions, but oh well... { instructionLines.Add(line); } } // Move on it++; } // PROGRAM ASSEMBLY // Initialize a module list List <string> module = new List <string>(); // Banner module.AddRange(GenerateDisclaimerHeader(programName)); // SOME INTERFACE INITIALIZATION // These are all for interface handling, ignored by the compiler (?) module.Add(@"&ACCESS RVP"); // read-write permissions module.Add(@"&REL 1"); // release number (increments on file changes) //module.Add(@"&COMMENT MACHINA PROGRAM"); // This was reported to not work module.Add(@"&PARAM TEMPLATE = C:\KRC\Roboter\Template\vorgabe"); module.Add(@"&PARAM EDITMASK = *"); module.Add(""); // MODULE HEADER module.Add("DEF " + programName + "()"); module.Add(""); // Declarations if (declarationLines.Count != 0) { module.AddRange(declarationLines); module.Add(""); } // Custom declarations if (customDeclarationLines.Count != 0) { module.AddRange(customDeclarationLines); module.Add(""); } // Initializations if (initializationLines.Count != 0) { module.AddRange(initializationLines); module.Add(""); } // MAIN PROCEDURE // Instructions if (instructionLines.Count != 0) { module.AddRange(instructionLines); module.Add(""); } module.Add("END"); module.Add(""); RobotProgramFile srcFile = new RobotProgramFile(programName, "src", Encoding, CC); srcFile.SetContent(module); robotProgram.Add(srcFile); return(robotProgram); }