Advanced Motor Control

Note: The wiring for this is very important. Please double-check your connections before proceeding.


In [ ]:
# Import GPIO Libraries
import RPi.GPIO as GPIO
import time

The pin configuration is dependent on the motor and wiring setup. The following code works for my current wiring setup with two motors and controllers (12V stepper motors and L293D H-Bridge driven with an 8 AA battery pack)


In [ ]:
GPIO.setmode(GPIO.BCM)

coil_A_1_pin = 18
coil_A_2_pin = 23
coil_B_1_pin = 24
coil_B_2_pin = 17

coil_C_1_pin = 16
coil_C_2_pin = 21
coil_D_1_pin = 12
coil_D_2_pin = 20

GPIO.setup(coil_A_1_pin, GPIO.OUT)
GPIO.setup(coil_A_2_pin, GPIO.OUT)
GPIO.setup(coil_B_1_pin, GPIO.OUT)
GPIO.setup(coil_B_2_pin, GPIO.OUT)

GPIO.setup(coil_C_1_pin, GPIO.OUT)
GPIO.setup(coil_C_2_pin, GPIO.OUT)
GPIO.setup(coil_D_1_pin, GPIO.OUT)
GPIO.setup(coil_D_2_pin, GPIO.OUT)

reverse_seq = ['1010', '0110', '0101', '1001']
forward_seq = list(reverse_seq) # to copy the list
forward_seq.reverse()

In [ ]:
def m1_forward(delay, steps):
    for i in range(steps):
        for step in forward_seq:
            m1_set_step(step)
            time.sleep(delay)

def m1_backwards(delay, steps):
    for i in range(steps):
        for step in reverse_seq:
            m1_set_step(step)
            time.sleep(delay)


def m1_set_step(step):
    GPIO.output(coil_A_1_pin, step[0] == '1')
    GPIO.output(coil_A_2_pin, step[1] == '1')
    GPIO.output(coil_B_1_pin, step[2] == '1')
    GPIO.output(coil_B_2_pin, step[3] == '1')

    
def m2_forward(delay, steps):
    for i in range(steps):
        for step in forward_seq:
            m2_set_step(step)
            time.sleep(delay)

def m2_backwards(delay, steps):
    for i in range(steps):
        for step in reverse_seq:
            m2_set_step(step)
            time.sleep(delay)


def m2_set_step(step):
    GPIO.output(coil_C_1_pin, step[0] == '1')
    GPIO.output(coil_C_2_pin, step[1] == '1')
    GPIO.output(coil_D_1_pin, step[2] == '1')
    GPIO.output(coil_D_2_pin, step[3] == '1')

In [ ]:
m1_set_step('0000')
m2_set_step('0000')
delay = 20 # Time Delay (ms)
steps = 5

m1_forward(int(delay) / 1000.0, int(steps))
m2_forward(int(delay) / 1000.0, int(steps))
m1_backwards(int(delay) / 1000.0, int(steps))

# release the motors from a 'hold' position
m1_set_step('0000')
m2_set_step('0000')

In [ ]:
import numpy as np

In [ ]:
x = np.arange(0, 6*np.pi, 0.1)

In [ ]:
y = np.sin(x)

In [ ]:
x_scaled = x * 20
y_scaled = y * 60

In [ ]:
x_moves = np.array(x_scaled[1:]-x_scaled[:-1], dtype=int)
y_moves = np.array(y_scaled[1:]-y_scaled[:-1], dtype=int)

In [ ]:
def draw_etch(x_moves, y_moves, delay=5):
    d = delay/1000.0
    
    for i in range(len(x_moves)):
        if x_moves[i]>0:
            m2_forward(d, x_moves[i])
        elif x_moves[i]<0:
            m2_backwards(d, -x_moves[i])
        if y_moves[i]>0:
            m1_forward(d, y_moves[i])
        elif y_moves[i]<0:
            m1_backwards(d, -y_moves[i])
        
    m1_set_step('0000')
    m2_set_step('0000')

In [ ]:
draw_etch(x_moves, y_moves)

Can we plot an Image with this thing?


In [ ]:
# import a bunch of stuff that we'll use to manipulate our images...
from skimage.io import imread
from skimage import filter
import numpy as np

from bokeh.plotting import figure, show
from bokeh.io import output_notebook

output_notebook()

In [ ]:
test_image = imread("img/snapshot-2.jpg", as_grey=True)

In [ ]:
p = figure(plot_width=480, plot_height=320, x_range=(0, 10), y_range=(0, 10))
p.image(image=[test_image[::-1]], x=[0], y=[0], dw=[10], dh=[10])

In [ ]:
show(p)

In [ ]:
from scipy.ndimage.interpolation import zoom
import random

In [ ]:
test_rescaled = zoom(test_image,zoom=0.1)

In [ ]:
test_rescaled.shape

In [ ]:
p2 = figure(plot_width=480, plot_height=320, x_range=(0, 10), y_range=(0, 10))
p2.image(image=[test_rescaled[::-1]], x=[0], y=[0], dw=[10], dh=[10])

In [ ]:
show(p2)

In [ ]:
#reverse every other line
odd_rows = test_rescaled[::2]
print "odd: %s" % (str(odd_rows.shape))
even_rows = test_rescaled[1::2]
print "even: %s" % (str(even_rows.shape))

In [ ]:
flipped_evens =  np.fliplr(even_rows)

In [ ]:
interleaved = np.empty((odd_rows.shape[0]+even_rows.shape[0],odd_rows.shape[1]))
interleaved[::2,:] = odd_rows
interleaved[1::2,:] = flipped_evens

In [ ]:
interleaved.shape

In [ ]:
p3 = figure(plot_width=480, plot_height=320, x_range=(0, 10), y_range=(0, 10))
p3.image(image=[interleaved[::-1]], x=[0], y=[0], dw=[10], dh=[10])

In [ ]:
show(p3)

In [ ]:
d = 10/1000.
flat_img = interleaved.flatten()
pixel_width = 4
pixel_height = 4
image_width = 72
x = np.ones(len(flat_img))
#print flat_img[:20]
y_jitter = np.array(flat_img*5, dtype=int)
#print y_jitter[:100]

direction = 1
count = 0
for i in range(len(x)):
    
    if count>=image_width:
        direction = direction * -1
        m1_backwards(d, 2 * pixel_height)
        count = 0
    
    if direction>0:
        for j in range(pixel_width):
            if y_jitter[i] == 0:
                m2_forward(d, 4)
            elif y_jitter[i] == 1:
                m2_forward(d, 2)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 2)
            elif y_jitter[i] == 2:
                m2_forward(d, 1)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 2)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 1)
            elif y_jitter[i] == 3:
                m2_forward(d, 1)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 1)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 1)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 1)
            else:
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 1)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 1)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 1)
                m1_forward(d, 4)
                m1_backwards(d, 8)
                m1_forward(d, 4)
                m2_forward(d, 1)
                
    else:
        m2_backwards(d, 1)

In [ ]: