Hey guys, I am using Teensy 3.6 and compiling it for 180Mhz. I have an OLED display connected with HW_SPI and 3 TMC2130 stepper motor drivers to teensy and I am configuring them over SoftwareSPI(bit-banging), the implemented library is from teemuatlut (link). There is a peculiar problem that I am facing, after each hard reset of the power supply to both teensy and drivers, I am unable to send commands over to drivers. Interestingly enough when I upload the code again it doesnt work straight out of the box, I need to upload stripped down version of same code (where I only initialize one driver) and after that the main program, and then it starts working. I researched a bit and found numerous solution for similar problems. But sadly none worked for me, so now I am confused what is the issue. Any help will be appreciated.
OLED used: https://www.adafruit.com/product/2674
TMC2130 used: https://www.watterott.com/en/SilentStepStick
Main code:
Stripped down code
P.S Sometimes I've to upload another stripped down program for another driver and then final big program and it works. Its quite weired!!
Also schematics are attached if it helps, they are terrible resolution in the attachment. Visit https://drive.google.com/open?id=1FZg5xVejizheG5QSlIUX6WKXLZtzo4v9 for high-res PDF, there are few manual jumper cables used which are not in the schema, but overall no major changes.
OLED used: https://www.adafruit.com/product/2674
TMC2130 used: https://www.watterott.com/en/SilentStepStick
Main code:
Code:
#include <SPI.h>
#include <ADC.h>
#include <Bounce2.h> // Software Debouncing Library
#include <TMC2130Stepper.h> // Stepper Motor Driver library
#include <Adafruit_GFX.h> // OLED graphics library
#include <Adafruit_SSD1325.h> // OLED driver library
//SM3 Pin definations
#define EN_PIN 46
#define DIR_PIN 41
#define STEP_PIN 42
#define CS_PIN 43
#define MOSI_PIN 45
#define MISO_PIN 19
#define SCK_PIN 44
#define lsmot3 4
#define rsmot3 3
//SM1 Pin definations
#define EN_PIN1 10
#define DIR_PIN1 5
#define STEP_PIN1 6
#define CS_PIN1 7
#define MOSI_PIN1 9
#define MISO_PIN1 47
#define SCK_PIN1 8
#define lsmot1 32
#define rsmot1 31
//SM2 Pin definations
#define EN_PIN2 28
#define DIR_PIN2 40
#define STEP_PIN2 24
#define CS_PIN2 25
#define MOSI_PIN2 27
#define MISO_PIN2 48 //1/ori48
#define SCK_PIN2 26
#define lsmot2 30
#define rsmot2 29
//motor homing sanity check
bool sm3homed = false;
bool tblocked = false;
bool calibhomed = false;
//oled pin definations
#define OLED_CS 23
#define OLED_RESET 21
#define OLED_DC 22
//UX Pin definations
#define switch1p 51 // switch 1 NC pin //NC - Normal Closed
#define switch1led 37 // switch 1 led pin
#define switch2p 49 // switch 2 NC pin
#define switch2led 38 // switch 2 led pin
#define switch3p 50 // switch 2 NC pin
#define switch3led 39 // switch 2 led pin
#define switch4p 54 // switch 2 NC pin
#define switch4led 34 // switch 2 led pin
#define switch5p 53 // switch 2 NC pin
#define switch5led 35 // switch 2 led pin
#define switch6p 52 // switch 2 NC pin
#define switch6led 36 // switch 2 led pin
int fsreadPin = A2;
ADC *adc = new ADC();;
//debouncing limit switches
Bounce calibupswitch = Bounce(rsmot3, 5);
Bounce calibdownswitch = Bounce(lsmot3, 5);
Bounce fsclswitch = Bounce(rsmot1, 5);
Bounce fsfarswitch = Bounce(lsmot1, 5);
Bounce dsclswitch = Bounce(rsmot2, 5);
Bounce dsfarswitch = Bounce(lsmot2, 5);
//debouncing UX switches
Bounce switch1 = Bounce( switch1p, 5 );
Bounce switch2 = Bounce( switch2p, 5 );
Bounce switch3 = Bounce( switch3p, 5 );
Bounce switch4 = Bounce( switch4p, 5 );
Bounce switch5 = Bounce( switch5p, 5 );
Bounce switch6 = Bounce( switch6p, 5 );
TMC2130Stepper SM3 = TMC2130Stepper(EN_PIN, DIR_PIN, STEP_PIN, CS_PIN, MOSI_PIN, MISO_PIN, SCK_PIN);
TMC2130Stepper SMfs = TMC2130Stepper(EN_PIN1, DIR_PIN1, STEP_PIN1, CS_PIN1, MOSI_PIN1, MISO_PIN1, SCK_PIN1);
TMC2130Stepper SM2 = TMC2130Stepper(EN_PIN2, DIR_PIN2, STEP_PIN2, CS_PIN2, MOSI_PIN2, MISO_PIN2, SCK_PIN2);
Adafruit_SSD1325 oled(OLED_DC, OLED_RESET, OLED_CS);
void setup() {
SPI.begin();
//OLED Stuff
oled.begin();
oled.clearDisplay();
oled.setRotation(2);
oled.setTextSize(3);
oled.setTextColor(WHITE);
oled.setCursor(10, 15);
oled.println("AF-MPD");
oled.setCursor(30, 48);
oled.setTextSize(1);
oled.println("CALIBRATION");
oled.display();
delay(1000);
oled.clearDisplay();
oled.setTextSize(1);
oled.setCursor(7, 24);
oled.println("Initializing...");
oled.display();
delay(200);
digitalWrite(EN_PIN, LOW);
delay(50);
digitalWrite(EN_PIN1, LOW);
delay(50);
digitalWrite(EN_PIN2, LOW);
delay(50);
pinMode(rsmot2, INPUT_PULLUP);
pinMode(lsmot2, INPUT_PULLUP);
pinMode(rsmot3, INPUT_PULLUP);
pinMode(lsmot3, INPUT_PULLUP);
pinMode(rsmot1, INPUT_PULLUP);
pinMode(lsmot1, INPUT_PULLUP);
pinMode(A0, INPUT);
pinMode(A14, INPUT);
pinMode(switch1p, INPUT);
pinMode(switch2p, INPUT);
pinMode(switch3p, INPUT);
pinMode(switch4p, INPUT);
pinMode(switch5p, INPUT);
pinMode(switch6p, INPUT);
pinMode(switch1led, OUTPUT);
pinMode(switch2led, OUTPUT);
pinMode(switch3led, OUTPUT);
pinMode(switch4led, OUTPUT);
pinMode(switch5led, OUTPUT);
pinMode(switch6led, OUTPUT);
delay(2000);
SPI.begin();
pinMode(MISO_PIN, INPUT_PULLUP);
pinMode(MISO_PIN1, INPUT_PULLUP);
pinMode(MISO_PIN2, INPUT_PULLUP);
SM3.begin();
delay(3000);
SM3.rms_current(900);
SM3.stealthChop(1);
SM3.microsteps(4);
digitalWrite(EN_PIN, HIGH);
digitalWrite(DIR_PIN, HIGH);
delay(300);
SMfs.begin();
delay(3000);
SMfs.rms_current(1000);
SMfs.stealthChop(0);
SMfs.microsteps(1);
digitalWrite(EN_PIN1, HIGH);
delay(300);
SM2.begin();
delay(3000);
SM2.rms_current(900);
SM2.stealthChop(1);
SM2.microsteps(1);
digitalWrite(EN_PIN2, HIGH);
delay(300);
}
void loop() {
calibupswitch.update();
calibdownswitch.update();
fsclswitch.update() ;
fsfarswitch.update() ;
dsclswitch.update() ;
dsfarswitch.update() ;
switch1.update();
switch2.update();
switch3.update();
switch4.update();
switch5.update();
switch6.update();
int sw4 = switch4.read();
int sw5 = switch5.read();
if (switch1.fell()) {
digitalWrite(switch1led, HIGH);
lockTB();
delay(2000);
digitalWrite(switch1led, LOW);
}
if (switch2.fell()) {
digitalWrite(switch2led, HIGH);
decoupleTB();
delay(1000);
delay(1000);
digitalWrite(switch2led, LOW);
}
if (switch3.fell()) {
digitalWrite(switch3led, HIGH);
delay(1000);
calibrate();
delay(1000);
digitalWrite(switch3led, LOW);
}
if (switch4.fell()) {
digitalWrite(switch4led, HIGH);
// dshome();
fsload();
digitalWrite(switch4led, LOW);
}
if (switch5.fell()) {
//dsengage();
digitalWrite(switch5led, HIGH);
fsdeload();
digitalWrite(switch5led, LOW);
}
oledtext("Waiting for command", 1);
}
int fsread = 0;
void fsload() {
digitalWrite(EN_PIN1, LOW);
digitalWrite(DIR_PIN1, LOW);
do {
digitalWrite(STEP_PIN1, HIGH);
delayMicroseconds(200); //DO NOT CHANGE KEEP 200 for switch
digitalWrite(STEP_PIN1, LOW);
delayMicroseconds(200); //DO NOT CHANGE KEEP 200
switch6.update();
} while (switch6.read()); //analogRead(A14) < 735 735 is valid only for
//preset position of the distance sensor, if its position
//is changed the value here needs to be calibrated for
//desired position. //switch6.read()
digitalWrite(EN_PIN1, HIGH);
}
void fsdeload() {
// turning on the driver
digitalWrite(EN_PIN1, LOW);
digitalWrite(DIR_PIN1, HIGH);
do {
digitalWrite(STEP_PIN1, HIGH);
delayMicroseconds(200); //DO NOT CHANGE KEEP 200
digitalWrite(STEP_PIN1, LOW);
delayMicroseconds(200); //DO NOT CHANGE KEEP 200
switch6.update();
} while (switch6.read()); //homesense(fsfarswitch) switch6.read()
for (int i = 0; i < 2000; i++) {
digitalWrite(STEP_PIN1, HIGH);
delayMicroseconds(200);
digitalWrite(STEP_PIN1, LOW);
delayMicroseconds(200);
}
// turning off the driver again
digitalWrite(EN_PIN1, HIGH);
}
void preload() {
digitalWrite(EN_PIN1, LOW);
digitalWrite(DIR_PIN1, LOW);
do {
digitalWrite(STEP_PIN1, HIGH);
delayMicroseconds(1);
digitalWrite(STEP_PIN1, LOW);
delayMicroseconds(1);
} while (analogRead(A0) < 550);
delay(2000);
digitalWrite(EN_PIN1, HIGH);
}
void lockTB() {
digitalWrite(EN_PIN, LOW);
SM3home();
tblocked = true;
}
void fshome() {
digitalWrite(EN_PIN1, LOW);
digitalWrite(DIR_PIN1, HIGH);
do {
fsfarswitch.update();
digitalWrite(STEP_PIN1, HIGH);
delayMicroseconds(120);
digitalWrite(STEP_PIN1, LOW);
delayMicroseconds(120);
} while (homesense(fsfarswitch));
digitalWrite(EN_PIN1, HIGH);
}
void dsengage() {
digitalWrite(EN_PIN2, LOW);
digitalWrite(DIR_PIN2, HIGH);
do {
digitalWrite(STEP_PIN2, HIGH);
delayMicroseconds(8); //DO NOT CHANGE KEEP 200 for switch
digitalWrite(STEP_PIN2, LOW);
delayMicroseconds(8); //DO NOT CHANGE KEEP 200
switch6.update();
} while (switch6.read());
//
// for (int i = 0; i < 1420000; i++) {
// digitalWrite(STEP_PIN2, HIGH);
// delayMicroseconds(8);
// digitalWrite(STEP_PIN2, LOW);
// delayMicroseconds(8);
// }
digitalWrite(EN_PIN2, HIGH);
}
void dshome() {
digitalWrite(EN_PIN2, LOW);
digitalWrite(DIR_PIN2, LOW);
do {
dsfarswitch.update();
digitalWrite(STEP_PIN2, HIGH);
delayMicroseconds(8);
digitalWrite(STEP_PIN2, LOW);
delayMicroseconds(8);
} while (homesense(dsfarswitch));
digitalWrite(DIR_PIN2, HIGH);
for (int i = 0; i < 10000; i++) {
digitalWrite(STEP_PIN2, HIGH);
delayMicroseconds(20);
digitalWrite(STEP_PIN2, LOW);
delayMicroseconds(20);
}
digitalWrite(EN_PIN2, HIGH);
}
void calibrate() {
if (calibhomed) {
delay(500);
digitalWrite(EN_PIN, LOW);
SM3move(HIGH, 29000); //7000 before for 3 mass calibration
digitalWrite(EN_PIN, HIGH);
delay(90000);
// digitalWrite(EN_PIN, LOW);
// SM3move(HIGH, 10000);
// digitalWrite(EN_PIN, HIGH);
// delay(70000);
// digitalWrite(EN_PIN, LOW);
// SM3move(HIGH, 12000);
// digitalWrite(EN_PIN, HIGH);
// delay(70000);
digitalWrite(EN_PIN, LOW);
digitalWrite(DIR_PIN, LOW);
do {
calibupswitch.update();
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(120);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(120);
} while (homesense(calibupswitch));
digitalWrite(DIR_PIN, HIGH);
for (int i = 0; i < 1500; i++) {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(200);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(200);
}
calibhomed = true;
digitalWrite(EN_PIN1, HIGH);
}
else {
delay(1500);
}
}
void decoupleTB() {
if (tblocked) {
digitalWrite(EN_PIN, LOW);
digitalWrite(DIR_PIN, LOW);
for (int i = 0; i < 3500; i++) {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(4000); //4000 for roundhead
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(4000);
}
delay(1800); // 1200 for roundhead
do {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(200);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(200);
calibupswitch.update();
} while (homesense(calibupswitch));
digitalWrite(DIR_PIN, HIGH);
for (int i = 0; i < 1500; i++) {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(200);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(200);
}
tblocked = false;
sm3homed = false;
calibhomed = true;
digitalWrite(EN_PIN, HIGH);
}
else {
delay(1000);
}
}
void SM3move(bool dir, int steps) {
digitalWrite(EN_PIN, LOW);
digitalWrite(DIR_PIN, dir); //setting direction to move
for (int i = 0; i < steps; i++) {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(400);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(400);
}
sm3homed = false;
calibhomed = false;
digitalWrite(EN_PIN, HIGH);
}
void SM3home() {
if (!sm3homed) {
digitalWrite(EN_PIN, LOW);
digitalWrite(DIR_PIN, HIGH);
do {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(220);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(220);
calibdownswitch.update();
} while (homesense(calibdownswitch));
//move preset number of steps in the opposite
//direction to have a homing reference
digitalWrite(DIR_PIN, LOW);
for (int i = 0; i < 500; i++) {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(200);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(200);
}
sm3homed = true;
digitalWrite(EN_PIN, HIGH);
delay(500);
}
else {
delay(1000);
}
}
char * oledtext(String txt, int size) {
oled.clearDisplay();
oled.setRotation(2);
oled.setTextSize(1);
oled.setTextColor(WHITE);
oled.setCursor(7, 24);
oled.println(txt);
oled.display();
}
bool homesense(Bounce db) {
// Senses the limit switch press and returns false
if (db.rose()) {
return false;
} else {
return true;
}
}
Stripped down code
Code:
#include <Bounce2.h> // Software Debouncing Library
#include <TMC2130Stepper.h> // Stepper Motor Driver library
#include <Adafruit_GFX.h> // OLED graphics library
#include <Adafruit_SSD1325.h> // OLED driver library
//SM3 Pin definations
#define EN_PIN 46
#define DIR_PIN 41
#define STEP_PIN 42
#define CS_PIN 43
#define MOSI_PIN 45
#define MISO_PIN 1
#define SCK_PIN 44
#define lsmot3 4
#define rsmot3 3
//motor homing sanity check
bool sm3homed = false;
//oled pin definations
#define OLED_CS 23
#define OLED_RESET 21
#define OLED_DC 22
//UX Pin definations
#define switch1p 52 // switch 1 NC pin //NC - Normal Closed
#define switch1led 36 // switch 1 led pin
#define switch2p 53 // switch 2 NC pin
#define switch2led 35 // switch 2 led pin
//debouncing limit switches
Bounce calibupswitch = Bounce(rsmot3, 5);
Bounce calibdownswitch = Bounce(lsmot3, 5);
//debouncing UX switches
Bounce switch1 = Bounce( switch1p, 5 );
Bounce switch2 = Bounce( switch2p, 5 );
TMC2130Stepper SM3 = TMC2130Stepper(EN_PIN, DIR_PIN, STEP_PIN, CS_PIN, MOSI_PIN, MISO_PIN, SCK_PIN);
Adafruit_SSD1325 oled(OLED_DC, OLED_RESET, OLED_CS);
void setup() {
pinMode(rsmot3, INPUT_PULLUP);
pinMode(lsmot3, INPUT_PULLUP);
pinMode(switch1p, INPUT);
pinMode(switch2p, INPUT);
SM3.begin();
SM3.rms_current(900);
SM3.stealthChop(1);
SM3.microsteps(4);
digitalWrite(EN_PIN, LOW);
digitalWrite(DIR_PIN, HIGH);
}
void loop() {
// calibupswitch.update();
// calibdownswitch.update();
// switch1.update();
// switch2.update();
//// if (switch1.fell()) {
//// SM3home();
//// }
// if (switch2.fell()) {
// SM3home();
// }
// oledtext("Waiting for command", 2);
//
}
void SM3move(bool dir, int steps) {
digitalWrite(DIR_PIN, dir); //setting direction to move
for (int i = 0; i < steps; i++) {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(400);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(400);
}
sm3homed = false;
}
void SM3home() {
if (!sm3homed) {
digitalWrite(DIR_PIN, HIGH);
do {
calibdownswitch.update();
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(1500);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(1500);
} while (homesense(calibdownswitch));
//move preset number of steps in the opposite
//direction to have a homing reference
digitalWrite(DIR_PIN, LOW);
for (int i = 0; i < 200; i++) {
digitalWrite(STEP_PIN, HIGH);
delayMicroseconds(1500);
digitalWrite(STEP_PIN, LOW);
delayMicroseconds(1500);
}
sm3homed = true;
delay(500);
}
else {
delay(1000);
}
}
char * oledtext(String txt, int size) {[URL="https://drive.google.com/open?id=1FZg5xVejizheG5QSlIUX6WKXLZtzo4v9"]https://drive.google.com/open?id=1FZg5xVejizheG5QSlIUX6WKXLZtzo4v9[/URL]
oled.clearDisplay();
oled.setRotation(2);
oled.setTextSize(size);
oled.setTextColor(WHITE);
oled.setCursor(5, 5);
oled.println(txt);
oled.display();
}
bool homesense(Bounce db) {
// Senses the limit switch press and returns false
if (db.rose()) {
return false;
} else {
return true;
}
}
P.S Sometimes I've to upload another stripped down program for another driver and then final big program and it works. Its quite weired!!
Also schematics are attached if it helps, they are terrible resolution in the attachment. Visit https://drive.google.com/open?id=1FZg5xVejizheG5QSlIUX6WKXLZtzo4v9 for high-res PDF, there are few manual jumper cables used which are not in the schema, but overall no major changes.
Attachments
Last edited: