Índice:

Pan-Tilt Multi Servo Control: 11 etapas (com imagens)
Pan-Tilt Multi Servo Control: 11 etapas (com imagens)

Vídeo: Pan-Tilt Multi Servo Control: 11 etapas (com imagens)

Vídeo: Pan-Tilt Multi Servo Control: 11 etapas (com imagens)
Vídeo: Hacking Cameras - Arduino VISCA Controller for Pan, Tilt, Zoom and more! 2024, Novembro
Anonim
Pan-Tilt Multi Servo Control
Pan-Tilt Multi Servo Control

Neste tutorial, vamos explorar como controlar vários servos usando Python em um Raspberry Pi. Nosso objetivo será um mecanismo PAN / TILT para posicionar uma câmera (uma PiCam).

Aqui você pode ver como nosso projeto final funcionará:

Teste de loop de controle de servo-controle:

Imagem
Imagem

Etapa 1: BoM - Lista de materiais

Partes principais:

  1. Raspberry Pi V3 - US $ 32,00
  2. Módulo de vídeo da mini câmera OV5647 com sensor 1080p de 5 megapixels - US $ 13,00
  3. TowerPro SG90 9G Micro Servo 180 graus (2 X) - US $ 4,00
  4. Mini Pan / Tilt Camera Platform Anti-Vibration Mount para câmera com 2 Servos (*) - US $ 8,00
  5. Resistor 1K ohm (2X) - Opcional
  6. Diversos: peças de metal, bandas, etc (no caso de você construir seu mecanismo de Pan / Tilt)

(*) você pode comprar uma plataforma Pan / Tilt completa com os servos ou construir a sua própria.

Etapa 2: Como funciona o PWM

O Raspberry Pi não tem saída analógica, mas podemos simular isso, usando uma abordagem PWM (Modulação por largura de pulso). O que faremos é gerar um sinal digital com frequência fixa, onde alteraremos a largura do trem de pulso, o que será "traduzido" como um nível de tensão de saída "médio" conforme mostrado abaixo:

Imagem
Imagem

Podemos usar este nível de tensão "médio" para controlar o brilho de um LED, por exemplo:

Imagem
Imagem

Observe que o que importa aqui não é a frequência em si, mas o "Ciclo de trabalho", que é a relação entre o tempo que o pulso está "alto" dividido pelo período da onda. Por exemplo, suponha que iremos gerar uma frequência de pulso de 50 Hz em um de nossos GPIO Raspberry Pi. O período (p) será o inverso da frequência ou 20ms (1 / f). Se quisermos que nosso LED fique com "meio" de brilho, devemos ter um Ciclo de Trabalho de 50%, isso significa um "pulso" que será "Alto" por 10ms.

Este princípio será muito importante para nós, para controlarmos a posição do nosso servo, uma vez que o “Ciclo de Trabalho” definirá a posição do servo conforme mostrado abaixo:

Servo

Etapa 3: Instalando o Hw

Instalando o Hw
Instalando o Hw
Instalando o Hw
Instalando o Hw

Os servos serão conectados a uma fonte externa de 5 V, tendo seu pino de dados (no meu caso, a fiação amarela) conectado ao Raspberry Pi GPIO conforme abaixo:

  • GPIO 17 ==> Tilt Servo
  • GPIO 27 ==> Pan Servo

Não se esqueça de conectar os GNDs juntos ==> Raspberry Pi - Servos - Fonte de alimentação externa)

Você pode ter como opção, um resistor de 1K ohm entre o Raspberry Pi GPIO e o pino de entrada de dados do servidor. Isso protegeria seu RPi no caso de um problema com o servo.

Etapa 4: Calibração de Servos

Calibração de Servos
Calibração de Servos
Calibração de Servos
Calibração de Servos
Calibração de Servos
Calibração de Servos

A primeira coisa a fazer é confirmar as características principais de seus servos. No meu caso, estou usando um Power Pro SG90.

De sua folha de dados, podemos considerar:

  • Faixa: 180o
  • Fonte de alimentação: 4,8 V (5 VCC externo como uma fonte de alimentação USB funciona bem)
  • Frequência de trabalho: 50 Hz (Período: 20 ms)
  • Largura de pulso: de 1ms a 2ms

Em teoria, o servo estará em seu

  • Posição inicial (0 graus) quando um pulso de 1 ms é aplicado ao seu terminal de dados
  • Posição neutra (90 graus) quando um pulso de 1,5 ms é aplicado ao seu terminal de dados
  • Posição final (180 graus) quando um pulso de 2 ms é aplicado ao seu terminal de dados

Para programar uma posição servo usando Python será muito importante conhecer o "Ciclo de Trabalho" correspondente para as posições acima, vamos fazer alguns cálculos:

  • Posição inicial ==> (0 graus) Largura de pulso ==> 1ms ==> Ciclo de trabalho = 1ms / 20ms ==> 2,0%
  • Posição neutra (90 graus) Largura de pulso de 1,5 ms ==> Ciclo de trabalho = 1,5 ms / 20 ms ==> 7,5%
  • Posição final (180 graus) Largura de pulso de 2 ms ==> Ciclo de trabalho = 2ms / 20ms ==> 10%

Portanto, o ciclo de trabalho deve variar em uma faixa de 2 a 10%.

Vamos testar os servos individualmente. Para isso, abra seu terminal Raspberry e inicie seu editor de shell Python 3 como "sudo" (por causa de você deve ser um "superusuário" para lidar com GPIOs):

sudo python3

Em Python Shell

>>

Importe o módulo RPI. GPIO e chame-o de GPIO:

importar RPi. GPIO como GPIO

Defina quais esquemas de numeração de pinos você deseja usar (BCM ou BOARD). Fiz este teste com BOARD, então os pinos que usei foram os pinos físicos (GPIO 17 = Pin 11 e GPIO 27 Pin 13). Foi fácil para mim identificá-los e não cometer erros durante a prova (no programa final irei usar o BCM). Escolha o de sua preferência:

GPIO.setmode (GPIO. BOARD)

Defina o pino do servo que você está usando:

tiltPin = 11

Se, em vez disso, você usou o esquema BCM, os 2 últimos comandos devem ser substituídos por:

GPIO.setmode (GPIO. BCM)

tiltPin = 17

Agora, devemos especificar que este pino será uma "saída"

GPIO.setup (tiltPin, GPIO. OUT)

E, qual será a frequência gerada neste pino, que para o nosso servo será 50Hz:

tilt = GPIO. PWM (tiltPin, 50)

Agora, vamos começar a gerar um sinal PWM no pino com um ciclo de trabalho inicial (vamos mantê-lo "0"):

inclinação = início (0)

Agora, você pode inserir diferentes valores de ciclo de trabalho, observando o movimento do seu servo. Vamos começar com 2% e ver o que acontece (observamos que o servo vai para a "posição zero"):

tilt. ChangeDutyCycle (2)

No meu caso, o servo foi para a posição zero, mas quando mudei o ciclo de trabalho para 3% observei que o servo ficou na mesma posição, começando a se mover com ciclos de trabalho maiores que 3%. Portanto, 3% é minha posição inicial (o graus). O mesmo aconteceu com 10%, meu servo ficou acima desse valor, ultrapassando o limite em 13%. Portanto, para este servo em particular, o resultado foi:

  • 0 grau ==> ciclo de trabalho de 3%
  • 90 graus ==> ciclo de trabalho de 8%
  • 180 graus ==> ciclo de trabalho de 13%

Depois de terminar seus testes, você deve parar o PWM e limpar os GPIOs:

inclinação = parar ()

GPIO.cleanup ()

A tela de impressão do Terminal acima mostra o resultado para ambos os meus servos (que tem resultados semelhantes). Seu alcance pode ser diferente.

Etapa 5: Criação de um script Python

Criação de um script Python
Criação de um script Python

Os comandos PWM a serem enviados ao nosso servo estão em "ciclos de trabalho", como vimos na última etapa. Mas normalmente, devemos usar o "ângulo" em graus como parâmetro para controlar um servo. Portanto, devemos converter o "ângulo" que é uma medida mais natural para nós no ciclo de trabalho, conforme compreensível por nosso Pi.

Como fazer isso? Muito simples! Sabemos que a faixa do ciclo de trabalho vai de 3% a 13% e que isso é equivalente a ângulos que variam de 0 a 180 graus. Além disso, sabemos que essas variações são lineares, portanto, podemos construir um esquema proporcional conforme mostrado acima. então, dado um ângulo, podemos ter um ciclo de trabalho correspondente:

ciclo de serviço = ângulo / 18 + 3

Mantenha esta fórmula. Vamos usá-lo no próximo código.

Vamos criar um script Python para executar os testes. Basicamente, vamos repetir o que fizemos antes no Python Shell:

do tempo importar dormir

importar RPi. GPIO como GPIO GPIO.setmode (GPIO. BCM) GPIO.setwarnings (False) def setServoAngle (servo, ângulo): pwm = GPIO. PWM (servo, 50) pwm.start (8) dutyCycle = ângulo / 18. + 3. pwm. ChangeDutyCycle (dutyCycle) sleep (0.3) pwm.stop () if _name_ == '_main_': import sys servo = int (sys.argv [1]) GPIO.setup (servo, GPIO. OUT) setServoAngle (servo, int (sys.argv [2])) GPIO.cleanup ()

O núcleo do código acima é a função setServoAngle (servo, ângulo). Esta função recebe como argumentos, um número de servo GPIO e um valor de ângulo para onde o servo deve ser posicionado. Uma vez que a entrada desta função é "ângulo", devemos convertê-la para o ciclo de trabalho em porcentagem, usando a fórmula desenvolvida anteriormente.

Quando o script é executado, você deve inserir como parâmetros, servo GPIO e ângulo.

Por exemplo:

sudo python3 angleServoCtrl.py 17 45

O comando acima posicionará o servo conectado no GPIO 17 com 45 graus em "elevação". Um comando semelhante pode ser usado para o controle Pan Servo (posição a 45 graus em "azimute"):

sudo python angleServoCtrl.py 27 45

O arquivo angleServoCtrl.py pode ser baixado do meu GitHub

Etapa 6: O Mecanismo Pan-Tilt

O Mecanismo Pan-Tilt
O Mecanismo Pan-Tilt

O servo "Pan" irá mover "horizontalmente" nossa câmera ("ângulo de azimute") e nosso servo "Tilt" irá movê-la "verticalmente" (ângulo de elevação).

A imagem abaixo mostra como funciona o mecanismo Pan / Tilt:

Imagem
Imagem

Durante nosso desenvolvimento, não iremos a "extremos" e usaremos nosso mecanismo Pan / Tilt de 30 a 150 graus apenas. Esse intervalo será suficiente para ser usado com uma câmera.

Etapa 7: O Mecanismo Pan-Tilt - Construção Mecânica

O Mecanismo Pan-Tilt - Construção Mecânica
O Mecanismo Pan-Tilt - Construção Mecânica
O Mecanismo Pan-Tilt - Construção Mecânica
O Mecanismo Pan-Tilt - Construção Mecânica
O Mecanismo Pan-Tilt - Construção Mecânica
O Mecanismo Pan-Tilt - Construção Mecânica

Vamos agora, montar nossos 2 servos como um mecanismo Pan / Tilt. Você pode fazer 2 coisas aqui. Compre um mecanismo de plataforma Pan-Tilt como o mostrado na última etapa ou construa o seu próprio de acordo com suas necessidades.

Um exemplo pode ser o que eu construí, apenas prendendo os servos uns aos outros, e usando pequenas peças de metal de brinquedos antigos como mostrado nas fotos acima.

Etapa 8: Conjunto de pan / tilt elétrico

Conjunto de pan / tilt elétrico
Conjunto de pan / tilt elétrico
Conjunto de pan / tilt elétrico
Conjunto de pan / tilt elétrico
Conjunto de pan / tilt elétrico
Conjunto de pan / tilt elétrico
Conjunto de pan / tilt elétrico
Conjunto de pan / tilt elétrico

Depois de ter seu mecanismo Pan / Tilt montado, siga as fotos para a conexão elétrica completa.

  1. Desligue seu Pi.
  2. Faça todas as conexões elétricas.
  3. Verifique novamente.
  4. Ligue seu Pi primeiro.
  5. Se tudo estiver OK, ligue seus servos.

Não exploraremos neste tutorial como configurar a câmera, isso será explicado no próximo tutorial.

Etapa 9: o script Python

Vamos criar um script Python para controlar os dois servos simultaneamente:

do tempo importar dormir

importar RPi. GPIO como GPIO GPIO.setmode (GPIO. BCM) GPIO.setwarnings (False) pan = 27 tilt = 17 GPIO.setup (tilt, GPIO. OUT) # white => TILT GPIO.setup (pan, GPIO. OUT) # cinza ==> PAN def setServoAngle (servo, ângulo): afirmar ângulo> = 30 e ângulo 90 (ponto médio) ==> 150 setServoAngle (tilt, int (sys.argv [2])) # 30 ==> 90 (ponto médio) ==> 150 GPIO.cleanup ()

Quando o script é executado, você deve inserir como parâmetros, ângulo de panorâmica e ângulo de inclinação. Por exemplo:

sudo python3 servoCtrl.py 45 120

O comando acima posicionará o mecanismo de Pan / Tilt com 45 graus em "azimute" (ângulo de panorâmica) e 120 graus de "elevação" (ângulo de inclinação). Observe que, se nenhum parâmetro for inserido, o padrão será ambos, ângulos de panorâmica e inclinação configurados em 90 graus.

Abaixo você pode ver alguns testes:

Imagem
Imagem

O arquivo servoCtrl.py pode ser baixado do meu GitHub.

Etapa 10: Teste de Loop de Servidores

Vamos agora criar um script Python para testar automaticamente toda a gama de servos:

do tempo importar dormir

importar RPi. GPIO como GPIO GPIO.setmode (GPIO. BCM) GPIO.setwarnings (False) pan = 27 tilt = 17 GPIO.setup (tilt, GPIO. OUT) # white => TILT GPIO.setup (pan, GPIO. OUT) # cinza ==> PAN def setServoAngle (servo, ângulo): afirmar ângulo> = 30 e ângulo <= 150 pwm = GPIO. PWM (servo, 50) pwm.start (8) dutyCycle = ângulo / 18. + 3. pwm. ChangeDutyCycle (dutyCycle) sleep (0.3) pwm.stop () if _name_ == '_main_': para i no intervalo (30, 160, 15): setServoAngle (pan, i) setServoAngle (tilt, i) para i em intervalo (150, 30, -15): setServoAngle (pan, i) setServoAngle (tilt, i) setServoAngle (pan, 100) setServoAngle (tilt, 90) GPIO.cleanup ()

O programa executará automaticamente um loop de 30 a 150 graus em ambos os ângulos.

Abaixo o resultado:

Eu conectei um osciloscópio apenas para ilustrar a teoria PWM conforme explicado anteriormente.

Imagem
Imagem

O código acima, servoTest.py, pode ser baixado do meu GitHub.

Etapa 11: Conclusão

Conclusão
Conclusão

Como sempre, espero que este projeto possa ajudar outras pessoas a encontrar seu caminho para o emocionante mundo da eletrônica!

Para obter detalhes e o código final, visite meu depósito no GitHub: RPi-Pan-Tilt-Servo-Control

Para mais projetos, visite meu blog: MJRoBot.org

Abaixo, um vislumbre do meu próximo tutorial:

Imagem
Imagem

Saludos do sul do mundo!

Vejo você no meu próximo instrutível!

Obrigado, Marcelo

Recomendado: