Port Manipulation

Hello Evryone,

I could use some guidance on the most efficient way to convert an analog signal to a 8bit word. I looked at port manipulation but having a hard time finding any examples.

Analog signal (POT) -------------> 8bit word

0V -------------> 00000000
0.1V -------------> 0000001
0.2V -------------> 0000010
*
*
*
*
*
4.9V -------------> 11111110
5.0V -------------> 11111111

I was thinking of mapping the the analog voltage to the binary word. Im a bit confused on how to write a binary word to a specified number pins. Any example code or good reference papers would be extremely helpful.

Thanks,
Monito

The value returned by analogRead is a 10 bit integer, 00 00000000 to 11 11111111, you could throw away the lower 2 bits and cast whats left to a byte:

byte val = analogRead(x) >>2;

If you have an Arduino UNO none of the ports have all 8 pins available, it could be done by splitting the byte across 2 ports, what exactly are you trying to do?

monito72:
I could use some guidance on the most efficient way to convert an analog signal to a 8bit word.

What do you mean "convert"? Input or output?

If you mean "input" then it already takes 104 µs to do an ADC read (normally) so efficiently converting it to a byte is not really a big consideration.

Thank you for the feedback.

I am building a laser control box. To control the output power of the laser it requires 8bits, a PWM pin and a few bits to read off the status. I attached a photo of the laser input connector.

My inputs are 2 potentiometer and a LCD display. The outputs needed are 8bits to driver the power of the laser. INPUT 1 bit alarm status. INPUT 1 bit Status signal. OUTPUT 1 bit Laser on/ off. OUTPUT 1 PWM 20-80KHz. INPUT 1 ANALOG Temperature. and OUTPUT Guide Beam. See attached port connection. Most of it I know how todo but stuck on how to convert a analog voltage from a pot to 8bit word. Splitting the bits would be fine.

Are you planning to use an Arduino? If so, which one? I am only familiar with those that use Atmega 328.

I can use either UNO or MEGA. Currently Im working on getting the 8bits to work. I can get it to work with print line

byte val = analogRead(sensorPin) >>2;
Serial.println(val, BIN);

But how do you assign this to pins? Which will be the MSB?

Assign to pins? What do you mean?

The right-most bit is the LSB, if that looks like what you want give me a little time to lash up a trial sketch. Let me know within 1 hour, its near ZZZZ time.

Yes that's correct.

Thanks for the help!

OK, stand by awhile, it takes more time to comment the code than to write it.

Sorry for long delay, been searching unsuccessfully for a decent test pot, here's what I have so far, try it with leds on pins 2 - 9, don't know if it will interfere with serial or not, got to sleepy to think. I'll check back later today.

void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);
  for(byte i = 2;i < 10;i++)
    pinMode(i,OUTPUT); // Pins 2 - 9 are outputs
    
}

void loop() {
  // put your main code here, to run repeatedly:
  byte val = analogRead(0) >> 2;
  PORTD = val << 2 ;  // lower 6 bits to pins 2 - 7
  PORTB |= val >> 6 ; // upper 2 bits to pins 8 - 9
  Serial.print(val);Serial.print("  ");
  Serial.print(val * 5.0 / 255);Serial.print("  ");
  Serial.print(PORTD);Serial.print("  ");Serial.println(PORTB,BIN);
  delay(1000);

monito72
Sorry I'm taking so long but just got in from shopping, now got to go out for dinner.
Here's an edited version for trial, my main worry is to not clobber pins not involved, I never found a good pot, only a tiny trimmer not good for my shaky hands, give it a try, I'll get back soon as I can.

byte pdmsk = 0b00000011, pbmsk = 0b11111100;
byte pbtmp, pdtmp;
void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);
  for(byte i = 2;i < 10;i++)
    pinMode(i,OUTPUT); // Pins 2 - 9 are outputs
    
}

void loop() {
      
  byte val = analogRead(0) >> 2;
   Serial.print(val);Serial.print("  ");
  pdtmp = PORTD & pdmsk;
  PORTD = val << 2 | pdtmp;  // lower 6 bits to pins 2 - 7
  pbtmp = PORTB & pbmsk; 
  PORTB = pbtmp | val >> 6; // upper 2 bits to pins 8 - 9
  
  
   
  Serial.print(PORTB & 0b00000011,BIN);
  Serial.print("  ");
  Serial.println(PORTD >> 2,BIN);
 
  delay(500);

}

The code worked. This was exactly what I was looking for.

After some more tests it turns out that it doesnt work. If I start low on the pot 0V and turn the pot to 5V it works but going from 5V to 0V it doesnt clear 2 bits. It stays high even though it should be low.