I have 8 digital pins on an Arduino connected to other hardware, as a way to communicate a number from 0-255 to the Arduino. What's an efficient way of checking those digital inputs and converting them into a single byte held in a variable?
I've know and can check the status of each bit one at a time and add it all up into a variable, but that seems to laborious and inefficient. Seems like there should be a way to set individual bits within a byte variable based on each digital input's status, or even read a byte value into a variable all at once based on the status of 8 digital inputs. Any ideas/help?
If you are using an Arduino UNO it will be a little hard to find 8 pins connected to the same port. The only port that kas all eight bits connected to pins is PORTD which covers Pin 0 through Pin 7. Unfortunately that includes Pin 0 and Pin 1 which are used for Serial. If you use them for data you can't use them for Serial.
The Arduino MEGA 2560 has several choices:
22-29 = PORTA
37-30 = PORTC (note the reversed ordering)
48-42 = PORTL (note the reversed ordering)
54-61 = PORTF
62-69 = PORTK
The closest I've been able to do on the 328P chip is to use the upper four bits of port D, pins 4 - 7, for the high nibble and the lower four bits of port B, pins 8 - 11, as the low nibble. By reading each port with a mask and adding them together, you will get one byte. If you need to use SPI then use port C, pins A0 - A3, for the low nibble. That also leaves the I2C pins available. It's not elegant but a lot faster than using bitRead and digitalRead.
ArduinoTom:
I've know and can check the status of each bit one at a time and add it all up into a variable, but that seems to laborious and inefficient.
How much free time does the processor have, in your application?
johnwasser:
If you are using an Arduino UNO it will be a little hard to find 8 pins connected to the same port. The only port that kas all eight bits connected to pins is PORTD which covers Pin 0 through Pin 7. Unfortunately that includes Pin 0 and Pin 1 which are used for Serial. If you use them for data you can't use them for Serial.
The Arduino MEGA 2560 has several choices:
22-29 = PORTA
37-30 = PORTC (note the reversed ordering)
48-42 = PORTL (note the reversed ordering)
54-61 = PORTF
62-69 = PORTK
Arctic_Eddie:
The closest I've been able to do on the 328P chip is to use the upper four bits of port D, pins 4 - 7, for the high nibble and the lower four bits of port B, pins 8 - 11, as the low nibble. By reading each port with a mask and adding them together, you will get one byte. If you need to use SPI then use port C, pins A0 - A3, for the low nibble. That also leaves the I2C pins available. It's not elegant but a lot faster than using bitRead and digitalRead.
Sorry, I'm missing the mechanics on this. I'm not following how to read a nibble all at once from a Port, or for that matter how to read a byte if I had an entire Port available... Could you dumb it down for me?
aarg:
How much free time does the processor have, in your application?
In this part of the code I actually have plenty of time, do I could digital read each pin and add up the results, it just seemed so ham-fisted. The tips posted here about Port and bit manipulation seems to be getting me into a more efficient ball park...