# DRO Installation & Setup Guide This guide walks through setting up the Digital Read Out application on a Raspberry Pi. ## System Requirements - **Hardware**: Raspberry Pi 4 (or later) - **OS**: Raspbian/Raspberry Pi OS (Bullseye or later) - **Python**: 3.7+ - **Arduino**: Arduino Nano with I2C encoder firmware ## Step 1: Install Dependencies ### Enable I2C ```bash sudo raspi-config # Navigate to: Interfacing Options → I2C → Yes # Reboot sudo reboot ``` ### Install Python Libraries ```bash # Update package manager sudo apt-get update sudo apt-get upgrade # Install required packages sudo apt-get install python3-tk python3-dev python3-pip # Install Python dependencies pip3 install smbus2 pip3 install adafruit-circuitpython-ads1x15 # Optional: for ADC ``` ### Optional: System Calculator ```bash sudo apt-get install galculator ``` ## Step 2: Configure I2C for Shutdown Allow the application to shutdown without a password: ```bash sudo visudo ``` Add this line to the end of the file (replace `pi` with your username): ``` pi ALL=(ALL) NOPASSWD: /sbin/poweroff, /sbin/reboot, /sbin/shutdown ``` Save with Ctrl+X, then Y, then Enter. ## Step 3: Upload Arduino Firmware The Arduino must run firmware that: 1. Reads from two rotary encoders 2. Maintains position counters 3. Responds to I2C read requests at address 0x08 See [ARDUINO_I2C_PROTOCOL.md](./ARDUINO_I2C_PROTOCOL.md) for protocol details. Example firmware structure: ```cpp #include volatile int16_t x_position = 0; volatile int16_t z_position = 0; void setup() { Wire.begin(0x08); Wire.onRequest(requestEvent); // Setup encoder interrupts pinMode(2, INPUT); pinMode(3, INPUT); attachInterrupt(0, x_encoder_isr, CHANGE); attachInterrupt(1, z_encoder_isr, CHANGE); } void requestEvent() { byte buffer[4]; buffer[0] = (byte)x_position; buffer[1] = (byte)(x_position >> 8); buffer[2] = (byte)z_position; buffer[3] = (byte)(z_position >> 8); Wire.write(buffer, 4); } // Encoder ISR routines... void loop() {} ``` Refer to the `i2c_encoder/` directory for the complete Arduino sketch. ## Step 4: Verify I2C Connection Test I2C communication: ```bash # Install I2C tools sudo apt-get install i2c-tools # Scan for I2C devices i2cdetect -y 1 # Should show Arduino at address 0x08: # 0 1 2 3 4 5 6 7 8 9 a b c d e f # 00: -- -- -- -- -- -- -- -- 08 -- -- -- -- ``` ## Step 5: Auto-Start Configuration ### Option A: Desktop File (GUI Autostart) Create `/home/pi/.config/autostart/dro.desktop`: ```ini [Desktop Entry] Type=Application Name=DRO Exec=python3 /home/pi/dro/dro.py --zoomed StartupNotify=false X-GNOME-Autostart-always-run=true ``` ### Option B: Systemd Service Create `/etc/systemd/system/dro.service`: ```ini [Unit] Description=Digital Read Out (DRO) Application After=graphical.target [Service] Type=simple User=pi WorkingDirectory=/home/pi/dro ExecStart=/usr/bin/python3 /home/pi/dro/dro.py --zoomed Restart=on-failure RestartSec=5 [Install] WantedBy=graphical.target ``` Enable and start: ```bash sudo systemctl daemon-reload sudo systemctl enable dro.service sudo systemctl start dro.service ``` ### Option C: Shell Script Autostart Create `/home/pi/dro/autostart.sh`: ```bash #!/bin/bash cd /home/pi/dro python3 dro.py --zoomed ``` Make executable: ```bash chmod +x /home/pi/dro/autostart.sh ``` Add to crontab (for user pi): ```bash crontab -e # Add line: @reboot /home/pi/dro/autostart.sh ``` ## Step 6: Test the Installation ### Test Mode (without Arduino) ```bash cd ~/dro python3 dro.py --test # Use keyboard to test: # A/Z = X encoder up/down # S/X = Z encoder up/down ``` ### With Hardware ```bash # Start the application python3 dro.py --zoomed # Check logs (if systemd service) journalctl -u dro.service -f ``` ## Step 7: Calibration ### Set Scale Factors Edit `dro.py` and adjust these lines based on your encoder specifications: ```python # X axis: negative to flip direction model.set_scale('x', -2.5/200) # mm per step # Z axis model.set_scale('z', 90/1000) # mm per step ``` **How to determine:** 1. Move the tool a known distance (e.g., 10 mm) 2. Record the encoder step count 3. Scale = Distance (mm) / Steps 4. Use negative for X if the direction is backwards ### Set Zero Points 1. Position tool at starting location 2. Press **X_0** button to zero X axis 3. Press **Z_0** button to zero Z axis ## Troubleshooting ### No I2C Communication ```bash # Check I2C is enabled raspi-config # Verify devices are connected i2cdetect -y 1 # Check for USB connections (if Arduino is USB) ls -la /dev/ttyUSB* ``` ### GUI Not Appearing ```bash # Check display settings export DISPLAY=:0 python3 dro.py # Verify Tkinter is installed python3 -c "import tkinter; print('Tkinter OK')" ``` ### I2C Errors - Check pull-up resistors (4.7 kΩ is standard) - Verify Arduino firmware is running - Try slower I2C speed: edit smbus2 initialization ### Position Drift - Recalibrate scale factors - Check encoder hardware connections - Verify encoder isn't slipping ## File Structure ``` /home/pi/dro/ ├── dro.py # Main application ├── autostart.sh # Auto-start script ├── power.png # Power button icon ├── test_model.py # Unit tests ├── README.md # Project overview ├── docs/ │ ├── DRO.md # Application documentation │ └── ARDUINO_I2C_PROTOCOL.md # I2C protocol └── i2c_encoder/ ├── i2c_encoder.ino # Arduino firmware └── i2c_test.py # Arduino test script ``` ## Performance Tips 1. **Reduce Update Interval** (for faster response): ```python self._update_interval_ms = 50 # 20 Hz instead of 10 Hz ``` 2. **Increase I2C Speed**: ```python bus = smbus2.SMBus(1) bus.bus.set_clock(400000) # 400 kHz fast mode ``` 3. **Use GPIO Directly** (instead of I2C) for more performance: - Requires hardware changes - RPi.GPIO library for direct GPIO reading ## Security Notes - The DRO needs `sudo` access to shutdown (configured via sudoers) - Store any sensitive config files outside the repo - Use `.env` files for sensitive data (not committed to git) ## Getting Help - Check logs: `journalctl -u dro.service -f` - Test I2C: `i2cget -y 1 0x08 0 i 4` - Python console test: ```bash python3 import smbus2 bus = smbus2.SMBus(1) print(bus.read_i2c_block_data(0x08, 0, 4)) ```