You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
291 lines
7.3 KiB
C++
291 lines
7.3 KiB
C++
/*
|
|
Stepper Motor Control - one step at a time
|
|
|
|
This program drives a unipolar or bipolar stepper motor.
|
|
The motor is attached to digital pins 8 - 11 of the Arduino.
|
|
|
|
The motor will step one step at a time, very slowly. You can use this to
|
|
test that you've got the four wires of your stepper wired to the correct
|
|
pins. If wired correctly, all steps should be in the same direction.
|
|
|
|
Use this also to count the number of steps per revolution of your motor,
|
|
if you don't know it. Then plug that number into the oneRevolution
|
|
example to see if you got it right.
|
|
|
|
Created 30 Nov. 2009
|
|
by Tom Igoe
|
|
|
|
*/
|
|
|
|
#include <Stepper.h>
|
|
|
|
// Typewriter head
|
|
unsigned char charmap[] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 24, 0, 64, 67, 74, 16, 72, 73, 51, 65, 14, 63, 1, 50, 57, 53, 54, 55, 56, 58, 59, 60, 61, 62, 31, 43, 0, 68, 0, 27, 0, 38, 19, 22, 30, 28, 23, 32, 42, 40, 36, 46, 34, 17, 44, 41, 35, 48, 25, 26, 37, 29, 33, 15, 49, 39, 21, 0, 0, 0, 45, 0, 82, 94, 88, 89, 86, 93, 3, 83, 4, 95, 84, 9, 87, 81, 92, 91, 6, 8, 90, 5, 2, 7, 85, 13, 79, 10, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 66, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20, 0, 0, 0, 76, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 75, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 70, 0, 0, 0, 0, 0, 52, 0, 0, 0, 0, 0, 0, 0, 71, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 78, 0, 0, 0, 0, 0, 69, 0, 0};
|
|
|
|
// Keyboard
|
|
uint8_t keyMap[9][8] {
|
|
/*0*/ {'5', '\x80'/*backarrw*/, '4', '=', '`', '9', '1', '8'},
|
|
/*1*/ {0, 0, 'y', '[', 'w', 'p', 'e', 'u'},
|
|
/*2*/ {'6', '\x81'/*forwarrw*/, '3', '-', 0, '0', '2', '7'},
|
|
/*3*/ {'a', 0, 'k', '\n', 'f', '\x82'/*caps*/, 'g', 'l'},
|
|
/*4*/ {'\t', '\x83'/*backsps*/, 't', ']', 'q', 'o', 'r', 'i'},
|
|
/*5*/ {'s', 0, 'j', '\'', 'd', 0, 'h', ';'},
|
|
/*6*/ {'c', '\x86'/*r_down_ctrl*/, 'm', 0, 'n', 'x', 0, '/'},
|
|
/*7*/ {'v', 0, ',', '\x84'/*l_shift*/, 'b', 'z', '\\', '.'},
|
|
/*8*/ {' ', '\x85'/*l_up_ctrl*/, 0, 0, 0, 0, 0, 0}
|
|
};
|
|
uint8_t lastKey[9] = { 0 };
|
|
|
|
const int stepsPerRevolution = 200; // change this to fit the number of steps per revolution
|
|
// for your motor
|
|
|
|
// initialize the stepper library on pins 8 through 11:
|
|
Stepper columnStepper(stepsPerRevolution, 8, 9, 10, 11);
|
|
Stepper charWheelStepper(96, 7, 6, 5, 4);
|
|
|
|
int charWidth = 11; // how many steps between char prints
|
|
|
|
int currentPos = 0;
|
|
int currentChar = 0;
|
|
int limitPin = 12;
|
|
int headMotorLimitPin = 13;
|
|
int hammerPin = 14;
|
|
|
|
int Motor1A = 2;
|
|
int Motor1B = 3;
|
|
int Motor2A = 15;
|
|
|
|
void setup() {
|
|
// initialize the serial port:
|
|
Serial.begin(1200);
|
|
|
|
// configure limit pin
|
|
pinMode(limitPin, INPUT);
|
|
digitalWrite(limitPin, HIGH);
|
|
|
|
pinMode(headMotorLimitPin, INPUT);
|
|
digitalWrite(headMotorLimitPin, HIGH);
|
|
|
|
pinMode(Motor1A, OUTPUT);
|
|
pinMode(Motor1B, OUTPUT);
|
|
pinMode(Motor2A, OUTPUT);
|
|
|
|
pinMode(hammerPin, OUTPUT);
|
|
digitalWrite(hammerPin, LOW);
|
|
|
|
// Keyboard
|
|
for (int i = 22; i < 30; i++) {
|
|
pinMode(i, INPUT);
|
|
digitalWrite(i, HIGH);
|
|
}
|
|
for (int i = 30; i < 40; i++) {
|
|
pinMode(i, INPUT);
|
|
digitalWrite(i, LOW);
|
|
}
|
|
|
|
columnStepper.setSpeed(90);
|
|
charWheelStepper.setSpeed(90);
|
|
//Serial.println("Finding home");
|
|
findHome();
|
|
//Serial.println("Home found!");
|
|
}
|
|
|
|
void loop() {
|
|
delay(1000);
|
|
unsigned long lastCharTime;
|
|
while(0) {
|
|
for (int i = 0; i < 98; i++) {
|
|
printChar('0');
|
|
}
|
|
while(1) {lineFeed();}
|
|
}
|
|
while(1) {
|
|
if (Serial.available() > 0) {
|
|
// read the incoming byte:
|
|
lastCharTime = millis();
|
|
unsigned char in = Serial.read();
|
|
if (in == '\n') {
|
|
lineFeed();
|
|
lineFeed();
|
|
home();
|
|
} else {
|
|
printChar(in);
|
|
}
|
|
}
|
|
if (millis() - lastCharTime > 1000) {
|
|
releaseSteppers();
|
|
}
|
|
readKey();
|
|
}
|
|
while(1) {
|
|
lineFeed();
|
|
delay(500);
|
|
}
|
|
while(1) {
|
|
//charWheelStepper.step(96);
|
|
charWheelStepper.step(1);
|
|
delay(100);
|
|
Serial.println(digitalRead(headMotorLimitPin));
|
|
|
|
}
|
|
bool limit = digitalRead(limitPin);
|
|
if(!limit) {
|
|
// step one step:
|
|
columnStepper.step(-1);
|
|
} else {
|
|
columnStepper.step(1200);
|
|
}
|
|
Serial.println(limit);
|
|
delay(3);
|
|
}
|
|
|
|
void printChar(unsigned char c){
|
|
int newLoc = charmap[c];
|
|
/*Serial.print("char ");
|
|
Serial.print(c);
|
|
Serial.print(" at ");
|
|
Serial.print(newLoc);*/
|
|
if (newLoc == 0){
|
|
charWheelStepper.step(1);
|
|
delay(30);
|
|
charWheelStepper.step(-1);
|
|
delay(30);
|
|
} else {
|
|
/*aSerial.print(", cur: ");
|
|
Serial.print(currentChar);
|
|
if (currentChar > newLoc) {
|
|
Serial.print(" > ");
|
|
newLoc = newLoc - currentChar;
|
|
currentChar += newLoc;
|
|
} else if (currentChar < newLoc) {
|
|
Serial.print(" < ");
|
|
|
|
} else {
|
|
Serial.print(" = ");
|
|
// that char is already selected
|
|
newLoc = 0;
|
|
}*/
|
|
newLoc = newLoc - currentChar;
|
|
currentChar += newLoc;
|
|
if (currentChar > 97) {
|
|
currentChar -= currentChar - 96;
|
|
}
|
|
/*Serial.print(" calcPos: ");
|
|
Serial.print(newLoc);
|
|
Serial.print(" new: ");
|
|
Serial.print(currentChar);*/
|
|
charWheelStepper.step(newLoc);
|
|
delay(30);
|
|
hammer();
|
|
freshTape();
|
|
}
|
|
columnStepper.step(charWidth);
|
|
currentPos += charWidth;
|
|
}
|
|
|
|
void hammer() {
|
|
digitalWrite(hammerPin, HIGH);
|
|
delay(13);
|
|
digitalWrite(hammerPin, LOW);
|
|
}
|
|
|
|
void freshTape() {
|
|
unsigned long start = millis();
|
|
char backTime = 13;
|
|
digitalWrite(Motor2A, LOW);
|
|
while(digitalRead(headMotorLimitPin)){
|
|
digitalWrite(Motor2A, HIGH);
|
|
if (millis() - start > 1000) {
|
|
digitalWrite(Motor2A, LOW);
|
|
return;
|
|
}
|
|
}
|
|
digitalWrite(Motor2A, LOW);
|
|
}
|
|
|
|
void home() {
|
|
columnStepper.step(-currentPos);
|
|
currentPos = 0;
|
|
}
|
|
|
|
void lineFeed(){
|
|
unsigned long start = millis();
|
|
char backTime = 13;
|
|
digitalWrite(Motor1A, LOW);
|
|
digitalWrite(Motor1B, LOW);
|
|
while(!digitalRead(limitPin)){
|
|
digitalWrite(Motor1A, HIGH);
|
|
if (millis() - start > 1000) {
|
|
digitalWrite(Motor1A, LOW);
|
|
digitalWrite(Motor1B, HIGH);
|
|
delay(backTime);
|
|
digitalWrite(Motor1B, LOW);
|
|
return;
|
|
}
|
|
}
|
|
start = millis();
|
|
while(digitalRead(limitPin)){
|
|
digitalWrite(Motor1A, HIGH);
|
|
if (millis() - start > 1000) {
|
|
digitalWrite(Motor1A, LOW);
|
|
digitalWrite(Motor1B, HIGH);
|
|
delay(backTime);
|
|
digitalWrite(Motor1B, LOW);
|
|
return;
|
|
}
|
|
}
|
|
digitalWrite(Motor1A, LOW);
|
|
digitalWrite(Motor1B, HIGH);
|
|
delay(backTime);
|
|
digitalWrite(Motor1B, LOW);
|
|
|
|
}
|
|
|
|
void findHome() {
|
|
currentPos = 0;
|
|
currentChar = 0;
|
|
bool limit = 0;
|
|
lineFeed();
|
|
while (!limit) {
|
|
columnStepper.step(-1);
|
|
delay(3);
|
|
limit = digitalRead(limitPin);
|
|
}
|
|
charWheelStepper.step(-100);
|
|
columnStepper.step(20);
|
|
charWheelStepper.step(-1);
|
|
limit = digitalRead(limitPin);
|
|
if (limit) {
|
|
lineFeed();
|
|
Serial.print("Column limit error!");
|
|
findHome();
|
|
}
|
|
}
|
|
|
|
void releaseSteppers(){
|
|
for (int i = 4; i < 12; i++) {
|
|
digitalWrite(i, LOW);
|
|
}
|
|
}
|
|
|
|
uint8_t readKey() {
|
|
for (int i = 30; i < 39; i++) {
|
|
byte row = i -30;
|
|
pinMode(i, OUTPUT);
|
|
digitalWrite(i, LOW);
|
|
delay(5);
|
|
uint8_t input = PINA;
|
|
pinMode(i, INPUT);
|
|
digitalWrite(1, LOW);
|
|
|
|
for (int col = 0; col < 8; col++) {
|
|
bool set = !((input >> col) & 1);
|
|
bool last = !((lastKey[row] >> col) & 1);
|
|
if (set && !last) {
|
|
Serial.write(keyMap[row][7-col]);
|
|
}
|
|
}
|
|
lastKey[row] = input;
|
|
}
|
|
}
|