Complete implementation of Python-KRL coordination features for seamless bidirectional communication between RSIPI and KUKA KRL programs. ## IOAPI Enhancements Added high-level I/O control methods for convenient digital I/O manipulation: - **set_output(channel, value, group='Digout')** - Set digital output by channel number - **get_input(channel, group='Digin')** - Read digital input by channel number - **pulse(channel, duration=0.1, group='Digout')** - Generate timed pulse on output Benefits: - Simpler channel-based addressing (channel 1 instead of 'Digout.o1') - Automatic channel name formatting - Built-in pulse generation for pneumatic actuators and signaling - Consistent error handling ## KRLAPI Enhancements Added coordination helper methods for Python-KRL synchronization: - **wait_for_signal(channel, timeout=5.0)** - Block until KRL sets I/O signal - **signal_complete(channel)** - Signal KRL that Python operation is complete - **write_param(slot, value)** - Write to Tech.C variables (Python → KRL) - **read_param(slot)** - Read from Tech.T variables (KRL → Python) Features: - Configurable timeouts with proper error handling - Flexible slot addressing (11, 'C11', 'c11' all work) - Slot validation (enforces 11-199 range) - Comprehensive logging for debugging - Clear docstrings with KRL code examples ## KRL Template Library Created comprehensive KRL templates demonstrating coordination patterns: **templates/krl/basic_handshake.src** - Simple I/O handshaking (KRL signals → Python waits → Python signals back) - Timeout handling and error recovery - Complete Python code examples in comments **templates/krl/parameter_passing.src** - Bidirectional Tech variable communication - KRL writes position to Tech.T, Python reads - Python calculates target, writes to Tech.C, KRL reads - Demonstrates full parameter exchange workflow **templates/krl/state_machine.src** - Multi-state coordination workflow - States: IDLE, CALIBRATING, READY, EXECUTING, COMPLETE, ERROR - Combines I/O signals and Tech variables - Error handling and timeout mechanisms - Demonstrates complex production-ready pattern **templates/krl/README.md** - Comprehensive coordination patterns documentation - Tech variable mapping conventions (C vs T variables) - I/O signal mapping standards - Timing best practices - Troubleshooting guide ## Python Coordination Examples Created production-ready Python examples demonstrating all coordination methods: **examples/coordination/01_basic_handshake.py** - Simple I/O handshake demonstration - Matches basic_handshake.src template - Command-line interface with argparse - Comprehensive logging and error handling **examples/coordination/02_parameter_passing.py** - Parameter exchange workflow - Reads position from KRL (Tech.T) - Calculates target position - Writes target to KRL (Tech.C) - Matches parameter_passing.src template **examples/coordination/03_state_machine.py** - Complex multi-state coordination - State monitoring loop with enum - Calibration routine with offset calculation - Error detection and signaling - Matches state_machine.src template **examples/coordination/README.md** - Complete usage instructions - Configuration requirements - Troubleshooting section - Customization examples - Advanced usage patterns ## Modified Files src/RSIPI/io_api.py: - Added time import - Implemented set_output() method - Implemented get_input() method with navigation of receive_variables - Implemented pulse() method with blocking time.sleep() - Comprehensive docstrings with examples src/RSIPI/krl_api.py: - Added time import - Implemented wait_for_signal() with configurable polling - Implemented signal_complete() method - Implemented write_param() with slot normalization and validation - Implemented read_param() with slot normalization and validation - KRL code examples in all docstrings ## New Directories templates/krl/ - 3 KRL program templates - Comprehensive README with patterns and conventions examples/coordination/ - 3 Python example scripts - Complete usage documentation ## Design Decisions **I/O Channel Numbering**: 1-based to match KUKA conventions **Tech Variable Slots**: Validated 11-199 range (KUKA reserves 1-10) **Blocking Operations**: wait_for_signal() and pulse() block with configurable timeouts **Error Handling**: Proper exceptions with clear messages **Logging**: Debug/Info/Warning levels for all operations **Documentation**: Every method includes KRL code examples ## Phase 3 Status: ✅ COMPLETE All planned features implemented: - ✅ High-level Digital I/O API - ✅ KRL state coordination helpers - ✅ Parameter passing via Tech variables - ✅ KRL code templates - ✅ Python coordination examples - ✅ Comprehensive documentation Next: Phase 4 (Advanced Motion Control)
394 lines
8.7 KiB
Markdown
394 lines
8.7 KiB
Markdown
# KRL Coordination Templates
|
|
|
|
This directory contains KRL program templates demonstrating common Python-KRL coordination patterns using RSIPI.
|
|
|
|
## Available Templates
|
|
|
|
### 1. basic_handshake.src
|
|
**Simple I/O handshaking between Python and KRL**
|
|
|
|
- KRL signals "ready" via digital output
|
|
- Python waits for signal, processes data
|
|
- Python signals "complete" via input
|
|
- KRL waits for completion, then continues
|
|
|
|
**Use Case**: Basic synchronization, ensuring Python completes processing before KRL continues.
|
|
|
|
**Coordination Methods Used**:
|
|
- `api.krl.wait_for_signal(channel, timeout)`
|
|
- `api.krl.signal_complete(channel)`
|
|
|
|
### 2. parameter_passing.src
|
|
**Bidirectional numerical data exchange via Tech variables**
|
|
|
|
- KRL writes current position to Tech.T variables
|
|
- Python reads position data
|
|
- Python calculates target and writes to Tech.C variables
|
|
- KRL reads target and executes motion
|
|
|
|
**Use Case**: Passing numerical parameters (positions, forces, tolerances) between Python and KRL.
|
|
|
|
**Coordination Methods Used**:
|
|
- `api.krl.read_param(slot)` - Read from Tech.T
|
|
- `api.krl.write_param(slot, value)` - Write to Tech.C
|
|
- `api.krl.wait_for_signal(channel, timeout)`
|
|
- `api.krl.signal_complete(channel)`
|
|
|
|
### 3. state_machine.src
|
|
**Multi-state workflow with complex coordination**
|
|
|
|
Implements a 5-state machine:
|
|
1. **IDLE**: Waiting to start
|
|
2. **CALIBRATING**: Python performing calibration
|
|
3. **READY**: Calibration complete
|
|
4. **EXECUTING**: Robot motion in progress
|
|
5. **COMPLETE**: Task finished
|
|
6. **ERROR**: Error handling state
|
|
|
|
**Use Case**: Complex workflows requiring multiple handshakes, error handling, and state tracking.
|
|
|
|
**Coordination Methods Used**:
|
|
- All coordination methods from basic_handshake and parameter_passing
|
|
- State variable in Tech.T[11]
|
|
- Command variable in Tech.C[11]
|
|
|
|
## Python-KRL Coordination Patterns
|
|
|
|
### Pattern 1: Simple Handshake
|
|
|
|
```python
|
|
# Python side
|
|
api.krl.wait_for_signal(1) # Wait for KRL ready signal
|
|
# Do processing...
|
|
api.krl.signal_complete(1) # Signal KRL to continue
|
|
```
|
|
|
|
```krl
|
|
; KRL side
|
|
$OUT[1] = TRUE ; Signal ready to Python
|
|
; Wait for Python completion
|
|
WHILE $IN[1] == FALSE
|
|
WAIT SEC 0.1
|
|
ENDWHILE
|
|
```
|
|
|
|
### Pattern 2: Parameter Exchange
|
|
|
|
```python
|
|
# Python side
|
|
api.krl.wait_for_signal(1)
|
|
|
|
# Read from KRL
|
|
value = api.krl.read_param('T11')
|
|
|
|
# Process and write back
|
|
result = process(value)
|
|
api.krl.write_param('C11', result)
|
|
|
|
api.krl.signal_complete(1)
|
|
```
|
|
|
|
```krl
|
|
; KRL side
|
|
$TECH.T[11] = some_value
|
|
$OUT[1] = TRUE ; Signal data ready
|
|
|
|
; Wait for Python
|
|
WHILE $IN[1] == FALSE
|
|
WAIT SEC 0.1
|
|
ENDWHILE
|
|
|
|
; Read result
|
|
result = $TECH.C[11]
|
|
```
|
|
|
|
### Pattern 3: Continuous Monitoring
|
|
|
|
```python
|
|
# Python side - non-blocking monitoring loop
|
|
api.start()
|
|
|
|
while api.is_running():
|
|
state = api.krl.read_param('T11')
|
|
|
|
if state == 1: # Specific state
|
|
# React to state change
|
|
api.krl.write_param('C11', calculated_value)
|
|
api.krl.signal_complete(1)
|
|
|
|
time.sleep(0.1) # Check every 100ms
|
|
|
|
api.stop()
|
|
```
|
|
|
|
```krl
|
|
; KRL side - updates state continuously
|
|
$TECH.T[11] = current_state
|
|
|
|
; Wait for Python response when needed
|
|
WHILE $IN[1] == FALSE
|
|
WAIT SEC 0.1
|
|
ENDWHILE
|
|
|
|
calculated = $TECH.C[11]
|
|
```
|
|
|
|
## Tech Variable Conventions
|
|
|
|
### Tech.C Variables (Python → KRL)
|
|
**"Control" variables - Python writes, KRL reads**
|
|
|
|
| Slot | Description | Example Usage |
|
|
|------|-------------|---------------|
|
|
| C11 | Command/state | 0=continue, 1=pause, 2=abort |
|
|
| C12-C14 | Position offsets | X, Y, Z corrections |
|
|
| C15-C17 | Target position | Calculated target coordinates |
|
|
| C18-C20 | Process parameters | Speed, force, tolerance |
|
|
| C21+ | Custom parameters | Application-specific data |
|
|
|
|
```python
|
|
# Python writes
|
|
api.krl.write_param('C11', 0) # Command: continue
|
|
api.krl.write_param('C12', 5.0) # X offset
|
|
api.krl.write_param('C13', -2.0) # Y offset
|
|
```
|
|
|
|
```krl
|
|
; KRL reads
|
|
command = $TECH.C[11]
|
|
offset_x = $TECH.C[12]
|
|
offset_y = $TECH.C[13]
|
|
```
|
|
|
|
### Tech.T Variables (KRL → Python)
|
|
**"Transfer" variables - KRL writes, Python reads**
|
|
|
|
| Slot | Description | Example Usage |
|
|
|------|-------------|---------------|
|
|
| T11 | Current state | State machine state number |
|
|
| T12-T14 | Current position | X, Y, Z coordinates |
|
|
| T15-T17 | Force/torque | Measured forces |
|
|
| T18-T20 | Sensor readings | External sensor data |
|
|
| T21+ | Custom data | Application-specific values |
|
|
|
|
```krl
|
|
; KRL writes
|
|
$TECH.T[11] = current_state
|
|
$TECH.T[12] = $POS_ACT.X
|
|
$TECH.T[13] = $POS_ACT.Y
|
|
$TECH.T[14] = $POS_ACT.Z
|
|
```
|
|
|
|
```python
|
|
# Python reads
|
|
state = api.krl.read_param('T11')
|
|
pos_x = api.krl.read_param('T12')
|
|
pos_y = api.krl.read_param('T13')
|
|
pos_z = api.krl.read_param('T14')
|
|
```
|
|
|
|
## I/O Signal Conventions
|
|
|
|
### Standard I/O Mapping
|
|
|
|
| Signal | Type | Purpose |
|
|
|--------|------|---------|
|
|
| $OUT[1] | Output | KRL → Python state/ready signal |
|
|
| $IN[1] | Input | Python → KRL completion acknowledgement |
|
|
| $IN[2] | Input | Python → KRL error signal |
|
|
| $OUT[2] | Output | KRL → Python auxiliary signal |
|
|
|
|
```python
|
|
# Python I/O methods
|
|
api.krl.wait_for_signal(1) # Wait for $OUT[1]
|
|
api.krl.signal_complete(1) # Set $IN[1]
|
|
api.io.set_output(2, True) # Control $OUT[2]
|
|
```
|
|
|
|
## Error Handling Best Practices
|
|
|
|
### Timeouts
|
|
|
|
**Always use timeouts to prevent indefinite blocking:**
|
|
|
|
```python
|
|
# Python
|
|
if not api.krl.wait_for_signal(1, timeout=10.0):
|
|
print("Timeout waiting for KRL!")
|
|
# Handle error
|
|
```
|
|
|
|
```krl
|
|
; KRL
|
|
INT counter
|
|
counter = 0
|
|
WHILE ($IN[1] == FALSE) AND (counter < 100)
|
|
WAIT SEC 0.1
|
|
counter = counter + 1
|
|
ENDWHILE
|
|
|
|
IF counter >= 100 THEN
|
|
; Timeout - handle error
|
|
HALT
|
|
ENDIF
|
|
```
|
|
|
|
### Error Signaling
|
|
|
|
**Use dedicated error channels:**
|
|
|
|
```python
|
|
# Python detects error
|
|
if error_condition:
|
|
api.io.set_output(2, True) # Signal error to KRL
|
|
```
|
|
|
|
```krl
|
|
; KRL checks for errors
|
|
IF $IN[2] == TRUE THEN
|
|
; Python signaled error
|
|
HALT
|
|
ENDIF
|
|
```
|
|
|
|
## Integration with RSI Motion Control
|
|
|
|
All coordination patterns work seamlessly with RSI real-time motion corrections:
|
|
|
|
```python
|
|
# Python coordinates with KRL AND sends real-time corrections
|
|
api.start()
|
|
|
|
# Wait for KRL to start motion phase
|
|
api.krl.wait_for_signal(1)
|
|
|
|
# Send real-time corrections during KRL motion
|
|
for i in range(100):
|
|
correction = calculate_correction()
|
|
api.motion.update_cartesian(X=correction)
|
|
time.sleep(0.004) # 250Hz update rate
|
|
|
|
# Signal motion phase complete
|
|
api.krl.signal_complete(1)
|
|
|
|
api.stop()
|
|
```
|
|
|
|
```krl
|
|
; KRL executes motion while Python sends corrections
|
|
$OUT[1] = TRUE ; Signal motion start
|
|
|
|
; Python sends corrections via RSI during this move
|
|
LIN target_pos Vel=0.5 m/s CPDAT1 Tool[1] Base[0]
|
|
|
|
; Wait for Python to finish corrections
|
|
WHILE $IN[1] == FALSE
|
|
WAIT SEC 0.1
|
|
ENDWHILE
|
|
```
|
|
|
|
## Testing Templates
|
|
|
|
To test these templates:
|
|
|
|
1. **Upload KRL program to robot controller**
|
|
2. **Start Python coordination script**
|
|
3. **Execute KRL program on teach pendant**
|
|
4. **Monitor coordination in Python logs**
|
|
|
|
Example Python test script:
|
|
|
|
```python
|
|
from RSIPI import RSIAPI
|
|
import time
|
|
|
|
api = RSIAPI('RSI_EthernetConfig.xml')
|
|
api.start()
|
|
|
|
try:
|
|
print("Waiting for KRL ready signal...")
|
|
|
|
if api.krl.wait_for_signal(1, timeout=30.0):
|
|
print("✅ KRL signaled ready!")
|
|
|
|
# Simulate processing
|
|
time.sleep(2.0)
|
|
print("Processing complete")
|
|
|
|
# Signal back to KRL
|
|
api.krl.signal_complete(1)
|
|
print("✅ Signaled KRL to continue")
|
|
|
|
else:
|
|
print("❌ Timeout waiting for KRL")
|
|
|
|
except KeyboardInterrupt:
|
|
print("\n⚠️ Interrupted by user")
|
|
|
|
finally:
|
|
api.stop()
|
|
print("API stopped")
|
|
```
|
|
|
|
## Troubleshooting
|
|
|
|
### Signal Not Received
|
|
|
|
**Check I/O configuration in RSI XML:**
|
|
```xml
|
|
<SEND>
|
|
<XML>
|
|
<ELEMENT Tag="Digin" Type="INT"/>
|
|
</XML>
|
|
</SEND>
|
|
<RECEIVE>
|
|
<XML>
|
|
<ELEMENT Tag="Digout" Type="INT"/>
|
|
</XML>
|
|
</RECEIVE>
|
|
```
|
|
|
|
### Tech Variable Not Found
|
|
|
|
**Ensure Tech variables are configured in RSI XML:**
|
|
```xml
|
|
<SEND>
|
|
<XML>
|
|
<ELEMENT Tag="Tech" Type="DOUBLE" Indizes="[1..199]"/>
|
|
</XML>
|
|
</SEND>
|
|
<RECEIVE>
|
|
<XML>
|
|
<ELEMENT Tag="Tech" Type="DOUBLE" Indizes="[1..199]"/>
|
|
</XML>
|
|
</RECEIVE>
|
|
```
|
|
|
|
### Timing Issues
|
|
|
|
- **Reduce check_interval for faster response**: `api.krl.wait_for_signal(1, check_interval=0.005)`
|
|
- **Increase timeout for slow operations**: `api.krl.wait_for_signal(1, timeout=60.0)`
|
|
- **Add WAIT SEC delays in KRL for signal propagation**
|
|
|
|
## Next Steps
|
|
|
|
After understanding these templates:
|
|
|
|
1. **Adapt templates** to your specific application
|
|
2. **Test coordination** patterns with your robot
|
|
3. **Implement error recovery** mechanisms
|
|
4. **Document custom** coordination protocols
|
|
5. **Create application-specific** state machines
|
|
|
|
## References
|
|
|
|
- [RSIPI Documentation](../../README.md)
|
|
- [Phase 3 Summary](../../PHASE_3_SUMMARY.md) (when available)
|
|
- [KUKA RSI 3.3 Documentation](https://www.kuka.com)
|
|
|
|
---
|
|
|
|
**Template Author**: RSIPI Development Team
|
|
**Last Updated**: January 17, 2026
|
|
**Version**: 1.0
|