Understanding digitalread()


#1

I’m new to electronics, and playing with Argon/Xenon.

I’m trying to understand how to read if a circuit is open/closed but not sure if I’m going about it the right way.

On an Argon, I have wiring from 3V3 to an LED for feedback, then reed switch set as normally closed, then going back to GND.

So 3V3-Resistor-LED-ReedSwitchNC-ReadSwitchCOM-GND.

When I open the reed switch, the light goes on. Hooray. But I want to be able to check if the switch is open, but I can’t seem to get it right. Rather than trying to fix what I have, what’s the best way to do that?

Thanks for any help and advice.

This is what I’ve tried:

I’ve tried pinMode(pin, INPUT / INPUT_PULLUP / INPUT_PULLDOWN), and putting the wire from D6 before and after the reedswitch.

Checking the variable on the web console or Particle mobile app always returns 1 if D6 is before the reed switch, or 0 after the reed switch.

Using digitalRead(), does D6 become like GND, so the circuit is complete if it is connected before the reed switch, regardless if the reed switch is open or closed?

int pin = D6;
int pinValue;

void setup() {
    
    pinMode(pin, INPUT);            // Before ReedSwitch = Always 1. After ReedSwitch = Always 0.
    //pinMode(pin, INPUT_PULLDOWN); // Before ReedSwitch = Always 1. After ReedSwitch = Always 0.
    //pinMode(pin, INPUT_PULLUP);   // Before ReedSwitch = Always 1. After ReedSwitch = Always 0.
    Particle.variable("PinStatus", pinValue);
}

void loop() {
    pinValue=digitalRead(pin);
}



#2

Hi @daunce,

I’m not sure I fully understand your circuit. You say the open the switch the LED comes on? That doesn’t seem to make a circuit, are you sure it’s not NO and you’re closing the switch?

I’m also not sure why you’re not seeing different values. It seems if you put the wire between the LED and the switch that you should see changing values. For example here’s an example circuit and you can see the voltage change when you close the circuit.

Have you tried it with the analog pins to see what values they see?

Have you tried just using the switch alone between the pin and GND (with INPUT_PULLUP) to make sure everything else is working?


#3

Thanks for the advice @kenmacd. I may have mixed up my terminology in regards to the reed switch.

I removed everything, and just had 3V3-GND with the D6 wire inbetween, and using INPUT_PULLUP, D6 returns 0 when it’s all plugged in.

When I unplugged GND, it returns 1.

When I unplug 3V3, it returns 0

When I unplug D6, it returns 1.

This is why I’m not sure I understand how D6 should read it. I thought when it’s all connected, it would read 1, because there’s voltage going through it. It’s the opposite of what I expected.

So if I have it backwards, and 0 indicates voltage, why does it return 0 when I unplug 3V3?


#4

If you are connecting 3v3 to ground on the Argon, you are shorting out your power supply, and may well release the magic smoke.

You can try leaving D6 unconnected, and with the pullup enabled, it should have a value of 1, then when you connect D6 to ground (and not 3v3), it should have a value of 0.


#5

oh… I’m confused as to how it should be wired up then… I thought it always started at 3V3, then chained through resisters, LEDs, switches etc, and then to GND, so I didn’t think there was anything wrong with removing those components in between.

How should it be wired up for a basic test?

To visualise it, see below. (It’s not an argon, but hopefully it’s close enough)


#6

You have GND and 3V3 shorted out in that picture. Not good.
Take a look at this to get you started:
https://docs.particle.io/tutorials/hardware-projects/hardware-examples/xenon/


#7

Thanks for the link @kenco. I appreciate you all hanging in there.

  1. From that pic, if D6 was set to high, does it have the same outcome as if it was connected to 3V3 instead?
  2. And if you removed the LED & resistor, doesn’t it end up connecting back to GND anyway, so 3V3 or D6-[LED]-[Resistor]-GND, would be 3V3/D6-GND ? I’m confused on this one.

  1. If I wanted to confirm the LED was on in that pic, where would I connect a wire to use digitalRead()? My expectation would be that if I was to pull out a wire anywhere in that path, the LED would turn off, and I could confirm that with a digitalRead().

I know that " ah ha!" moment is coming… fingers crossed… I’m just a bit slower these days…


#8

If you removed the LED and resistor you’d break the circuit and no current would be flowing but if you replace them with zero resistance you will create a short-circuit which will eventually damager your device as you have been warned twice before already.

You need a resistance in your path to limit the current flowing through your circuit.

Not exactly. Any given GPIO pin will only delvier aprox. 20mA and in a short-circuit condition probably only fry itself and maybe it’s neighouring circuits, but 3v3 will drive all the current it can and potentially damage a lot more than only D6.

The schematic you got from @kenmacd is what you want to replicate.
Just take the long electrode of the battery symbol as 3v3, the short as GND and the proble as your desired INPUT_PULLUP pin (e.g. D6).


#9

Answers:

  1. With respect to the breadboard picture:
    If you moved the blue wire (D6 end) to 3v3 the LED would turn on. Which would be the same scenario as D6 going HIGH. If you moved blue wire to GND (D6 end), the LED would turn off. Or D6 going LOW.

  2. If you removed the LED and resistor you would have an OPEN circuit. Your 3v3/D6-GND scenario is a SHORT circuit. You need a resistive element to limit the current so you don’t blow things up. That’s why you see 3v3–>LED–>RESISTOR—>GND Or in the picture D6–>LED–>RESISTOR–>GND.

  3. In the picture you would just jumper D6(output) to D7(input) if you wanted to read the state of the LED.


#10
`3V3
  |
 RES
  |
 LED
  |
  +------------D6 (INPUT_PULLUP) 
  |            No magnet on reed = 0V
  |
 Reed NC
  |
  0V`

#11

Thank you @ScruffR & @kenco. That makes sense now… I think… Woohoo! :smiley: I really appreciate your help today.

Just so I fully understand, in regards to the breadboard pic:

If I jumper D6(output) to D7(input), wouldn’t that be like a short circuit? or is it OK because PULLUP adds some resistance?

If I used D6(output) to D7(input) to read the state of the LED, would that accurately reflect the state of the LED? I thought it would read if D6 is high or low. What if D6 was high, and I pulled the wire going to GND?


#12

Nope, pinMode(somePin, INPUT) (no pull-resistor) would mean somePin is “virtually infinite” resistance, so virtually no current is flowing and hence no short-circuit.
With internal pull-resistors you’d have a ~40k resistance parallel to the “virtually infinite” digital circuit.
But for D7 you also have the onboard LED and its series resistor to consider.

However, if you had D6 and D7 as OUTPUT and both contradicting levels (LOW vs. HIGH) you’d create a short.

Can you clarify why you’d have an OUTPUT in connection with your reed switch?

If you happened to have forgotten what your last digitalWrite(somePin, unknownValue) may have been, you can also digitalRead(somePin) to jog your memory :wink:


#13

So the project I’m planning is like a door sensor. I thought I needed to put voltage on the line, and have the reed switch open/close, and then read the value to see if the switch was open/closed. I was also using the LED for feedback.

Based on your comment and some googling, I wired it up D6(input_PULLUP)->resistor->reed switch COM->reed switch NC->GND.

So now it returns 0 when the 2 magnets are together (door closed), and 1 when magnets are apart. Woah. Exactly what I wanted. So I was going about it all wrong. Thanks for helping.

I just don’t understand why. I thought D6 as input was like GND, which meant it had to have a +ve connection somewhere. My el-cheapo multimeter reads around 0.07V and 3.22V. Where is that voltage coming from?

This has been a great day for learning.


#14

Nope, in order to be an INPUT that pin mustnot pull the signal it wants to sense to GND.
But in order to get a reliable signal you need some “bias” to prevent the signal from floating. That’s where pull-resistors come in.

Like in real life: If you want to know what people actually think about you, you listen to their conversations about you without them knowing you are there :wink:
Once you are there you will mostly only hear a “filtered” story :flushed:
However, they need some reason to actually talk about you - that’s what the pull-resistors would be
:see_no_evil: :speak_no_evil: :hear_no_evil:


#15

I’m going to have to think about that some more for it to sink in.

I was able to open/close the reed switch, and read the status of it, as well as publish the event, and send arguments to a function to control a relay. I’m pretty happy with it. Big thanks to everyone that helped out. I couldn’t have done it without you (obviously!).

More tinkering to come.


#16

Take a look here. This might clear some things up in regards to IO on a microcontroller.
https://embeddedartistry.com/blog/2018/6/4/demystifying-microcontroller-gpio-settings