Sari la conținut
ELFORUM - Forumul electronistilor

INTERFATA PIC IN LABVIEW


costi002

Postări Recomandate

  • Răspunsuri 54
  • Creat
  • Ultimul Răspuns

Top autori în acest subiect

  • Liviu M

    13

  • costi002

    13

  • Vlad Mihai

    12

Vizitator mihai_ylye

am ajuns la partea cu LABVIEW...deci temperatura pot sa o afisez in hyperterminal si acum nu imi mai trebuie decat sa o afisez in LABVIEW...PROBLEMA ESTE CA NU STIU DELOC ACEST PROGRAM...niste mici sfaturi mi ar fi de un real ajutor...deci in labview trebuie sa ma folosesc de transmisia seriala...altceva nu mai stiu...va multumesc si sper ca ma puteti ajuta cat de ptin puteti macar

Link spre comentariu
  • 5 luni mai târziu...

am si eu niste probleme privind conexiunea unui pic16f877a cu Labview. Trimit 4 valori ale parametrilor masurate cu pic prin rs232, folosesc ca separator \n. Am configurat Labview sa citeasca aceste 4 valori si sa le afiseze, dar problema e ca nu stie care e primul parametrul masurat si care e ultimul. In loc de temperatura imi pune valoarea unei tensiuni etc. Practic imi incurca valorile. Are cineva vreo idee?

sbit LCD_RS at RB0_bit;sbit LCD_EN at RB1_bit;sbit LCD_D4 at RB2_bit;sbit LCD_D5 at RB3_bit;sbit LCD_D6 at RB4_bit;sbit LCD_D7 at RB5_bit;sbit LCD_RS_Direction at TRISB0_bit;sbit LCD_EN_Direction at TRISB1_bit;sbit LCD_D4_Direction at TRISB2_bit;            //configurare  conexiune pic catre LCDsbit LCD_D5_Direction at TRISB3_bit;sbit LCD_D6_Direction at TRISB4_bit;sbit LCD_D7_Direction at TRISB5_bit;   unsigned short current_duty1;  unsigned char txt1[] = "******SMPS******";  unsigned char txt2[] = "*****control****";  unsigned char txt3[] = "****USV 2013****";  unsigned char ch,uart_rd;  unsigned int Tensiune,val1,t,valoare_adc1,curent;  unsigned long u,power,i;void main() {   UART1_Init(9600);                       // Initialize USART module (8 bit, 38400 baud rate, no parity)  TRISB = 0xC0;          // set RB0,RB1 pin as input  PORTB = 0x00;  ADCON1     = 0x80;                       // configure Vref, and analog channels  TRISA      = 0xFF;                       // designate PORTA as input    TRISC.F3 = 1;                           //Configure 1st bit of PORTD as input  TRISC.F4 = 1;                          //Configure 1st bit of PORTD as output  TRISC.F0 = 0;  PORTC.F0 = 0;                        //off  Lcd_Init();                        // Initialize LCD  Lcd_Cmd(_LCD_CLEAR);               // Clear display  Lcd_Cmd(_LCD_CURSOR_OFF);          // Cursor off  PWM1_Init(1000);  Lcd_Out(1,2,txt1);                 // Write text in first row  Lcd_Out(2,2,txt2);                 // Write text in second row  Delay_ms(300);  Lcd_Cmd(_LCD_CLEAR);               // Clear display  Lcd_Out(2,2,txt3);                 // Write text in first row  Delay_ms(300);  Lcd_Cmd(_LCD_CLEAR);               // Clear display  LCD_Out(1, 1,"T:");  LCD_Out(1, 9,"Vi:");  LCD_Out(2, 1,"Vo: ");  LCD_Out(2, 9,"Io");      current_duty1  = 10;   PWM1_Start();                       // start PWM1  PWM1_Set_Duty(current_duty1);        // setare   factor de umplerewhile (1) {         Valoare_adc1 = ADC_Read(4); current_duty1= valoare_adc1>> 2;  // conversie citire de pe ADC din 10 Biti in 8 Biti    si setare pwm in fucntie de    ce citeste pe ADC PWM1_Set_Duty(current_duty1);        //comanda uart        {    if (UART1_Data_Ready()) {     // If data is received,      uart_rd = UART1_Read();     // read the received data,      if (uart_rd==0x61)      PORTC.F0=1;      if (uart_rd==0x62)      PORTC.F0=0;    }    } //comanda on/off      if(PORTC.F3 == 0)                      //If the switch is pressed    {       Delay_ms(100);                             //Switch Debounce       if(PORTC.F3 == 0)                       //If the switch is still pressed       {          Delay_ms(100);         PORTC.F0 = 1;                          //comanda on       }    }  if(PORTC.F4 == 0)                      //If the switch is pressed    {       Delay_ms(100);                             //Switch Debounce       if(PORTC.F4 == 0)                       //If the switch is still pressed       {          Delay_ms(100);         PORTC.F0 = 0;                          //comanda off       }    }    /* end */      // Grade Celsius      val1=ADC_read(3);                // citim    tensiunea  generata de seznor in portul ADC1     t=(val1*0.48876);//conversia   tensiunii citite in grade celsius             ch = (t/10)%10;               //=> afisez zecile                        // write ASCII digit on serial port       LCD_chr(1,3,'0'+ch);        UART1_Write(48+ch);   ch = t%10;       LCD_chr(1,4,'0'+ch);       //=> afisez unitatile        UART1_Write(48+ch);                  // write ASCII digit on serial port           UART1_Write('\n');                  // write ASCII digit on serial port             LCD_Chr_CP('C');      // Voltage Vin      Tensiune=ADC_read(0);                // get ADC value for U from channel 1      u=(long)Tensiune*500*11,11;               // covert adc reading to milivolts      u=u/1023;                            // 0..1023 -> 0-3500mV      ch=u/1000;                           // extract 10.00 U digit      if (ch==0)        {          LCD_Chr(1,11, 32);                // write empty space if digit is 0        }      else        {          LCD_Chr(1,12,48+ch);              // write ASCII digit at 1st row, 2nd column        }          UART1_Write(48+ch);      ch=(u/100) %10;                      // extract 01.00 U digit      LCD_Chr_CP(48+ch);         UART1_Write(48+ch);                  // write ASCII digit on serial port    LCD_Chr_CP('.');                     // write '.' at cursor point       UART1_Write('.');                  // write ASCII digit on serial port    ch=(u/10) %10;                       // extract 00.10 U digit    LCD_Chr_CP(48+ch);                   // write ASCII digit at cursor point                       UART1_Write(48+ch);                  // write ASCII digit on serial port           UART1_Write('\n');                  // write ASCII digit on serial port      LCD_Chr_CP('V');                     // write 'V' at cursor point      // Voltage Vout       Tensiune=ADC_read(1);                // get ADC value for U from channel 1      u=(long)Tensiune*500*11,15;               // covert adc reading to milivolts      u=u/1023;                            // 0..1023 -> 0-3500mV      ch=u/1000;                           // extract 10.00 U digit      if (ch==0)        {          LCD_Chr(2,4, 32);                // write empty space if digit is 0        }      else        {          LCD_Chr(2,4,48+ch);              // write ASCII digit at 1st row, 2nd column        }             UART1_Write(48+ch);                  // write ASCII digit on serial port      ch=(u/100) %10;                      // extract 01.00 U digit      LCD_Chr_CP(48+ch);       UART1_Write(48+ch);                  // write ASCII digit on serial port                           // write ASCII digit at cursor point    LCD_Chr_CP('.');                     // write '.' at cursor point                UART1_Write('.');                  // write ASCII digit on serial port     ch=(u/10) %10;                       // extract 00.10 U digit     LCD_Chr_CP(48+ch);                   // write ASCII digit at cursor point                    UART1_Write(48+ch);                  // write ASCII digit on serial port           UART1_Write('\n');                  // write ASCII digit on serial port          //Curent          curent=ADC_read(2);                // get ADC value for U from channel 1      i=(long)curent*5000;               // covert adc reading to milivolts      i=i/1023;                            // 0..1023 -> 0-3500mV      ch=i/1000;                           // extract 10.00 U digit      if (ch==0)        {          LCD_Chr(2,12, 32);                // write empty space if digit is 0        }      else        {          LCD_Chr(2,13,48+ch);              // write ASCII digit at 1st row, 2nd column        }          UART1_Write(48+ch);      ch=(i/100) %10;                      // extract 01.00 U digit      LCD_Chr_CP(48+ch);       UART1_Write(48+ch);                  // write ASCII digit on serial port    LCD_Chr_CP('.');                     // write '.' at cursor point       UART1_Write('.');                  // write ASCII digit on serial port    ch=(i/10) %10;                       // extract 00.10 U digit    LCD_Chr_CP(48+ch);                   // write ASCII digit at cursor point    UART1_Write(48+ch);                  // write ASCII digit on serial port           UART1_Write('\n');                  // write ASCII digit on serial port      LCD_Chr_CP('A');         }                         }
Link spre comentariu

si eu am aavut aceasta problema. rezolvareagasita de mine a fost: labview trimite pe serial catre pic un caracter identic cu cel asteptat de pic. dupa ce pic-ul vede caracterul, trimite setul de valori. un fel de sicronizare pornita de labview

Link spre comentariu

In locul tau as incerca sa fac o rutina care sa transmita toate datele odata, nu pe rand, ca acum.

Adica as memora toti parametrii intr-o matrice si din cand in cand as trimite matricea la PC. In felul asta as fi sigur ca PIC-ul transmite in ordinea pe care o vreau.

Sau cand o cere labview. Adica in labview faci o rutina care sa trimita un caracter anume (sa zicem #) pe seriala, dupa care sa se mute in "mod receptie". PIC-ul supravegheaza seriala si cand primeste # pune datele din matrice pe seriala.

 

LE Cam asa arata la mine. Folosesc intreruperile sa ma prind cand se intampla ceva pe seriala. In rutina de tratare a intreruperilor citesc caracterele venite pe seriala si in functie de valoarea lor setez un flag sau nu. In main testez diversele flaguri si actionez in consecinta.

"Codul" din labview am senzatia ca-l ai deja (e trei posturi mai sus).

 

if(RCIF)    /*comunicatie seriala*/   {       bRxInt = 1;  //anunt main ca am receptionat ceva       if(ucGlIdx >= 16)          ucGlIdx = 0;       if(RCREG != 'c')  //'c' e caracterul de activare a transmisiei. Daca nu-l primesc       {          ucComBuf[ucGlIdx] = RCREG;  //umplu bufferul de receptie          ucGlIdx++;          bTxStart = 0;  //dezactivez transmisia       }       else //daca primesc 'c'          bTxStart = 1;   //activez transmisia   }

 

In main

/**************************************** Receptie/Transmisie seriala; cea mai mare parete a actiunii e in isr.c; ar trebui revazut*************************************/       if (bRxInt)  /*** intrerupere generata de interfata seriala - receptie */       {          if(bTxStart == 0)   //nu transmit => actualizez parametrii din controler          {             ucMaxActionari1 = ucComBuf[7] & 0x0F;             ucMaxActionari2 = (ucComBuf[7] & 0xF0) >>4;  	         eeprom_write(ucEePhAddress,ucComBuf[8]);	         eeprom_write(ucEePhAddress+1,ucComBuf[8+1]);	         eeprom_write(ucEePhAddress+2,ucComBuf[8+2]);	         eeprom_write(ucEePhAddress+3,ucComBuf[8+3]);          }          else //transmit datele din buffer          {             TXSTA = 0b00100100;  // activeaza transmisia.              for(ucIdx = 3; ucIdx<16; ucIdx++)             {                TXREG = ucComBuf[ucIdx];                DelayMs(5);             }                TXSTA = 0b00000100;  // dezactiveaza transmisia.           }                    bRxInt = 0;          bTxStart = 0;       } // if (bRxInt)
Link spre comentariu

Da, scuze am revazut acum, programul din labview am realizat altul, dar m-am uitat si al tau. Multumesc de secvente de cod, dar pacat ca nu stiu cum sa le folosesc in codul meu.

Link spre comentariu

Cred c-ar mai fi o posibilitate.La inceputul transmisiei, inainte sa transmiti date reale, trimite un caracter "start transmisie" (un caracter pe care altfel nu-l folosesti). In Labview asteapta pana vine caracterul asta si afiseaza numai caracterele (cate or fi ele) care vin dupa el. Poate asa reusesti sa "sincronizezi" comunicatia.

Link spre comentariu

Voi incerca sa fac o functie separata de transmisie uart, eu practic in cod transmit ce apare pe LCD. am curatat codul de tot ce are legatura cu uart si voi face separat. Momentan aici am rams, mai departe nu mai stiu.

sbit LCD_RS at RB0_bit;sbit LCD_EN at RB1_bit;sbit LCD_D4 at RB2_bit;sbit LCD_D5 at RB3_bit;sbit LCD_D6 at RB4_bit;sbit LCD_D7 at RB5_bit;sbit LCD_RS_Direction at TRISB0_bit;sbit LCD_EN_Direction at TRISB1_bit;sbit LCD_D4_Direction at TRISB2_bit;            //configurare  conexiune pic catre LCDsbit LCD_D5_Direction at TRISB3_bit;sbit LCD_D6_Direction at TRISB4_bit;sbit LCD_D7_Direction at TRISB5_bit;  unsigned short current_duty1;  unsigned char txt1[] = "******SMPS******";  unsigned char txt2[] = "*****control****";  unsigned char txt3[] = "****USV 2013****";  unsigned char ch;  unsigned char buffer1[7];  unsigned char buffer2[7];  unsigned char buffer3[7];  unsigned char buffer4[7];  unsigned int Tensiune,Tensiune1,val,valoare_adc,curent;  unsigned long u,u1,m,t;   void Transmisie_UART() {    Tensiune1= ADC_Read(1);   //voltage Vout   //Delay_ms(10);   Tensiune= ADC_Read(0);         //Volage Vin  // Delay_ms(10);   val = ADC_Read(3);             //Temperatura  // Delay_ms(10);   curent = ADC_Read(2);          //Curent  // Delay_ms(10);     FloatToStr((Tensiune*500*11,11),buffer1);                   //converteste valoarea din float in string     FloatToStr((Tensiune1*500*11,15),buffer2);     FloatToStr((val*0,48876),buffer3);     FloatToStr((Curent*500),buffer4);     UART1_Write_Text(" Tensiune Intrare: ");     UART1_Write_Text(buffer1);     UART1_Write_Text(" Tensiune Iesire: ");     UART1_Write_Text(buffer2);     UART1_Write_Text(" Temperatura: ");     UART1_Write_Text(buffer3);     UART1_Write_Text(" Curent Iesire: ");     UART1_Write_Text(buffer4); }void main() {  UART1_Init(9600);  Delay_ms(100);  TRISB = 0xC0;                             // set RB0,RB1 pin as input  PORTB = 0x00;  ADCON1     = 0x80;                       // configure Vref, and analog channels  TRISA      = 0xFF;                       // designate PORTA as input    TRISC.F3 = 1;                           //Configure 1st bit of PORTD as input  TRISC.F4 = 1;                          //Configure 1st bit of PORTD as output  TRISC.F0 = 0;   PORTC.F0 = 0;                        // consumator off    Lcd_Init();                        // Initialize LCD  Lcd_Cmd(_LCD_CLEAR);               // Clear display  Lcd_Cmd(_LCD_CURSOR_OFF);          // Cursor off   PWM1_Init(1000);   Lcd_Out(1,2,txt1);                 // Write text in first row  Lcd_Out(2,2,txt2);                 // Write text in second row  Delay_ms(300);  Lcd_Cmd(_LCD_CLEAR);               // Clear display  Lcd_Out(2,2,txt3);                 // Write text in first row  Delay_ms(300);  Lcd_Cmd(_LCD_CLEAR);               // Clear display  LCD_Out(1, 1,"T:");  LCD_Out(1, 9,"Vi:");  LCD_Out(2, 1,"Vo: ");  LCD_Out(2, 9,"Io");  current_duty1  = 10;  PWM1_Start();                       // start PWM1  PWM1_Set_Duty(current_duty1);        // setare   factor de umplerewhile (1) { Valoare_adc = ADC_Read(4); current_duty1= valoare_adc>> 2;  // conversie citire de pe ADC din 10 Biti in 8 Biti    si setare pwm in fucntie de    ce citeste pe ADC PWM1_Set_Duty(current_duty1);//comanda on/off      if(PORTC.F3 == 0)                      //If the switch is pressed    {       Delay_ms(100);                             //Switch Debounce       if(PORTC.F3 == 0)                       //If the switch is still pressed       {          Delay_ms(100);         PORTC.F0 = 1;                          //comanda on       }    }  if(PORTC.F4 == 0)                      //If the switch is pressed    {       Delay_ms(100);                             //Switch Debounce       if(PORTC.F4 == 0)                       //If the switch is still pressed       {          Delay_ms(100);         PORTC.F0 = 0;                          //comanda off       }    }     /* end */// Temperatura      val=ADC_read(3);                           // citim    tensiunea  generata de seznor in portul ADC1       t=(val*0.48876);                         //conversia   tensiunii citite in grade celsius        ch = (t/10)%10;                          //=> afisez zecile       LCD_chr(1,3,'0'+ch);       ch = t%10;       LCD_chr(1,4,'0'+ch);                     //=> afisez unitatile           LCD_Chr_CP('C');      // Voltage Vin      Tensiune=ADC_read(0);                // get ADC value for U from channel 1      u=(long)Tensiune*500*11,11;               // covert adc reading to milivolts      u=u/1023;                            // 0..1023 -> 0-3500mV      ch=u/1000;                           // extract 10.00 U digit      if (ch==0)        {          LCD_Chr(1,11, 32);                // write empty space if digit is 0        }      else        {          LCD_Chr(1,12,48+ch);              // write ASCII digit at 1st row, 2nd column        }          UART1_Write(48+ch);      ch=(u/100) %10;                      // extract 01.00 U digit      LCD_Chr_CP(48+ch);      LCD_Chr_CP('.');                     // write '.' at cursor point        ch=(u/10) %10;                       // extract 00.10 U digit    LCD_Chr_CP(48+ch);                   // write ASCII digit at cursor point    LCD_Chr_CP('V');                     // write 'V' at cursor point      // Voltage Vout       Tensiune1=ADC_read(1);                // get ADC value for U from channel 1      u1=(long)Tensiune1*500*11,15;               // covert adc reading to milivolts      u1=u1/1023;                            // 0..1023 -> 0-3500mV      ch=u1/1000;                           // extract 10.00 U digit      if (ch==0)        {          LCD_Chr(2,4, 32);                // write empty space if digit is 0        }      else        {          LCD_Chr(2,4,48+ch);              // write ASCII digit at 1st row, 2nd column        }      ch=(u1/100) %10;                      // extract 01.00 U digit      LCD_Chr_CP(48+ch);      LCD_Chr_CP('.');                     // write '.' at cursor point     ch=(u1/10) %10;                       // extract 00.10 U digit     LCD_Chr_CP(48+ch);                   // write ASCII digit at cursor point         //Curent          curent=ADC_read(2);                // get ADC value for U from channel 1      m=(long)curent*500;               // covert adc reading to milivolts      m=m/1023;                            // 0..1023 -> 0-3500mV      ch=m/1000;                           // extract 10.00 U digit      if (ch==0)        {          LCD_Chr(2,12, 32);                // write empty space if digit is 0        }      else        {          LCD_Chr(2,13,48+ch);              // write ASCII digit at 1st row, 2nd column        }      ch=(m/100) %10;                      // extract 01.00 U digit      LCD_Chr_CP(48+ch);       LCD_Chr_CP('.');                     // write '.' at cursor point       ch=(m/10) %10;                       // extract 00.10 U digit    LCD_Chr_CP(48+ch);                   // write ASCII digit at cursor point    LCD_Chr_CP('A');}       }
Link spre comentariu

Pai nu trebuia curatat nimic. Trebuia doar ca inainte de primul UART1_Write(); sa apelezi UART1_Write('Z'); (sa zicem) .In Labview la inceput 'sari' peste tot ce primesti si nu e Z. Cand primesti Z ai "sincronizat" receptia cu transmisia - ce vine dupa vine in ordinea pe care o doresti. Sau?LE Pe de alta parte, eu n-as trimite pe seriala diversele valori transformate in caractere, ci le-as trimite ca numere si le-as decoda in Labview, pentru ca - transmiti mai putin- in PC ai mai multa putere de procesareAdica in loc sa transformi 25°C in caracterele 2 si 5 in PIC si sa transmiti caracterul 2 su caracterul 5 (2 caractere), transmiti 25 (un caracter) si-l "decodezi" in PC.La fel cu tensiunile. In loc sa transmiti 4 caractere (in cazulö numerelor pe 4 cifre), transmiti 2 caractere ((nr & 0x00FF) si ((nr &FF00)>>8)).

Link spre comentariu

Liviu, hai ca incerc si varianta ta, mai am codul vechi. si in Labview configurez chestia cu Z in scan from string?in cod chestia cu Z o fac inainte de primul Uart_Write nu?

Link spre comentariu

Nu stiu exact cum faci receptia in Labview, asa ca nu-s sigur. Dar in princiupiu da. Daca receptionezi un string cu mai multe caractere, atunci cauti Z si "decodezi" ce e dupa.PS Vezi c-am editat mai sus.LE Da, Z va fi trimis inainte de date.

Link spre comentariu

Creează un cont sau autentifică-te pentru a adăuga comentariu

Trebuie să fi un membru pentru a putea lăsa un comentariu.

Creează un cont

Înregistrează-te pentru un nou cont în comunitatea nostră. Este simplu!

Înregistrează un nou cont

Autentificare

Ai deja un cont? Autentifică-te aici.

Autentifică-te acum



×
×
  • Creează nouă...

Informații Importante

Am plasat cookie-uri pe dispozitivul tău pentru a îmbunătății navigarea pe acest site. Poți modifica setările cookie, altfel considerăm că ești de acord să continui.Termeni de Utilizare si Ghidări