pic e termopar tipo j

Software e Hardware para uC PIC

Moderadores: andre_luis, 51, guest2003, Renie

Re: pic e termopar tipo j

Mensagempor MOR_AL » 08 Set 2014 18:53

saulo alex de souza escreveu:...
Vou fazer algumas observações em determinados ranges de temperatura e tentar linearilisar por software a curva do termopar, já que pretendo medir de 0°C a 600°C no máximo.
Depois disso, vou construir o circuito real no protoboard e postarei o código e os demais resultados.
...

Eu fiz a linearização a que você se refere e indiquei isso em minha postagem anterior, mas parece que você não tomou conhecimento, ou não apresentou um retorno.
Minha linearização permitia um erro teórico de menos de 1% entre 0ºC e 1360ºC.
Ainda fiz as contas com inteiros com 32 bits e com precisão. Não precisei usar operações com ponto flutuante.
As dicas estão todas lá.
MOR_AL
"Para o triunfo do mal só é preciso que os bons homens não façam nada." Edmund Burke.
"Nunca discutas com pessoas estúpidas. Elas irão te arrastar ao nível delas e vencê-lo por possuir mais experiência em ser ignorante". Mark Twain
Avatar do usuário
MOR_AL
Dword
 
Mensagens: 2934
Registrado em: 19 Out 2006 09:38
Localização: Mangaratiba - RJ

Re: pic e termopar tipo j

Mensagempor saulo alex de souza » 09 Set 2014 13:14

Olá Moral, agora sim, eu li todo o antigo tópico. A minha idéia é muito parecida com a do Sé, mas ao invés de pulsadores para aumentar e diminuir a temperatura grau a grau. Eu pretendo mapear... talvez 10 ranges de temperatura(via proteus e confirmar com um controlador de temperatura autonics tc4s), eu não sei ainda, mas enfim, fazendo isso vou somar ou subtrair um valor b(variável) da faixa de temperatura que o termopar estiver, vai ficar semelhante a equação da reta ax+b, sendo a=5mV(que é a minha menor resolução por grau celsius), x=meu ganho e b o valor a ser incrementado ou subtraído, como disse. Obrigado pela atençao Moral :D . Assim, que meu trabalho parar de me tirar o couro e a patroa não pertubar muito vou montar o circuito, acho que em uma placa perfurada que gera menos ruído que um protoboad(eu acho :?: ).
saulo alex de souza
Bit
 
Mensagens: 16
Registrado em: 27 Ago 2014 12:12

Re: pic e termopar tipo j

Mensagempor ze » 09 Set 2014 15:36

dica: você não precisa linearizar a faixa toda. apenas a que voce vai usar efetivamente. p.ex. eu consegui linearizar - e ficou filé - uma faixa de 50 a 350º de um forno (fixo em 200) com uma pequeníssima tabela de valores unsigned int e uma linha de programa em c. Pena que acho que abri uma discussão desta no efêmero boteco, onde mediante palavras mágicas, consegui fazer o moris e outros oráculos exporem sua sabedoria que me proporcionaram sucesso absoluto.
Pensando bem, deixa de ser munheca (=eu) e linearize a faixa toda. Meia dúzia de bytes a+ nem vão fazer cosquinha no seu mc

Tenta fazer a sua linearização, que se 'fervam' seus neurônios, e no momento oportuno, caso desejes, procuro nos meus fontes e deixo pública a "fórmula secreta". No meu caso quando usei o max31855 minha variável foi o x onde usei um conceito pessoal de ganho variável por faixa. Mas porém contudo todavia entretanto no entanto, para gerar o mapinha suei um pouco a camisa com o excel (o idiota que vos escreve não salvou a panilha e esqueceu o método que usou. típico dele...)

Existem mc´s com ampop embutido (attyni261 p.ex.). Talvez não tão preciso quando o op07 mas é no mínimo uma alternativa curiosa para uma aplicação minimalista. Usei 1 destes pra medir alguns uV (corrente) num fio cuprotal com sucesso

abç
Avatar do usuário
ze
Dword
 
Mensagens: 1655
Registrado em: 05 Jun 2007 14:32

Re: pic e termopar tipo j

Mensagempor andre_luis » 09 Set 2014 16:11

Existem familias de CIs da Linear Technology proprios para compensar a não-linearidade dos termopares. Antigamente isso era feito por amplificadores operacionais utilizando diodos alimentados proximos da região do 'joelho' da curva de corrente, mas calibrar isso era uma atividade extressante.

Se quizer manter uma precisão razoável na leitura, seria fundamental fazer essa compensação não-linear, seja por hardware ou por firmware. Há técnicas extremamente simples de extrair os coeficientes de uma função não-linear que faz essa compensação. Se desejar, procuro um trabalho antigo que realizei baseado no MATLAB e amplificadores OTA.
"Por maior que seja o buraco em que você se encontra, relaxe, porque ainda não há terra em cima."
Avatar do usuário
andre_luis
Dword
 
Mensagens: 5447
Registrado em: 11 Out 2006 18:27
Localização: Brasil - RJ

Re: pic e termopar tipo j

Mensagempor saulo alex de souza » 09 Set 2014 17:28

Sim André, gostaria de dar uma olhada em seu trabalho com o matlab. Quanto ao ci dedicado, gostei muito do max31855j que o Zé mencionou, é possível adquiri-lo por $4,55 a unidade no mousereletronics, o problema é o frete que fica em $40,00.
saulo alex de souza
Bit
 
Mensagens: 16
Registrado em: 27 Ago 2014 12:12

Re: pic e termopar tipo j

Mensagempor MOR_AL » 09 Set 2014 18:17

Segue uma apresentação que fiz.
É para o termopar tipo K, mas o que conta é a metodologia.
Neste método vejo apenas dois gargalos:
1 - Encontrar os limites de temperatura para cada reta que substituirá a curva do termopar.
2 - Encontrar a equação das retas que substituem a curva do termopar.

Observar que você precisará:
1 - Compensar o offset do amplificador operacional.
2 - Usar um ganho que terá que ser ajustado para se obter 3 dígitos corretos.
3 - Usar uma fonte de referência para o CAD, pois o Vcc, apesar de estável, não possui precisão no valor (cai entre 4,75V e 5,25V). Use o CI TL431.
4 - Subtrair a tensão gerada pela conexão do termopar com o circuito (junta a temperatura ambiente. Usei um LM35 para tal.

Talvez eu possa lhe auxiliar em obter as equações das retas com erro teórico menor que 1ºC. Estarei viajando nos próximos dias e só poderei fazê-lo após meu regresso.

http://www.4shared.com/office/2JbYB8O7b ... 2__1_.html

MOR_AL
"Para o triunfo do mal só é preciso que os bons homens não façam nada." Edmund Burke.
"Nunca discutas com pessoas estúpidas. Elas irão te arrastar ao nível delas e vencê-lo por possuir mais experiência em ser ignorante". Mark Twain
Avatar do usuário
MOR_AL
Dword
 
Mensagens: 2934
Registrado em: 19 Out 2006 09:38
Localização: Mangaratiba - RJ

Re: pic e termopar tipo j

Mensagempor andre_luis » 09 Set 2014 20:16

Saulo, escaneei o trabalho que estava guardado no sótão, e tá meio avacalhado, mas o conteúdo é o que importa.
O que vai te interessar são as seguintes partes:
1 ) Extrair as constantes do polinomio de 2o ou 3o grau
2 ) Criar a função inversa ( compensa a não linearidade, gerando uma reta )
3 ) Gerar o circuito pra fazer isso - caso não queira por microcontrolador.

http://teprom.eng.br/arquivos/itm/TermometroOptico.zip

( obs.: Depois de muito tempo descobri que foi erro de montagem que gerou os valores errados )
"Por maior que seja o buraco em que você se encontra, relaxe, porque ainda não há terra em cima."
Avatar do usuário
andre_luis
Dword
 
Mensagens: 5447
Registrado em: 11 Out 2006 18:27
Localização: Brasil - RJ

Re: pic e termopar tipo j

Mensagempor saulo alex de souza » 15 Set 2014 15:08

Olá pessoal, parte do circuito que vou utilizar para a leitura do termopar j. Na verdade implementei até mais do que eu vou realmente utilizar. Desenvolvi um circuito para leitura do lm35(assim testando sua eficiência) através de um pic12f675 e exibindo o valor da temperatura em displays de sete segmentos, mas como esse pic tem poucos pinos, resolvi implementar mais um pouco e agregar 2 74ls164 para expandir seus pinos. Segue o código:
cpp code
#include "C:\Users\Particular\Documents\PROGRAMAS CCS\PIC E LM35\pic e lm35 com display.h"
int16 a,q;
// .ABCDEFG
int unidade,cont,cont2,dezena,contador,i,j,m[10]={ 0b00000001,//númeto 0
0b01001111,//número 1
0b00010010,//número 2
0b00000110,//número 3
0b01001100,//número 4
0b00100100,//número 5
0b00100000,//número 6
0b00001111,//número 7
0b00000000,//número 8
0b00000100};//número 9
float p;
void display_unidade (int j)//função que acerta display de unidades
{
a=0;
for(cont2=0;cont2<=7;cont2++)//envia os 8bits
{
if(bit_test(j,a)==1)//bit vale 1?
{
output_high(pin_a5);//seta pino de dados
output_low(pin_a4);//resseta pino de clock
delay_us(4); //aguarda 4 uS para estabilizar a saída
output_high(pin_a4);//seta pino de clock(74ls164-clock ativo na borda de subida)
}
else // bit vale 0
{
output_low(pin_a5);//resseta pino de dados
output_low(pin_a4);//resseta pino de clock
delay_us(4); //aguarda 4 uS para estabilizar a saída
output_high(pin_a4);//seta pino de clock(74ls164-clock ativo na borda de subida)
}
++a; //incrementa para testar próximo bit
}
}

void display_dezena (int i)//função que acerta display de dezenas
{
a=0;
for(cont=0;cont<=7;cont++)//envia os 8bits
{
if(bit_test(i,a)==1)//bit vale 1?
{
output_high(pin_a2);//seta pino de dados
output_low(pin_a1);//resseta pino de clock
delay_us(4); //aguarda 4uS para estabilizar a saída
output_high(pin_a1);//seta pino de clock(74ls164-clock ativo na borda de subida)
}
else // bit vale 0
{
output_low(pin_a2);//resseta pino de dados
output_low(pin_a1);//resseta pino de clock
delay_us(4); //aguarda 4uS para estabilizar a saída
output_high(pin_a1);//seta pino de clock(74ls164-clock ativo na borda de subida)
}
++a;//incrementa para testar próximo bit
}
}
void main()
{

setup_adc_ports(sAN0|VSS_VDD);
setup_adc(ADC_CLOCK_INTERNAL);
setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
setup_timer_1(T1_DISABLED);
setup_comparator(NC_NC);
setup_vref(FALSE);
set_adc_channel(0);//seta canal analógico 0
delay_us(40);//aguada 40uS para estabilizar
while(1)
{
q=read_adc();//lê canal analógico
p=(0.00489*q);//multiplica valor lido pela resolução mínima
p=(p*100);//converte para graus Celsius
contador=p;//TRUNCA VALOR PARA INTEIROS
unidade=0;
dezena=0;
while(contador>9) //CONTA QUANTAS DEZENAS POSSUI CONTADOR
{
contador=contador-10;
++dezena;
}
while(contador>0)//CONTA QUANTAS UNIDADES POSSUI CONTADOR
{
--contador;
++unidade;
}


delay_ms(5000);//espera 5s para próxima atualização do display
switch(dezena) //verifica qual valor da dezena
{
case 0:
display_dezena(m[0]);
break;
case 1:
display_dezena(m[1]);
break;
case 2:
display_dezena(m[2]);
break;
case 3:
display_dezena(m[3]);
break;
case 4:
display_dezena(m[4]);
break;
case 5:
display_dezena(m[5]);
break;
case 6:
display_dezena(m[6]);
break;
case 7:
display_dezena(m[7]);
break;
case 8:
display_dezena(m[8]);
break;
case 9:
display_dezena(m[9]);
break;
}
switch(unidade) //verifica qual valor da unidade
{
case 0:
display_unidade(m[0]);
break;
case 1:
display_unidade(m[1]);
break;
case 2:
display_unidade(m[2]);
break;
case 3:
display_unidade(m[3]);
break;
case 4:
display_unidade(m[4]);
break;
case 5:
display_unidade(m[5]);
break;
case 6:
display_unidade(m[6]);
break;
case 7:
display_unidade(m[7]);
break;
case 8:
display_unidade(m[8]);
break;
case 9:
display_unidade(m[9]);
break;
}
}

}

Imagem

Imagem
saulo alex de souza
Bit
 
Mensagens: 16
Registrado em: 27 Ago 2014 12:12

Re: pic e termopar tipo j

Mensagempor ze » 15 Set 2014 17:11

oi. lembre-se: só quero somar... ao invés do 'switch (dezena)', que tal tentar apenas:
display_dezena(m[dezena]); e display_unidade(m[unidade]);
outra: coloque tabela na flash.. e otras cositas más...

a propósito, bacana usar shift register 164. welcome
de novo: so mar....
abç
Avatar do usuário
ze
Dword
 
Mensagens: 1655
Registrado em: 05 Jun 2007 14:32

Re: pic e termopar tipo j

Mensagempor andre_luis » 15 Set 2014 20:38

Quanto á linearização, já decidiu se vai fazer por hardware ou por firmware ?
"Por maior que seja o buraco em que você se encontra, relaxe, porque ainda não há terra em cima."
Avatar do usuário
andre_luis
Dword
 
Mensagens: 5447
Registrado em: 11 Out 2006 18:27
Localização: Brasil - RJ

Re: pic e termopar tipo j

Mensagempor saulo alex de souza » 16 Set 2014 12:01

É verdade Zé. Puts!! fica bem mais compacto o código. Quanto a linearização vou fazer por software André, é que tô meio sem tempo, mas logo vou postar algo a respeito.
saulo alex de souza
Bit
 
Mensagens: 16
Registrado em: 27 Ago 2014 12:12

Re: pic e termopar tipo j

Mensagempor ze » 16 Set 2014 12:26

por sw então é mais 1 motivo pra otimizar o código. tem + coisas mas dx pra depois
continuando...
na simulação (apenas) não precisa de resistores. ligue direto do pino ao display.
desnecessários 7805, diodos, capacitores e etc. clique nas propriedades de cada 1 e "exclua da simulação"
isso é pra tornar a simulação + rápida (caso seu pc for=omeu=lêntium)
e pra completar, você cometeu um erro de principiante ao usar display e led verde (esqueci de te avisar ontem)
fome... voar muçá
abç
Avatar do usuário
ze
Dword
 
Mensagens: 1655
Registrado em: 05 Jun 2007 14:32

Re: pic e termopar tipo j

Mensagempor saulo alex de souza » 16 Set 2014 16:15

Então Zé, eu postei o circuito inteiro apenas para quem quisesse reproduzi-lo, agora não entendi o problema dos displays e leds verdes? :roll:
saulo alex de souza
Bit
 
Mensagens: 16
Registrado em: 27 Ago 2014 12:12

Re: pic e termopar tipo j

Mensagempor ze » 16 Set 2014 17:21

oi. que bacana que atingiu um nível de maturidade no qual aquelas dicas lhe são desnecessárias. então considere que as deixei apenas para alguém que queira simular seu circuito pelo qual aliás somos gratos. agora... com relação ao led, lhe peço perdão pela falta de maturidade de minha pessoa, e porquê não dizer... do led também. rs. tento ser eu mesmo e não um robô. e este forum (ainda) me permite isso razão pela qual ainda estamos aí.

Pra não postar só besteira e levar puxão de orelha, permita-me complementar:
no proteus:
-em circuitos digitais use pullup ao invés de resistor
-nas propriedades de leds, displays 7seg selecione DIGITAL e não ANALOGUE
-resumindo, evite mesclar circuito analógico com digital
-em mc´s carregue arquivo .cof ao invés de .hex. Você vê rodando o fonte
-bom, não me lembro agora de + coisas

Sucessos e continue contando conosco... e pra nós!!
Avatar do usuário
ze
Dword
 
Mensagens: 1655
Registrado em: 05 Jun 2007 14:32

Re: pic e termopar tipo j

Mensagempor saulo alex de souza » 05 Out 2014 16:46

Aqui está mais uma etapa do programa para leitura de termopar. A leitura do canal do lm35 é perfeita, mas o canal do termopar não lê o termopar, acredito que é algo relacionado a fonte simétrica do amplificador, pois simulei com 2 lm35, um em cada canal, e a leitura é perfeita. Alguém sabe como resolver?

j7rka1.PNG


cpp code
#include "C:\Users\Particular\Documents\PROGRAMAS CCS\PIC E TERMOPAR TIPO J\PIC E TERMOPAR J.h"
int16 lm35,termopar,contador;
#use fast_io(b)
#use fast_io(c)
#byte portb=0x06
#byte portc=0x07
// .GFEDCBA
int unidade,dezena,centena, m[10]={ 0b01000000,//número 0
0b01111001,//número 1
0b00100100,//número 2
0b00110000,//número 3
0b00011001,//número 4
0b00010010,//número 5
0b00000010,//número 6
0b01111000,//número 7
0b00000000,//número 8
0b00010000};//número 9
float p,t;

void main()
{

setup_adc_ports(AN0_AN1_AN3);
setup_adc(ADC_CLOCK_INTERNAL);
setup_spi(SPI_SS_DISABLED);
setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
setup_timer_1(T1_DISABLED);
setup_timer_2(T2_DISABLED,0,1);
setup_comparator(NC_NC_NC_NC);
setup_vref(FALSE);
set_tris_c(0b00000000);//define I/O PORTC
set_tris_b(0b00011111);//define I/O PORTB
portb=0x00;
portc=0x00;

while(1)
{
set_adc_channel(0);//seta canal analógico 0
delay_us(40);//aguada 40uS para estabilizar
lm35=read_adc();//lê temperatura ambiente através do lm35
p=(0.00487*lm35);//multiplica valor lido pela resolução mínima
p=(p*100);//converte para graus Celsius
set_adc_channel(1);//seleciona canal analógico 1
delay_us(40);//aguada 40uS para estabilizar
termopar=read_adc();//lê termopar j
t=(0.00487*termopar);//multiplica valor lido pela resolução mínima
t=(t*200);//converte para graus Celsius
contador=(t+p); //soma termopar+lm35 e truca para inteiros
unidade=0;
dezena=0;
centena=0;
//a=resolução
//x=valor lido no A/D
//b=valor a ser somado
// ou subtraido para corrigir desvio
if(contador>0 && contador<28)// 1 primera reta, temperatura=ax+b
{
contador=++contador; //soma um a contador
}
if(contador>47 && contador<65)//64-48=16;2 reta
{
contador=--contador;//subtrai um de contador
}
if(contador>64 && contador<79)//78-65=13; 3 reta
{
contador=(contador-2);//subtrai 2 de contador
}
if(contador>78 && contador<92)//91-79=12; 4 reta
{
contador=(contador-3);//subtrai 3 de contador
}
if(contador>91 && contador<104)//103-92=11; 5 reta
{
contador=(contador-4);//subtrai 4 de contador
}
if(contador>103 && contador<115)//114-104=10; 6 reta
{
contador=(contador-5);
}
if(contador>114 && contador<125)//124-115=9; 7 reta
{
contador=(contador-6);
}
if(contador>124 && contador<135)//134-125=9; 8 reta
{
contador=(contador-7);
};
if(contador>135 && contador <145)//144-136=8; 9 reta
{
contador=(contador-8);
}
if(contador>144 && contador<155)//10 reta
{
contador=(contador-9);
}
if(contador>154 && contador<165)//11 reta
{
contador=(contador-10);
}
if(contador>164 && contador<174)// 12 reta
{
contador=(contador-11);
}
if(contador>173 && contador<184)// 13 reta
{
contador=(contador-12);
}
if(contador>183 && contador<192)// 14 reta
{
contador=(contador-13);
}
if(contador>191 && contador<202)// 15 reta
{
contador=(contador-14);
}
if(contador>201 && contador<211)// 16 reta
{
contador=(contador-15);
}
if(contador>210 && contador<220)//17 reta
{
contador=(contador-16);
}
if(contador>219 && contador<229)// 18 reta
{
contador=(contador-17);
}
if(contador>228 && contador<238)// 19 reta
{
contador=(contador-18);
}
if(contador>237 && contador<247)// 20 reta
{
contador=(contador-19);
}
if(contador>246 && contador<256)// 21 reta
{
contador=(contador-20);
}
if(contador>255 && contador<265)// 22 reta
{
contador=(contador-21);
}
if(contador>264 && contador<274)// 23 reta
{
contador=(contador-22);
}
if(contador>273 && contador<284)//24 reta
{
contador=(contador-23);
}
if(contador>283 && contador<293)//25 reta
{
contador=(contador-24);
}
if(contador>292 && contador<302)//26 reta
{
contador=(contador-25);
}
if(contador>301 && contador<312)//27 reta
{
contador=(contador-26);
}
if(contador>311 && contador<321)//28 reta
{
contador=(contador-27);
}
if(contador>320 && contador<331)//29 reta
{
contador=(contador-28);
}
if(contador>330 && contador<340)//30 reta
{
contador=(contador-29);
}
if(contador>339 && contador<350)//31 reta
{
contador=(contador-30);
}
if(contador>349 && contador<360)//32 reta
{
contador=(contador-31);
}
if(contador>359 && contador<369)//33 reta
{
contador=(contador-32);
}
if(contador>368 && contador<379)//34 reta
{
contador=(contador-33);
}
if(contador>378 && contador<389)// 35 reta
{
contador=(contador-34);
}
if(contador>388 && contador<399)// 36 reta
{
contador=(contador-35);
}
if(contador>398 && contador<408)//37 reta
{
contador=(contador-36);
}
if(contador>407 && contador<418)//38 reta
{
contador=(contador-37);
}
if(contador>417 && contador<428)//39 reta
{
contador=(contador-38);
}
if(contador>427 && contador<437)// 40 reta
{
contador=(contador-39);
}
if(contador>436 && contador<447)//41 reta
{
contador=(contador-40);
}
if(contador>446 && contador<456)//42 reta
{
contador=(contador-41);
}
if(contador>455 && contador<465)//43 reta
{
contador=(contador-42);
}
if(contador>464 && contador<474)//44 reta
{
contador=(contador-43);
}
if(contador>473 && contador<483)// 45 reta
{
contador=(contador-44);
}
if(contador>482 && contador<492)//46 reta
{
contador=(contador-45);
}
if(contador>491 && contador<500)//47 reta
{
contador=(contador-46);
}
if(contador>499 && contador<508)//48 reta
{
contador=(contador-47);
}
while(contador>=100)//conta quantas centenas tem a variável contador
{
contador=(contador-100);
++centena;
}
while(contador>=10)//conta quantas dezenas tem a variável contador
{
contador=(contador-10);
++dezena;
}
while(contador>=1)//conta quantas unidades tem a variável contador
{
contador=(contador-1);
++unidade;
}
portc=m[centena];
output_low(pin_b5);//liga display das centenas
delay_ms(500);
output_high(pin_b5);
delay_ms(500);
portc=m[dezena];
output_low(pin_b6);//liga display das dezenas
delay_ms(500);
output_high(pin_b6);
delay_ms(500);
portc=m[unidade];
output_low(pin_b7);//liga display das unidades
delay_ms(500);
output_high(pin_b7);
delay_ms(500);
}


}
Você não está autorizado a ver ou baixar esse anexo.
saulo alex de souza
Bit
 
Mensagens: 16
Registrado em: 27 Ago 2014 12:12

AnteriorPróximo

Voltar para PIC

Quem está online

Usuários navegando neste fórum: Nenhum usuário registrado e 1 visitante

x