1

Some pins (eg, GPIO 17, GPIO 26) don't work when using pigpio. I launch pigpio deamon using sudo pigpio -x -1 to enable all pins, but the two mentioned earlier don't work as they should - I had it connected to the direction pin for step motor driver - pins stay low.

pigpio code:

from time import sleep
import pigpio
from math import *

class Read:
    def __init__(self):
        self.direction_pin = 26
        self.step_pin = 27
        self.microstep0_pin = 10
        self.microstep1_pin = 9
        self.microstep2_pin = 11
        self.en_pin = 4
        self.sleep_pin = 14
        self.reset_pin = 15

        self.steps_per_rev = 6400                       # microsteping if enabled
        self.motor_enable, self.motor_disable = 0, 1        # default state of the pin_ena
        self.stepper_speed_mmps = 30                    # mm per sec
        self.step_delay = 10*10e-9                  # specified by stepper driver in usec
        self.UP, self.DOWN = 1, 0
        self.pos = 0
        self.direction = self.UP
        self.target_pos, self.target_pos_mm = 0, 0
        self.mm_per_rv = 40*pi                      # wheel length
        self.step_per_mm = self.steps_per_rev/self.mm_per_rv
        self.max_speed_mmps = 1000/self.step_per_mm     # 111 mm per sec for current setup

        self.pi = pigpio.pi()

        self.pi.write(self.direction_pin, self.direction)
        self.pi.set_mode(self.en_pin, pigpio.OUTPUT)
        self.pi.set_mode(self.direction_pin, pigpio.OUTPUT)
        self.pi.set_mode(self.step_pin, pigpio.OUTPUT)
        self.pi.set_mode(self.microstep0_pin, pigpio.OUTPUT)
        self.pi.set_mode(self.microstep1_pin, pigpio.OUTPUT)
        self.pi.set_mode(self.microstep2_pin, pigpio.OUTPUT)
        self.pi.set_mode(self.sleep_pin, pigpio.OUTPUT)
        self.pi.set_mode(self.reset_pin, pigpio.OUTPUT)
        self.pi.write(self.en_pin, self.motor_disable)
        self.pi.write(self.microstep0_pin, 1)
        self.pi.write(self.microstep1_pin, 1)
        self.pi.write(self.microstep2_pin, 1)
        self.pi.write(self.sleep_pin, 1)
        self.pi.write(self.reset_pin, 1)
        

        self.eject_distance = 126.4  # mm
        self.distance_to_measure = 38.1+49.6+1  # mm
        self.one_step_1_32_mm = 125.9/6400
        self.distance_between_fields = 7.75  # mm
        self.steps_eject = int(self.eject_distance/self.one_step_1_32_mm)
        self.steps_init = int(self.distance_to_measure/self.one_step_1_32_mm)
        self.steps_to_go = int(
            self.distance_between_fields/self.one_step_1_32_mm)
        self.distance_back = self.distance_between_fields*10+self.distance_to_measure
        self.steps_back = self.steps_to_go*10+self.steps_init
        self.eject_flag = False

    def constrain(self, val, min_v, max_v):
        if val < min_v:
            val = min_v
        elif val > max_v:
            val = max_v
        else:
            pass
        return val

    def step(self):
        self.pi.write(self.step_pin, 1)
        sleep(self.step_delay)
        self.pi.write(self.step_pin, 0)

    def move_relative(self, stepper_speed_mmps, target_pos_mm):
        # global pos, direction, target_pos
        dr = -1 if target_pos_mm < 0 else 1
        delta_pos = ceil(abs(target_pos_mm)*self.step_per_mm)*dr
        self.target_pos = self.pos + delta_pos
        # stepper_speed_mmps = round(
        #     self.constrain(stepper_speed_mmps, 1, self.max_speed_mmps-1))
        stepper_speed = stepper_speed_mmps*self.step_per_mm
        pulse_delay = (1/stepper_speed) - self.step_delay

        # checking direction
        previous_direction = self.direction
        self.direction = self.UP if (self.target_pos > self.pos) else self.DOWN
        if (self.direction != previous_direction):
            self.pi.write(self.direction_pin, self.direction)
            sleep(self.step_delay)
            print("Direction changed")
        else:
            pass

        print("Initializing movement from pos: {}, to pos: {}".format(
            self.pos, self.target_pos))

        self.pi.write(self.en_pin, self.motor_enable)

        while self.pos != self.target_pos:
            self.step()
            sleep(pulse_delay)
            self.pos = (self.pos+1) if self.direction else (self.pos-1)

        print("arrived at position: ", self.pos)
        self.pi.write(self.en_pin, self.motor_disable)



    def test_motor(self):
        self.move_relative(self.stepper_speed_mmps,
                           self.eject_distance)
        self.move_relative(self.stepper_speed_mmps,
                           -self.eject_distance)



if __name__ == "__main__":
    aaa = Read()
    aaa.test_motor()

This correctly prints "Direction changed" when it was changed - but the motor direction doesn't actually change - pin stays low.

Problem doesn't exist when I use RPi.GPIO lib with the RpiMotorLib:

self.motor = RpiMotorLib.A4988Nema(self.direction_pin, self.step_pin, (
            self.microstep0_pin, self.microstep1_pin, self.microstep2_pin), "DRV8825")
self.motor.motor_go(True, "1/32", 6400, .0005, False, .05)
                sleep(0.1)
self.motor.motor_go(False, "1/32", 6400, .0005, False, .05)

I included parts of the code, direction pin is the same in both examples.

Update: This makes completely no sense to me, but when I open python3 from terminal, and try to write to this pin - it works fine. But in my code suddenly it doesn't.

4
  • Please edit your question and include the pigpio code which does not work and the RPi.GPIO code which works.
    – joan
    Commented Oct 21, 2022 at 9:48
  • @joan Just edited - hope that's enough Commented Oct 21, 2022 at 10:16
  • Thanks. Need more context though. Need to see how everything is initialised. Can you share the complete code?
    – joan
    Commented Oct 21, 2022 at 10:28
  • @joan sure, just did Commented Oct 21, 2022 at 10:38

1 Answer 1

1

pigpio does not assign a level to a GPIO when you open it for output. It is left at the last level.

I expect this is what causes the behaviour you are seeing.

You need to initialise the level.

e.g.

self.pi.write(self.direction_pin, self.direction)
self.pi.set_mode(self.direction_pin, pigpio.OUTPUT)
3
  • I don't understand. Mode on this pin is set when initializing class instance. Then I change state. I don't exactly care whats the state of the pin on the start, because i change it every time I use method move_relative - the problem is that the line self.pi.write(self.direction_pin, self.direction) in method move_relative doesn't change the state on the pin Commented Oct 21, 2022 at 14:22
  • The direction pin is an OUPUT pin. You need to set the direction pin level to 0 or 1. At the moment you leave the pin at the level it was before the program starts.
    – joan
    Commented Oct 21, 2022 at 14:27
  • This only needs to be done in the initialisation section when you do all the mode settings. You do actually give levels to most of the pins already.
    – joan
    Commented Oct 21, 2022 at 14:35

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.