Dando movimento aos “olhos da segurança” de forma automática…
Continuando com os aprimoramentos do ‘controlador de servos’ para uso com suporte Pan Tilt para câmeras, foi pensado na possibilidade de fazer os movimentos horizontais de forma automática (esquerda e direita), como uma varredura no campo visual. Isto permitirá visualizar eventos em vários ângulos continuamente. Veja o novo esquema abaixo:
Conforme se observa no esquema, foi acrescentado um interruptor nomeado de ‘VARREDURA’ e um led indicador desta função. Ao ser pressionado uma vez, liga o led e começa o processo de deslocar o servo gradativamente para um lado e depois inverte o movimento até o ínicio. Isto se repetirá até o botão ‘VARREDURA’ ser pressionado novamente, quando então apagará o led e os servos irão para a posição determinada pelos potenciômetros horizontal e vertical ( potenciômetro do Joy Stick PS ou similar). Se acionamos para alterar a posição vertical, quer seja para cima ou baixo, e ao encontrar a posição desejada pressionamos o botão ‘VARREDURA’, então ficará gravado esta posição vertical e começará a varredura horizontal. Quando ocorrer um reset na alimentação este valor será perdido e a varredura será desligada.
Nos ‘defines’ do arquivo “C” pode ser alterados para dar os movimentos desejados (curso max e min) e velocidade de operação. Veja eles abaixo:
//limites de excursão dos servos horizontais e verticais
#define lim_minv 85 //determina o limite horário max. do servo vertical
#define lim_minh 65 //determina o limite horário max. do servo horizontal
#define lim_maxv 180 //determina o limite anti-horário max. do servo vertical
#define lim_maxh 180 //determina o limite anti-horário max. do servo horizontal
#define lim_initv 105 //posição pós reset do servo vertical
#define lim_inith 105 //posição pós reset do servo horizontal
#define p_total 220 //determina o periodo total (aprox.18 ms))
#define vel_inc 5 //determina a velocidade de reação dos joystick
#define vel_varr 70 //velocidade em modo varredura
#define v_estab 10 // estabiliza contra variações da leitura do AD
Tem se notado na prática, que alguns modelos tem cursos diferentes com o mesmo pulso. Cada hobista deve se certificar que os ajustes acima satisfazem corretamente para o modelo usado.
Depois de alterar, não esqueça de recompilar usando o MplabX_Ide, e usar o novo arquivo Hex gerado.
Os potenciômetros devem ser montados próximos ao pic, enquanto as saídas dos servos podem ser levadas por uma distância considerável, por meio de cabos blindado de 3 fios, até o servomotor. Use uma fonte de alimentação de 5 volts para alimentar o circuito.
Obs. Esta montagem é de natureza didática, sendo realizada apenas em placa de montagem experimentais (do tipo Protoboard), sujeito a bugs ainda não observados. Esta sendo fornecido os arquivos desta montagem, podendo ser alterados conforme a necessidade dos hobistas.
Atenção: Antes de fazer placa de circuito impresso, teste em placa de montagem experimental e veja se o circuito atende as suas necessidades.
Segue pasta com os arquivos desta montagem, compilados com MplabX (XC8 Compiler):
Manuais:
PIC12F675
servomotor
Pan Tilt Camera
Curiosidades:
O Concorde entrou para a história da aviação
Museus — lugares interessantes para visitar
Sua Vida É Controlada Pelo Destino?
A Bíblia contém um código oculto?
Como enfrentar a ameaça terrorista
De onde vieram as instruções?
A estabilidade e a satisfação no trabalho sofrem ameaças
Em busca da sociedade perfeita
“Como nos lembramos . . . do alho!”
A doença mais temida do século 19
Cabras — a salvação dos fazendeiros no sertão
As catacumbas de Odessa — um labirinto subterrâneo
Outros assuntos:
Por que Deus permitiu o Holocausto?
Os desastres naturais são castigo de Deus?
Qual é o sentido da vida?
Por que as pessoas morrem?
Como superar o medo da morte?
O que é a alma?
Será que temos data marcada para morrer?
As experiências de quase morte são visões de outra vida?
A alma é imortal?
Quem vai para o inferno?
A mentira que tornou Deus cruel
O que é a ressurreição?
O que é a fera de sete cabeças de Apocalipse capítulo 13?
O que é a batalha do Armagedom?
Vídeos Educativos para assistir com seus filhos pequenos
Até o próximo artigo!!!
Olá Cláudio, bom dia!
Tire mais uma dúvida por favor… Fiz o esquema na protoboard, funcionou bem, só que o servo só funciona de um lado no potenciômetro. Exemplo: Colocando o potenciômetro todo pra cima o servo horizontal desloca todo para a esquerda e na medida que vou voltando o potenciômetro o servo volta ao lugar normal, parecendo não ir pra direita. Esse ajuste eu faço no trecho que o Sr. deixou no artigo? Qual compilador o Sr. usa? Mais uma vez muito obrigado ! 😀
Olá Gerson!
Nesta montagem foi usado o Mplab X XC8.
Cláudio
ok!larios no esquema é o pic 12f675 vou testar.muito obrigado pela força, sucesso.
olá larios queria saber se é possivel transformar esse codigo em hex,já tentei copilar mais sempre dar erro nao sei quem é o autor.Trata-se um drive de servo ou seja ele converte o pwm (1a2ms) e aciona o motor .
é um projeto para hobista que querem como eu construir seus proprio servo motor!!
codigo
#include
#fuses INTRC_IO,NOWDT,NOPUT //,NOBROWNOUT
#use delay(clock=4000000)
#use fast_io(a)
#use rs232(baud=9600, xmit=PIN_A2)
//analog implementation
//AN0=target
//AN1=potentiomenter
//driver type:
//type 0: ch0-left, ch1-right,
//type 1: ch0-on/off, ch1-direction
#define driver_type 0
//output (type=0)
#define motorL PIN_A4
#define motorR PIN_A5
//output (type=1)
#define motorON PIN_A4
#define motorDIR PIN_A5
//PID
#define Kp 0.2 * 16
#define Ki 0.0 * 16
#define Kd 0.0 * 16
#define dead_band 1
#define offset 30
#define max_pwm 240
#define max_integration 20000
#define derivate_dead_band 10
#byte ADRESH=0x1e
#byte ADRESL=0x9e
#byte ADCON0=0x1f
#byte ANSEL=0x9f
#define get_analog(var) #asm \
movf ADRESL,w \
movwf &var \
movf ADRESH,w \
movwf &var+1 \
#endasm
#define neg16(a) #asm \
COMF a,F \
COMF &a+1,F \
INCF a,F \
BTFSC 03,2 \
INCF &a+1,F \
#endasm
#define txd16(dato) putc((int)dato); putc((int)(dato>>8))
//long BARG;
#define sgn16(i) (bit_test(i,15))
int sign;
int16 target,pot,e,pwm,tmp,prev_e=0,derivate,integration=0;
void main()
{
int cont;
set_tris_a(0b00001011);
ANSEL=0b00010011; //0:nc, 001:fosc/8, 0011:DDAA
#if driver_type==0
output_low(motorL); output_low(motorR);
#else
output_low(motorON);
#endif
while(true) //bucle
{
//Get analog channels
//TARGET
ADCON0=0b10000001; //1: Right, 0: vref=5v, 00:NC, 00: ch=0, 1: start, 1: AD_ON
delay_us(100);
bit_set(ADCON0,1); //start
while(bit_test(ADCON0,1));
get_analog(target);
//POTENTIOMETER
ADCON0=0b10000101; //1: Right, 0: vref=5v, 00:NC, 01: ch=1, 1: start, 1: AD_ON
delay_us(100);
bit_set(ADCON0,1); //start
while(bit_test(ADCON0,1));
get_analog(pot);
//** IMPLEMENTS PID *******
pwm=0;
e=target-pot; //error
derivate=e-prev_e; prev_e=e; //derivate
if((e>dead_band) || (e+dead_band>4;
if (sign) neg16(pwm);
//Kd
sign=false;
if (sgn16(derivate)) { sign=true; neg16(derivate); }
if(derivate>derivate_dead_band)
{
tmp=derivate*Kd; //tmp=tmp>>4;
if (sign) neg16(tmp);
pwm=pwm+tmp;
}
}
//Ki
sign=false;
if (sgn16(integration)) { sign=true; neg16(integration); }
if (integration>max_integration) integration=max_integration; //check limits
tmp=integration; tmp=tmp>>4;
tmp=tmp*Ki; tmp=tmp>>4;
if (sign) {neg16(tmp); neg16(integration) }
pwm=pwm+tmp;
tmp=pwm;
if(pwm)
{
if(sgn16(tmp))
{
//negative
#if driver_type==0
output_high(motorL);
#else
output_high(motorON);
output_high(motorDIR);
#endif
neg16(tmp);
}
else
{
//positive
#if driver_type==0
output_high(motorR);
#else
output_high(motorON);
output_low(motorDIR);
#endif
}
tmp+=offset;
if(tmp>max_pwm) tmp=max_pwm;
}
//************************
//implements PWM
for(cont=0;cont<255;cont++)
{
delay_us(50);
if ((int)tmp==cont)
{
#if driver_type==0
output_low(motorL); output_low(motorR);
#else
output_low(motorON);
#endif
}
}
#if driver_type==0
output_low(motorL); output_low(motorR);
#else
output_low(motorON);
#endif
/* //monitor
putc('0'); txd16(POT);
putc(0x3c); txd16(TARGET);
putc(0x3d); txd16(PWM);
*/
} //while(1)
}
endereço da imagem
https://lh3.googleusercontent.com/XtoVKgDyEFR_Aw1Hu11MLnD02bdXUnXlstgMZ1A9ffgqJlpiJj-Y57GGVVwa-qdfxn5G=s123
Olá Morais!
Parece que está faltando o ‘include’ com o tipo de microcontrolador. Pelo esquema no link que me passou não dá para enxergar nada, nem o tipo de microcontrolador.
Na suposição que esteja usando o 12f675, consegui compilar conforme abaixo:
#include <12F675.h>//supondo que seja o 12f675
//#device adc=10
#fuses INTRC_IO,NOWDT,NOPUT //,NOBROWNOUT
#use delay(clock=4000000)
#use fast_io(a)
#use rs232(baud=9600, xmit=PIN_A2)
//analog implementation
//AN0=target
//AN1=potentiomenter
//driver type:
//type 0: ch0-left, ch1-right,
//type 1: ch0-on/off, ch1-direction
#define driver_type 0
//output (type=0)
#define motorL PIN_A4
#define motorR PIN_A5
//output (type=1)
#define motorON PIN_A4
#define motorDIR PIN_A5
//PID
#define Kp 0.2 * 16
#define Ki 0.0 * 16
#define Kd 0.0 * 16
#define dead_band 1
#define offset 30
#define max_pwm 240
#define max_integration 20000
#define derivate_dead_band 10
#byte ADRESH=0x1e
#byte ADRESL=0x9e
#byte ADCON0=0x1f
#byte ANSEL=0x9f
#define get_analog(var) #asm \
movf ADRESL,w \
movwf &var \
movf ADRESH,w \
movwf &var+1 \
#endasm
#define neg16(a) #asm \
COMF a,F \
COMF &a+1,F \
INCF a,F \
BTFSC 03,2 \
INCF &a+1,F \
#endasm
#define txd16(dato) putc((int)dato); putc((int)(dato>>8))
//long BARG;
#define sgn16(i) (bit_test(i,15))
int sign;
int16 target,pot,e,pwm,tmp,prev_e=0,derivate,integration=0;
void main()
{
int cont;
set_tris_a(0b00001011);
ANSEL=0b00010011; //0:nc, 001:fosc/8, 0011:DDAA
#if driver_type==0
output_low(motorL); output_low(motorR);
#else
output_low(motorON);
#endif
while(true) //bucle
{
//Get analog channels
//TARGET
ADCON0=0b10000001; //1: Right, 0: vref=5v, 00:NC, 00: ch=0, 1: start, 1: AD_ON
delay_us(100);
bit_set(ADCON0,1); //start
while(bit_test(ADCON0,1));
get_analog(target);
//POTENTIOMETER
ADCON0=0b10000101; //1: Right, 0: vref=5v, 00:NC, 01: ch=1, 1: start, 1: AD_ON
delay_us(100);
bit_set(ADCON0,1); //start
while(bit_test(ADCON0,1));
get_analog(pot);
//** IMPLEMENTS PID *******
pwm=0;
e=target-pot; //error
derivate=e-prev_e; prev_e=e; //derivate
if((e>dead_band) || (e+dead_band>4));
if (sign) neg16(pwm);
//Kd
sign=false;
if (sgn16(derivate)) { sign=true; neg16(derivate); }
if(derivate>derivate_dead_band)
{
tmp=derivate*Kd; //tmp=tmp>>4;
if (sign) neg16(tmp);
pwm=pwm+tmp;
}
}
//Ki
sign=false;
if (sgn16(integration)) { sign=true; neg16(integration); }
if (integration>max_integration) integration=max_integration; //check limits
tmp=integration; tmp=tmp>>4;
tmp=tmp*Ki; tmp=tmp>>4;
if (sign) {neg16(tmp); neg16(integration) }
pwm=pwm+tmp;
tmp=pwm;
if(pwm)
{
if(sgn16(tmp))
{
//negative
#if driver_type==0
output_high(motorL);
#else
output_high(motorON);
output_high(motorDIR);
#endif
neg16(tmp);
}
else
{
//positive
#if driver_type==0
output_high(motorR);
#else
output_high(motorON);
output_low(motorDIR);
#endif
}
tmp+=offset;
if(tmp>max_pwm) tmp=max_pwm;
}
//************************
//implements PWM
for(cont=0;cont<255;cont++)
{
delay_us(50);
if ((int)tmp==cont)
{
#if driver_type==0
output_low(motorL); output_low(motorR);
#else
output_low(motorON);
#endif
}
}
#if driver_type==0
output_low(motorL); output_low(motorR);
#else
output_low(motorON);
#endif
/* //monitor
putc('0'); txd16(POT);
putc(0x3c); txd16(TARGET);
putc(0x3d); txd16(PWM);
*/
} //while(1)
//}
gerando o seguinte hex:
:1000000000308A0004280000FF238316900000308F
:100010008A000A2884011F3083051F08BF399F000A
:1000200083161F08F0390F389F00073083129F0096
:100030000515B001B101B401B5010B3065001330F5
:1000400083169F0083120512851281309F00213094
:10005000A000A00B29289F149F182C2883161E0887
:100060008312A6001E08A70085309F002130A00043
:10007000A00B38289F149F183B2883161E08831254
:10008000A8001E08A900AD01AC0128082602AA009C
:100090002708AB002908031C290FAB0230082A02ED
:1000A000B2002B08B3003108031C310FB3022B0838
:1000B000B1002A08B000AB08031D70282A08013CD3
:1000C000031C702801302A07B7002B08B80003185A
:1000D000B80AB808031D70283708043C031C7028B0
:1000E000A50803197828AC09AD09AC0A0319AD0AB3
:1000F000A501B31F82280130A500B209B309B20AD5
:100100000319B30AB308031D892832080A3C0318EF
:100110009928AF01AE01A50803199328AE09AF09CC
:10012000AE0A0319AF0A2E08AC070318AD0A2F0850
:10013000AD072528A501B51FA4280130A500B409E5
:10014000B509B40A0319B50A35084D3C0318B3289C
:10015000FF3A031DAF283408203C0318B3284E3063
:10016000B5002030B4003508AF003408AE00AF0C45
:10017000AE0CAF0CAE0CAF0CAE0CAF0CAE0C0F3027
:10018000AF05AF01AE01AF0CAE0CAF0CAE0CAF0CB7
:10019000AE0CAF0CAE0CAF05A5080319D928AE09FB
:1001A000AF09AE0A0319AF0AB409B509B40A0319B5
:1001B000B50A2E08AC070318AD0A2F08AD072D08A5
:1001C000AF002C08AE002C082D040319FF28AF1F28
:1001D000F0280516AE09AF09AE0A0319AF0AF128D7
:1001E00085161E30AE070318AF0AAF08031DFC28A2
:1001F0002E08F03C0318FF28AF01F030AE00B60126
:10020000360F032910291030A000A00B052900008B
:1002100036082E02031D0E2905128512B60A002982
:06022000051285126300C7
:02400E00F43983
:00000001FF
;PIC12F675
Mas como não sei o esquema, nem tenho certeza do pic usado, não posso afirmar que vá funcionar. Fica por sua conta e risco.
Cláudio
bom dia larios e um prazer muito grande de conhecer jente nova tenho 48 anos trabalho no ramos de eletronica departamento de radio frequencia e eletronica analogica e muito bom ver teus projetos microcomtrolado fusiona muito bem um abraço wesley