B4R Question Error in reading a button!

Beja

Expert
Licensed User
Longtime User
Hello friends
currentButtonState = buttonPin.Read() = 0
'the error is: Unknown member -read'
syntax correction appreciated!
 

Beja

Expert
Licensed User
Longtime User
Here's the complete code:
B4X:
Sub Process_Globals
    Public Serial1 As Serial
    Private tm As TM1637Display
    Private counter As Int
    Private buttonPin As Pin
    Private lastButtonState As Boolean
    Private lastDebounceTime As Long
    Private debounceDelay As Long
End Sub

Private Sub AppStart
    Serial1.Initialize(115200)
    Log("AppStart")
    
    tm.Initialize(2, 3)  ' Initialize the display
    buttonPin.Initialize(4, 0)  ' Initialize button pin (change 4 to your actual button pin)
    
    counter = 0  ' Initialize counter to 0
    lastButtonState = False
    lastDebounceTime = 0
    debounceDelay = 50  ' Adjust debounce delay as needed
    
    ' Set up a loop to continuously check the button state
    Dim loopTimer As Timer
    loopTimer.Initialize("LoopTimer_Tick", 50)
    loopTimer.Enabled = True
End Sub

Sub LoopTimer_Tick
    Dim currentButtonState As Boolean
    currentButtonState = buttonPin.Read() = 0  ' Assuming button press pulls the pin low (change to 1 if high)
    
    ' Check if the button state has changed and debounce
    If currentButtonState <> lastButtonState Then
        lastDebounceTime = Millis
    End If
    
    If (Millis - lastDebounceTime) > debounceDelay Then
        If currentButtonState <> lastButtonState Then
            lastButtonState = currentButtonState
            
            ' Increment counter if button is pressed
            If currentButtonState = True Then  ' Button pressed
                counter = counter + 1
                tm.ShowNumberDec2(counter, True, 4, 0)
            End If
        End If
    End If
End Sub
 
Upvote 0

emexes

Expert
Licensed User
https://www.b4x.com/b4r/help/core.html#pin_digitalread

DigitalRead As Boolean
Reads the pin value and returns true or false.

Also, it returns Boolean, thus "= 0" is not needed.

Although you might still need to invert the state, if button is "active low" eg:

B4X:
    Private buttonPin As Pin

...

Sub LoopTimer_Tick
    Dim currentButtonState As Boolean
    currentButtonState = (buttonPin.DigitalRead() = False)    ' Assuming button press pulls the pin low (False?)
 
Upvote 0

Beja

Expert
Licensed User
Longtime User
Should Read not be DigitalRead?

Right, in B4R it's digitalread Btn_StateChanged (State As Boolean)
https://www.b4x.com/b4r/help/core.html#pin_digitalread



Also, it returns Boolean, thus "= 0" is not needed.

Although you might still need to invert the state, if button is "active low" eg:

B4X:
    Private buttonPin As Pin

...

Sub LoopTimer_Tick
    Dim currentButtonState As Boolean
    currentButtonState = (buttonPin.DigitalRead() = False)    ' Assuming button press pulls the pin low (False?)

H iemexes
Thanks for the tip, there's no more error messages. the display is blank though.. not responding to the button press. Button is between pin4 and gnd. Any meaning for that?
 
Upvote 0

Beja

Expert
Licensed User
Longtime User
Edited:
Sub Process_Globals
    Public Serial1 As Serial
    Private tm As TM1637Display
    Private counter As Int
    Private buttonPin As Pin
    Private lastButtonState As Boolean
    Private lastDebounceTime As Long
    Private debounceDelay As Long
End Sub

Private Sub AppStart
    Serial1.Initialize(115200)
    Log("AppStart")
    
    tm.Initialize(2, 3)  ' Initialize the display
    buttonPin.Initialize(4, 0)  ' Initialize button pin (change 4 to your actual button pin)
    
    counter = 0  ' Initialize counter to 0
    lastButtonState = False
    lastDebounceTime = 0
    debounceDelay = 50  ' Adjust debounce delay as needed
    
    ' Set up a loop to continuously check the button state
    Dim loopTimer As Timer
    loopTimer.Initialize("LoopTimer_Tick", 50)
    loopTimer.Enabled = True
End Sub

'Sub LoopTimer_Tick
'    Dim currentButtonState As Boolean
'    currentButtonState = buttonPin.Read() = 0  ' Assuming button press pulls the pin low (change to 1 if high)
    
    
    Sub LoopTimer_Tick
    Dim currentButtonState As Boolean
    currentButtonState = (buttonPin.DigitalRead() = False)    ' Assuming button press pulls the pin low (False?)
    
    
    ' Check if the button state has changed and debounce
    If currentButtonState <> lastButtonState Then
        lastDebounceTime = Millis
    End If
    
    If (Millis - lastDebounceTime) > debounceDelay Then
        If currentButtonState <> lastButtonState Then
            lastButtonState = currentButtonState
            
            ' Increment counter if button is pressed
            If currentButtonState = True Then  ' Button pressed
                counter = counter + 1
                tm.ShowNumberDec2(counter, True, 4, 0)
            End If
        End If
    End If
End Sub
 
Upvote 0

emexes

Expert
Licensed User
Button is between pin4 and gnd. Any meaning for that?

How is it pulled high when the button is not pressed?

Is it done internally within the microcontroller, or by the Arduino (or ESP32?) board, or by your own circuitry with a resistor to VCC?

Even better: what board or module are you using? As in "brand" and exact model number id and colloquial name.

Lol more info is better, but to be honest, sometimes I have trouble working out exactly which ESP32 variant I have, even when it's right in front of me.

edit: in fact, I remember a few years ago resorting to trading photos of a module, in order to determine wtf what we were dealing with
 
Upvote 0

emexes

Expert
Licensed User
Button is between pin4 and gnd. Any meaning for that?

https://learn.sparkfun.com/tutorials/pull-up-resistors/all

1724486803414.png
 
Upvote 0

Gerardo Tenreiro

Active Member
Licensed User
Hi
The best option is to create an interrupt every time the button value is changed with the "AddListener" instruction

First you define the pin as an input and then you add it to the list so that when it changes value the code is executed and you can process it.
Something like that

#Region Project Attributes
#AutoFlushLogs: True
#CheckArrayBounds: True
#StackBufferSize: 600
#End Region
'Ctrl+Click to open the C code folder: ide://run?File=%WINDIR%\System32\explorer.exe&Args=%PROJECT%\Objects\Src

Sub Process_Globals
Public Serial1 As Serial
Public E4 As Pin

End Sub

Private Sub AppStart
Serial1.Initialize(115200)
Log("Inicio Aplicacion")

E4.Initialize(4,E4.MODE_INPUT_PULLUP)

E4.AddListener(CH_E4)


End Sub

Sub CH_E4(Estado As Boolean)
If Estado = Treu Then
Log("Entrada Activa")
Else
Log("Entrada Desactiva")
End If

End Sub
 
Upvote 0

emexes

Expert
Licensed User
Button is between pin4 and gnd. Any meaning for that?

How is it pulled high when the button is not pressed?

Is it done internally within the microcontroller, or by the Arduino (or ESP32?) board, or by your own circuitry with a resistor to VCC?

What board or module are you using?
 
Upvote 0

Beja

Expert
Licensed User
Longtime User
I reviewed the code but didnt find anyone
How is it pulled high when the button is not pressed?

Is it done internally within the microcontroller, or by the Arduino (or ESP32?) board, or by your own circuitry with a resistor to VCC?

What board or module are you using?

pull-up fesistor is from the pin to vcc, so the pin is always high until the button is pressed. As mentioned I reviewed the code and found nothing needs to be corrected .
 
Upvote 0

emexes

Expert
Licensed User
I reviewed the code and found nothing needs to be corrected .

Well, if your project is not working then something needs to be corrected. Could be hardware, could be software.

Hardware can be checked by putting a multimeter to pin 4 of the Arduino shield "bus". Make sure that that pin is ~3 or ~5 volts normally, and changes to ~0 volts when button is pressed.

Maybe the pin is not initialized correctly, eg why are you hardcoding the mode:

B4X:
buttonPin.Initialize(4, 0)  ' Initialize button pin (change 4 to your actual button pin)

rather than using eg MODE_INPUT or MODE_INPUT_PULLUP constant listed on the B4R Pin object help page:

https://www.b4x.com/b4r/help/core.html#pin_initialize
 
Upvote 0

emexes

Expert
Licensed User
Well, if your project is not working then something needs to be corrected.

More ideas:

Arduino pin numbering starts from 0. For most bus and chip pin numbering, the first pin is pin 1, but for Arduino shields the first pin is Pin0 aka D0. Thus Pin4 is actually the 5th pin along the shield connector. I think everybody's miscounted pin numbers at least once ? and experts probably more than once ?

Maybe try using Pin2 (the third pin along) instead of Pin4, because Pin2 doesn't have any other additional functions that might be interfering with its use as a digital input.
 
Upvote 0

Beja

Expert
Licensed User
Longtime User
More ideas:

Arduino pin numbering starts from 0. For most bus and chip pin numbering, the first pin is pin 1, but for Arduino shields the first pin is Pin0 aka D0. Thus Pin4 is actually the 5th pin along the shield connector. I think everybody's miscounted pin numbers at least once ? and experts probably more than once ?

Maybe try using Pin2 (the third pin along) instead of Pin4, because Pin2 doesn't have any other additional functions that might be interfering with its use as a digital input.

Thank you for the appreciated efforts to help with this issue.
Problem is solved, and if you promise not to tell anyone I will tell you what was the culprit.
First let me apologize to Erel, who provided a very clean and tested code to use the TM1637 display. His code was so simple and straitforward. It only needed a transistor, a button , a couple of resistors and some diodes.
An infra-red diode was reversed -Ouch! that's all.
You spent a lot of time, and to make it up, I will post this small project with circuit sch and Ardiono scetch as soo as it's finished.
 
Upvote 0
Top