PIC16F877A - Object Detection and Rejection - Timer Interrupt

Thread Starter

daljeet795

Joined Jul 2, 2018
295
I don't really know. I would always recommend 18F over 16F but I haven't used that particular part or evaluation board. The one on that board is 3.3Vmax, will that do? Note that there are many 18F's and 16F1xxx Enhanced Midrange that will drop into the same socket as your '877A. You can proceed now with the 877A then upgrade as your requirements become more apparent. As before, if you are looking to upgrade have at it but consider looking at some that have built-in quadrature encoder modules. A parametric search on Microchip.com will help you there. But in any case, you'll have to have a firm idea of the features/performance that your application requires and use those as a guide.
@JohnInTX as discussed PIC16F877A is only working with the limited speed of the belt. PIC16F877A works only up to 30 % belt speed

could I use PIC18F46K22 instead of PIC16F877A into the socket of the development board?

https://ww1.microchip.com/downloads/en/DeviceDoc/40001412G.pdf
 

Thread Starter

daljeet795

Joined Jul 2, 2018
295
I believe you are going to see the problems that occur when you proceed piecemeal without a full design.
  • When you get an interrupt from the encoder,
  • Detect the object (if SENSOR==1)
  • Send the scan request '1' to the PC
  • Wait for the PC's reply
  • If 'B' is returned, put a '1' in the shift register
  • Proceed from there..
There is more to do in the serial comms but that is a start.
Good luck!
@JohnInTX I am working on the theory one thing at one time. I was using the sensor instead of the scanner. sensor worked for me that's why I am coming to the scanner. if it works. later I would add start / stop with Buzzer

I tried to merge both programs into one again

C:
#include <xc.h>
#include <stdio.h>
#include <conio.h>

#pragma config FOSC = HS  // Oscillator Selection bits (XT oscillator)
#pragma config WDTE = OFF  // Watchdog Timer Enable bit (WDT disabled)
#pragma config PWRTE = ON  // Power-up Timer Enable bit (PWRT enabled)
#pragma config BOREN = OFF  // Brown-out Reset Enable bit (BOR disabled)
#pragma config LVP = OFF  // Low-Voltage (Single-Supply) In-Circuit Serial Programming Enable bit (RB3 is digital I/O, HV on MCLR must be used for programming)
#pragma config CPD = OFF  // Data EEPROM Memory Code Protection bit (Data EEPROM code protection off)
#pragma config WRT = OFF  // Flash Program Memory Write Enable bits (Write protection off; all program memory may be written to by EECON control)
#pragma config CP = OFF  // Flash Program Memory Code Protection bit (Code protection off)
// #pragma config statements should precede project file includes.
// Use project enums instead of #define for ON and OFF.

#define ENCODER RC0
#define SENSOR  RC1
#define KICKER  RD0
#define _XTAL_FREQ 20000000  // **you need this for delays**

__bit gotIRQ;  // signals main that an interrupt

void putch(char data)
{  
    while(!TRMT);
    TXREG = data;
}

  char  getch ()
{
   if(OERR == 1){     // reset UART on overflow error
       CREN = 0;
       CREN = 1;
  }
  while(RCIF==0);   // Wait till the data is received
   return(RCREG);   // Return the received data to calling function
}
void send (char *s)
{
  while (*s != 0)
  putch(*s++);
}

void main(void)
{
  char data;
  unsigned int ShiftReg = 0; //  Init to 0
  INTCON = 0; // No interrupts
  TRISC = 0b00000011; // RC0 Eencoder Pin RC1 Sensor Pin
  TRISD = 0b00000000; // RD0 Kicker pin

  TXSTA = 0b00100100;                           // TX enabled, BRGH=1
  RCSTA = 0b10010000;                           // Serial Port, Continuous Receive enabled
  SPBRG = 0x81;                                 // baud rate 9600

  //CCP1 MODULE INITIALIZATION
  T1CON = 0b00000011;  // 1:1 prescale, OSC disabled, Input Synchronized, External clock on T1CKI(RC0), Timer ON
  CCP1CON = 0b00001011;  // Compare mode using CCPR1H and CCPR1L as a 16 bit value
//Set CCPR1H and CCPR1L (16 bits) to the number of encoder pulses e.g. for 795
    CCPR1H = 0x03;
    CCPR1L = 0x84;
    CCP1IF = 0;
    CCP1IE = 1;  //Enabled CCP1 interrupt
    INTCON = 0xc0;  //Enabled Global interrupts & Peripherals interrupt
    while(1)
  {
  if (gotIRQ)
  {
     gotIRQ = 0;  // acknowledge the interrupt ** ALWAYS and before the delay **

     ShiftReg <<= 1;  // shift the integer shift register one bit left. LSbit = 0 after shift

    ReceivePcData = getch();

  if ( ReceivePcData == 'B')
  ShiftReg |= 0x0001;  // bad object, put 1 in LSbit
  if(ShiftReg & 0x0400){  // and if the #10 bit after shift is '1', kick it
  KICKER = 1;  // set output pulse high
  __delay_ms(40);  // *groan* Delay to see output ( inbuilt delay)
  KICKER = 0;  // set output pulse low
  }// kicker
  }// gotIRQ
} // while
}// main

void __interrupt() IRQ(void){
  // CCP1 Interrupt
  if(CCP1IF == 1)  // if the CCP1 Interrupt flag is set...
  {
  CCP1IF = 0;

  if (SENSOR == 1)
      {
           printf("\rThe Sensor is: %d", SENSOR);
      }


  gotIRQ = 1;  // 'Signal' main that an interrupt happened
  }
}
Note - This is pseudo code only it may not compile. I am trying to arrange program in a sequence to perform task's
Edit : modified getch() function in the program
 
Last edited:

JohnInTX

Joined Jun 26, 2012
4,787
@JohnInTX as discussed PIC16F877A is only working with the limited speed of the belt. PIC16F877A works only up to 30 % belt speed

could I use PIC18F46K22 instead of PIC16F877A into the socket of the development board?
Sure, why not? It's a much better chip. Even at the same clock speed, it will run better. But it may or not speed things up. That depends on where the slowdown is. If it is not processing interrupts fast enough then yes, better. If your real problem is that 40ms blocking delay then no, it won't.

Take another look at your pseudocode right after gotIRQ. Shouldn't you be sending something to the PC somewhere in there?

Could we please stick with one version of something like getch? In a previous version, you correctly checked the overflow error but the latest one reverts to some old version. If you keep doing that, this project will take a very long time to complete, if ever.

Here's a freebie. Consider what getch() does. If no character arrives, you will stay there forever and the rest of the program will hang right there. Write a new function that returns a character if available or 00h if not. That way, you can poll the UART without hanging the program.
 
Last edited:

Thread Starter

daljeet795

Joined Jul 2, 2018
295
Sure, why not? It's a much better chip. Even at the same clock speed, it will run better. But it may or not speed things up. That depends on where the slowdown is. If it is not processing interrupts fast enough then yes, better. If your real problem is that 40ms blocking delay then no, it won't.
I don't think a 40 ms delay is the problem I think the counter of pic16f877a is not much capable to count pulse of encoder at high speed so I want to check the counter of other chip

@JohnInTX Can this be a reason ?
 

Thread Starter

daljeet795

Joined Jul 2, 2018
295
Here's a freebie. Consider what getch() does. If no character arrives, you will stay there forever and the rest of the program will hang right there. Write a new function that returns a character if available or 00h if not. That way, you can poll the UART without hanging the program.
@JohnInTX Here is my thinking
C:
#include <xc.h>
#include <stdio.h>
#include <conio.h>

// CONFIG
#pragma config FOSC = HS
#pragma config WDTE = OFF
#pragma config PWRTE = OFF
#pragma config BOREN = ON
#pragma config LVP = OFF
#pragma config CPD = OFF
#pragma config WRT = OFF
#pragma config CP = OFF
//END CONFIG

#define ENCODER RC0
#define SENSOR  RC1
#define KICKER  RD0
#define _XTAL_FREQ 20000000

__bit gotIRQ;  // signals main that an interrupt
void putch(char data){               
    while(!TRMT);
    TXREG = data;
}
unsigned char getch()
{
    if(OERR == 1){      // reset UART on overflow error
        CREN = 0;
        CREN = 1;
    }
    while(RCIF==0);    // Wait till the data is received
    return(RCREG);     // Return the received data to calling function
}
void send (char *s)
{
  while (*s != 0)
  putch(*s++);
}

}
void main(void)

{

    char data;
    unsigned int ShiftReg = 0; //  Init to 0
    INTCON = 0; // No interrupts
    TRISC = 0b00000011; // RC0 Eencoder Pin RC1 Sensor Pin
    TRISD = 0b00000000; // RD0 Kicker pin
   
    TXSTA = 0b00100100;                           // TX enabled, BRGH=1
    RCSTA = 0b10010000;                           // Serial Port, Continuous Receive enabled
    SPBRG = 0x81;                                 // baud rate 9600
   
   //CCP1 MODULE INITIALIZATION
   T1CON = 0b00000011;  // 1:1 prescale, OSC disabled, Input Synchronized, External clock on T1CKI(RC0), Timer ON
   CCP1CON = 0b00001011;  // Compare mode using CCPR1H and CCPR1L as a 16 bit value
//Set CCPR1H and CCPR1L (16 bits) to the number of encoder pulses e
    CCPR1H = 0x03;
    CCPR1L = 0x84;
    CCP1IF = 0;
    CCP1IE = 1;  //Enabled CCP1 interrupt
    INTCON = 0xc0;  //Enabled Global interrupts & Peripherals interrupt
    while (1)
    {
   
      if (SENSOR == 1)
      {
           printf("\rThe Sensor is: %d", SENSOR);
          
           data = getch (); // Receive a char from serial port
          
           if (data ==  'B')
           {
               if (gotIRQ)
              {
                  gotIRQ = 0;  // acknowledge the interrupt ** ALWAYS and before the delay **
                  ShiftReg <<= 1;  // shift the integer shift register one bit left. LSbit = 0 after shift
                  if (SENSOR == 1)
                  ShiftReg |= 0x0001;  // bad object, put 1 in LSbit
                  if(ShiftReg & 0x0400)  // and if the #10 bit after shift is '1', kick it
        
                  {
                     KICKER = 1;  // set output pulse high
                     __delay_ms(40);  // *groan* Delay to see output ( inbuilt delay)
                     KICKER = 0;  // set output pulse low
                  }// kicker
              }// gotIRQ
           }
       }
      
    }
void __interrupt() IRQ(void){
  // CCP1 Interrupt
  if(CCP1IF == 1)  // if the CCP1 Interrupt flag is set...
  {
     CCP1IF = 0;
     gotIRQ = 1;  // 'Signal' main that an interrupt happened
  }
}
The problem with this code it doesn't check condition when sensor doesn't sense the object and when PC send 'G'
 

JohnInTX

Joined Jun 26, 2012
4,787
I don't think a 40 ms delay is the problem I think the counter of pic16f877a is not much capable to count pulse of encoder at high speed so I want to check the counter of other chip

@JohnInTX Can this be a reason ?
Maybe. I looked at it in detail (and showed my calculations) in #150 here:
https://forum.allaboutcircuits.com/...tion-and-rejection.158059/page-8#post-1389586

What makes you think it is not counting fast enough into the counter?
What is the max frequency you are looking for?

I actually think the 18F would be a worthwhile replacement but you really should know EXACTLY where your problem here is before changing. Otherwise, you never know what is going on and you'll spend a lot of time chasing rainbows.

Going to the 18F would allow you to use the MCC code generator which can save lots of time and grief, too.

What do you think?
 

JohnInTX

Joined Jun 26, 2012
4,787
The problem with this code it doesn't check condition when sensor doesn't sense the object and when PC send 'G'
It doesn't need to check the condition if the sensor doesn't detect an object, right? And think about the logic: this code sets up a rejection, yes. That rejection only happens when the PC says 'B', yes again? So can't you just ignore 'G' from the PC? You DO have to wait for a character but the only one you have to do anything about is 'B'.

Annnnddd.. this whole thing runs at one sense-decision per interrupt right? So... it should wait for that interrupt, do one and only one complete shift, sense, ask PC to scan, wait for PC response, queue up a kick in the shift register if the response is 'B', check the other end of the shift register for kicking the object there.

Sketch the sequence out on paper first. Trace it out mentally. Only when it makes complete sense do you code it.

And where is all of that other stuff like printf("\rThe Sensor is: %d", SENSOR); coming from? You can see a '1' on the screen as easily as all of that. When you send long lines of text, you add about 1ms delay per character at 9600 baud. Can you afford that? I don't know either so leave it out.
 

Thread Starter

daljeet795

Joined Jul 2, 2018
295
Consider what getch() does. If no character arrives, you will stay there forever and the rest of the program will hang right there. Write a new function that returns a character if available or 00h if not. That way, you can poll the UART without hanging the program.
@JohnInTX Do you mean I have to write a function that returns either 'B' or 'G.' if the PC sends 'G' function should be returned 'G' and if the PC sends 'B' function should be returned 'B' and

What makes you think it is not counting fast enough into the counter?
What is the max frequency you are looking for?
I think you are asking for the output frequency of the encoder pulses
This document show Output frequency ≤300 kHz (TTL)
http://pfinder.baumer.com/pfinder_m...t/Drehgeber/Baumer_EIL580_Vollwelle_DS_EN.pdf

while testing code on the belt rejection was working on the 30% speed of the belt. I tested code with different speed like 15%, 20% up to 30% rejection happen but the speed of belt increase from 30% to 100 % rejection doesn't happen

There may many reasons behind this but my guess PIC16f877A is not counting pulses of encoder at high speed
 

JohnInTX

Joined Jun 26, 2012
4,787
1) The function just returns whatever the PC has sent or 00h if it hasn’t sent anything. You decode the ‘B’ later.

2) It isn’t running at 300khz, that would be 3600 RPM. I don’t think your belt is moving that fast. So,
What is the calculated input frequency at the desired max speed?
What is the inpit frequency where is starts to malfunction?
What is the interrupt rate at both of those points?
Have you inspected the signal with an oscilloscope to confirm that the optos can operate that fast?
Have you checked my calculations that indicate that the input count rate is sufficient and validate the assumptions I made?

Edit: the PIC should count a little over 4MHz so I don’t think that is your problem. The 4N25 should be good enough but your circuit could be better. You are hitting the input with about .8 Vdd with the voltage divider and Vce of the phototransistor. That is marginal for the Schmitt T1CKI. You also don’t have an active pull-down, just 12.2K to ground. That will be slow. I would use a common collector arrangement so that the pull down is active and the pull up is 1K to Vdd. That will be faster and swing closer to the rails. Scope it to be sure.
Your circuit:
https://forum.allaboutcircuits.com/attachments/upload_2019-4-1_10-36-27-png.173840/

Good luck!
 
Last edited:

Thread Starter

daljeet795

Joined Jul 2, 2018
295
If no character arrives, you will stay there forever and the rest of the program will hang right there. Write a new function that returns a character if available or 00h if not. That way, you can poll the UART without hanging the program.
I am struggling here perhaps it's what you said

C:
unsigned char wait_for_a_PC(void)
{
  unsigned int PC = 0; 
  while (PC == 0) 
    PC = CheckPC()); 
  
  return PC;  // then return that value
}

unsigned char CheckPC()
{
    unsigned char i;   
  {
  if(i == 'B')
   return B; 
  }
  return G;     
}
 

JohnInTX

Joined Jun 26, 2012
4,787
Uhh.. no. Study this. It does the job as I understand it.
C:
#include <xc.h>
#include <stdio.h>
#include <conio.h>
// CONFIG
#pragma config FOSC = HS
#pragma config WDTE = OFF
#pragma config PWRTE = OFF
#pragma config BOREN = ON
#pragma config LVP = OFF
#pragma config CPD = OFF
#pragma config WRT = OFF
#pragma config CP = OFF
//END CONFIG
#define ENCODER RC0
#define SENSOR  RC1
#define KICKER  RD0
#define _XTAL_FREQ 20000000
__bit gotIRQ;  // signals main that an interrupt occurred
__bit PCisScanning;  // 1 = we sent a scan request to the PC and expect a reply
unsigned char PCreply; // holds reply from PC

void putch(unsigned char data){
  while(!TRMT);
  TXREG = data;
}

// checkPC: checks UART, returns a char received or '\0' if none - does not wait on receive
unsigned char checkPC(void){
  if(OERR == 1){  // reset UART on overflow error
  CREN = 0;
  CREN = 1;
  }
  if(RCIF)  // if a char has been received
  return RCREG;  // return the char
  else
  return ('\0');  // else, return 00
}

void main(void)
{
  char data;
  unsigned int ShiftReg = 0; //  Init to 0

  INTCON = 0;  // No interrupts
  TRISC = 0b00000011; // RC0 Encoder Pin RC1 Sensor Pin
  TRISD = 0b00000000; // RD0 Kicker pin

  TXSTA = 0b00100100;  // TX enabled, BRGH=1
  RCSTA = 0b10010000;  // Serial Port, Continuous Receive enabled
  SPBRG = 0x81;  // baud rate 9600

  //CCP1 MODULE INITIALIZATION
  T1CON = 0b00000011;  // 1:1 prescale, OSC disabled, Input Synchronized, External clock on T1CKI(RC0), Timer ON
  CCP1CON = 0b00001011;  // Compare mode using CCPR1H and CCPR1L as a 16 bit value
  //Set CCPR1H and CCPR1L (16 bits) to the number of encoder pulses e
  CCPR1H = 0x03;
  CCPR1L = 0x84;
  CCP1IF = 0;
  CCP1IE = 1;  //Enabled CCP1 interrupt
  INTCON = 0xc0;  //Enabled Global interrupts & Peripherals interrupt

  while (1)
  {
  if (gotIRQ) // everything runs once per belt segment
  {
  gotIRQ = 0;  // acknowledge the interrupt ** ALWAYS and before the delay **
  ShiftReg <<= 1;  // shift the integer shift register one bit left. LSbit = 0 after shift

  if (SENSOR == 1) // if there is an object present
  {
  putch('1');  // ask the PC to scan the object
  PCisScanning = 1;  // note that we ARE expecting a reply from PC
  }
  else
  {
  putch('0');  // you only need this if the PC needs to know about each segment on the belt
  // it also tells the PC that the comms are still working
  PCisScanning = 0;  // note that we are NOT expecting a reply from PC
  }

  // while the PC is (maybe) scanning, use that time to see if you need to kick
  if(ShiftReg & 0x0400)  // if the #10 bit after shift is '1', kick the object at end of belt
  {
  KICKER = 1;  // set output pulse high
  __delay_ms(40);  // *groan* Delay to see output ( inbuilt delay)
  KICKER = 0;  // set output pulse low
  }// kicker

  // now if we expect a reply from PC wait for it but not forever
  // if not, just back to top of loop
  if(PCisScanning == 1)
  {
  //wait for the PC reply OR another interrupt
  while(((PCreply = checkPC()) == '\0') && !gotIRQ);

  if(PCreply == 'B')  // if got a reply before an interrupt AND it's 'B'..
  ShiftReg |= 0x0001;  // bad object, put 1 in LSbit

  // here you can add some error processing if you got the next
  // interrupt before the PC replied i.e. dead PC or belt too fast
  // you can also decode other responses from the PC here.  Note
  // that you don't have to process a 'G' response if all you want
  // to know is if the scan was bad.  You could decode 'G' to know
  // that the PC was working and the comms were good if you want.

  } // process wait for PC
  } // gotIRQ
  } // while loop
}//main


void __interrupt() IRQ(void){
  // CCP1 Interrupt
  if(CCP1IF == 1)  // if the CCP1 Interrupt flag is set...
  {
  CCP1IF = 0;
  gotIRQ = 1;  // 'Signal' main that an interrupt happened
  }
}
 

Thread Starter

daljeet795

Joined Jul 2, 2018
295
Have you checked my calculations that indicate that the input count rate is sufficient and validate the assumptions I made?

Edit: the PIC should count a little over 4MHz so I don’t think that is your problem. The 4N25 should be good enough but your circuit could be better. You are hitting the input with about .8 Vdd with the voltage divider and Vce of the phototransistor. That is marginal for the Schmitt T1CKI. You also don’t have an active pull-down, just 12.2K to ground. That will be slow. I would use a common collector arrangement so that the pull down is active and the pull up is 1K to Vdd. That will be faster and swing closer to the rails. Scope it to be sure.

Good luck!
@JohnInTX many thank

If I am not wrong in the reading datasheet so I think this encoder should work with 5V DC.

upload_2019-6-1_21-4-42.png

http://pfinder.baumer.com/pfinder_m...t/Drehgeber/Baumer_EIL580_Vollwelle_DS_EN.pdf

I haven't tried at 5V supply yet but I will give 5V power

In case if encoder doesn't work on the 5V DC Then I am thinking to use the following circuit

as you suggested I am using collector output of 4n25

upload_2019-6-1_21-8-44.png

so I think It would be faster then previous

Will it batter to use a resistor divider circuit to convert 24V into 5V DC?
 

Attachments

Last edited:

JohnInTX

Joined Jun 26, 2012
4,787
Well, page 3 of the datasheet says that the voltage/output is determined by the part number of the encoder. One encoder won't do all of the listed voltages.
so I think It would be faster then previous
Did you ever actually scope out the opto signal? That is kind of important here. Sooner or later you have to quit flailing around and drill down into each problem or this will never get done.

But if you are using the common collector configuration:
Since you have a 24V encoder (not 5V/RS422), I would re-do the opto with a 1.1K collector resistor for the best speed in the current configuration. The calculation:
Input current: (24V - 1.5Vf) /1K = 22.5ma. That is actually OVER the encoder's output current spec of <=20ma. The smallest your LED resistor can be is 1125 ohms.
Assume 20ma input. CTRmin = 20% so 20ma in gives you 20ma*.2 = 4ma collector current.
You want to pull down the input to pretty much 0 (plus Vce(sat)) so 5Vdd/4ma = 1250 ohms minimum collector R. You also want this R to be the minimum you can get away with to keep the speed up. Bigger R means slower rise time.
 

Thread Starter

daljeet795

Joined Jul 2, 2018
295
Well, page 3 of the datasheet says that the voltage/output is determined by the part number of the encoder. One encoder won't do all of the listed voltages.
EIL 580-SC10.5L.N.05000.A-11103997

N 8...30 VDC, HTL/push-pull, 6 channel

N indicates It works between 8 to 30 V DC

Did you ever actually scope out the opto signal? That is kind of important here. Sooner or later you have to quit flailing around and drill down into each problem or this will never get done.
I don't have a scope I can't see signal's

But if you are using the common collector configuration:
Since you have a 24V encoder (not 5V/RS422), I would re-do the opto with a 1.1K collector resistor for the best speed in the current configuration. The calculation:
Input current: (24V - 1.5Vf) /1K = 22.5ma. That is actually OVER the encoder's output current spec of <=20ma. The smallest your LED resistor can be is 1125 ohms.
Assume 20ma input. CTRmin = 20% so 20ma in gives you 20ma*.2 = 4ma collector current.
You want to pull down the input to pretty much 0 (plus Vce(sat)) so 5Vdd/4ma = 1250 ohms minimum collector R. You also want this R to be the minimum you can get away with to keep the speed up. Bigger R means slower rise time.
@JohnInTX If I understand correctly Do you mean I have to use 1.1K resistor instead of 10K resistor only ?

finally, circuit looks like following
upload_2019-6-1_22-27-47.png
 
Last edited:

JohnInTX

Joined Jun 26, 2012
4,787
EIL 580-SC10.5L.N.05000.A-11103997
N 8...30 VDC, HTL/push-pull, 6 channel
N indicates It works between 8 to 30 V DC
I know. That's why you can't use 5V and that's where I got the specs for the 20ma output current.


I don't have a scope I can't see signals
Well, a lot of guessing in our future I suspect. Seriously, a scope is mandatory for this kind of work.


If I understand correctly Do you mean I have to use 1.1K resistor instead of 10K resistor only ?
finally, circuit looks like following
View attachment 178723
Since you have a 24V encoder (not 5V/RS422), I would re-do the opto with a 1.1K collector resistor for the best speed in the current configuration. The calculation:
Input current: (24V - 1.5Vf) /1K = 22.5ma. That is actually OVER the encoder's output current spec of <=20ma. The smallest your LED resistor can be is 1125 ohms.
Assume 20ma input. CTRmin = 20% so 20ma in gives you 20ma*.2 = 4ma collector current.
You want to pull down the input to pretty much 0 (plus Vce(sat)) so 5Vdd/4ma = 1250 ohms minimum collector R. You also want this R to be the minimum you can get away with to keep the speed up. Bigger R means slower rise time.
Circuit is good. 1.2K on the input, 1.3K on the output collector.
 
Last edited:

JohnInTX

Joined Jun 26, 2012
4,787
I think you are asking for the output frequency of the encoder pulses
This document show Output frequency ≤300 kHz (TTL)
Ref post #289 I calculated the RPM at max encoder frequency using your 300KHz figure. For the HTL output, it maxes out at 160KHz. That is:
160K Pulses/sec
------------------- * 60 sec/min = 1920RPM max rotational speed. I don't think you are going that fast.
5000PP/Rev

160K pulses/sec is a period of 6.25 uSec. This is well within the PIC's T1CKI input minimum period requirement of 240ns. So I think the basic counting of the PIC is OK at whatever speed the encoder is at. The opto speed is another story but one thing at a time.

You still need to let us know what those pulse rates asked for in #289 are. That way we can calculate the interrupt rate and see if you have enough time to process them or whether you need a faster chip.
 

Thread Starter

daljeet795

Joined Jul 2, 2018
295
Ref post #289 I calculated the RPM at max encoder frequency using your 300KHz figure. For the HTL output, it maxes out at 160KHz. That is:
160K Pulses/sec
------------------- * 60 sec/min = 1920RPM max rotational speed. I don't think you are going that fast.
5000PP/Rev

You still need to let us know what those pulse rates asked for in #289 are. That way we can calculate the interrupt rate and see if you have enough time to process them or whether you need a faster chip.
2) It isn’t running at 300khz, that would be 3600 RPM. I don’t think your belt is moving that fast. So,
What is the calculated input frequency at the desired max speed?
What is the inpit frequency where is starts to malfunction?
What is the interrupt rate at both of those points?
1200 RPM motor moving the belt. There is VFD to control the speed of Motor

@JohnInTX I have no idea how to calculate input frequency at the desired max speed?
 

JohnInTX

Joined Jun 26, 2012
4,787
I don't have a scope I can't see signal's
Yet you were ready to buy another encoder to try and see if it works. Guessing. That encoder is roughly $350 US .
For less than $100US, you can get a 2 channel, 25MHz USB scope (displays on your PC) and see what's going on. For $350 USD, you can get into an entry level Siglent or Rigol and work like a BOSS. Post a request in our Test and Measurement forum to get advice on the best one to get.

I have no idea how to calculate input frequency at the desired max speed?
Been through that:
https://forum.allaboutcircuits.com/...tion-and-rejection.158059/page-8#post-1389586
You have too:
https://forum.allaboutcircuits.com/...tion-and-rejection.158059/page-8#post-1390754

Get on it.
 
Last edited:
Top