B4R Question [Solved] Modifying Erel's TM1637 code to use external clock!

Beja

Expert
Licensed User
Longtime User
Hello all,
I tried to modify Erel's code here , so that I can replace the generated clock on pin 2 of Arduino, with an external clock, here's the code and the logs at the end.
Please help correct the code:


TM1637 and Arduno with external clock:
Sub Process_Globals
    Public Serial1 As Serial
    Private tm As TM1637Display
    Private switchPin As Pin
    Private counter As Int
    Private lastSwitchState As Boolean
    Private debounceTime As Long
    Private lastDebounceTime As Long
End Sub

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

    ' Initialize TM1637 display
    tm.Initialize(2, 3)
  
    ' Initialize switch pin (connected to pin 4)
    switchPin.Initialize(4, Pin.INPUT_PULLUP)  ' Set pin mode to input with internal pull-up resistor
  
    ' Initialize the counter
    counter = 0
    lastSwitchState = True  ' Assume switch is not pressed initially
    debounceTime = 200  ' Debounce time in milliseconds
  
    ' Initialize a timer for periodic tasks, if needed
    'timer1.Initialize("Timer1_Tick", 1000)
    'timer1.Enabled = True
End Sub

Private Sub Timer1_Tick
    ' Optional: This can be used for other periodic tasks
End Sub

Private Sub HandleSwitch
    Dim currentSwitchState As Boolean
    currentSwitchState = switchPin.Value = Pin.LOW  ' Assuming LOW means pressed

    ' Check if the switch state has changed (falling edge detection)
    If lastSwitchState = True And currentSwitchState = False Then
        ' Increment the counter and update the display
        counter = counter + 1
        tm.ShowNumberDec2(counter, True, 4, 0)
      
        ' Record the time of this action
        lastDebounceTime = Millis
    End If

    ' Update the last switch state
    lastSwitchState = currentSwitchState

    ' Optional: Debounce logic
    If Millis - lastDebounceTime > debounceTime Then
        ' Additional debounce logic (if needed)
    End If
End Sub

Private Sub Loop
    ' Continuously check the switch state
    HandleSwitch
End Sub

'logs
'Main - 37: Undeclared variable 'pin' is used before it was assigned any value.
'Main - 19: Undeclared variable 'pin' is used before it was assigned any value.
'Main - 61: Syntax error
'Main - 58: 'end sub' is missing.

Note: I am trying to use a mechanical switch for clocking the 1637
 
Last edited:

Daestrum

Expert
Licensed User
Longtime User
try changing pin.LOW etc to switchPin.LOW
 
Upvote 0

Beja

Expert
Licensed User
Longtime User
try changing pin.LOW etc to switchPin.LOW
That worked! thanks Deastrum,
Still a couple of erros :

log
Main - 37: Unknown member: value
Main - 19: Unknown member: input_pullup
Main - 61: Syntax error
Main - 58: 'end sub' is missing.
 
Upvote 0

Daestrum

Expert
Licensed User
Longtime User
Not 100% sure ( of correct commads / terms)

But don't you need to read the pin to get the state so something like
B4X:
'currentSwitchState = switchPin.Value = Pin.LOW

currentSwitchState = (switchPin.Digital/AnalogRead(???) = switchPin.LOW)
 
Last edited:
Upvote 0

Beja

Expert
Licensed User
Longtime User
Not 100% sure ( of correct commads / terms)

But don't you need to read the pin to get the state so something like
B4X:
'currentSwitchState = switchPin.Value = Pin.LOW

currentSwitchState = (switchPin.Digital/AnalogRead(???) = switchPin.LOW)

You are correct Daestrum.. The issue is now solved and I would like to share the solution, so other can benefit from it.
The is the complete B4R code, except the debounce which I am still working on.. proubley I will use a .1 mF accross the switch pins.
The code is simple with few lines, so I didn't bring a zip file here.

I can't thank Erel enough for these wonderful tools he provided for us and supported us in developing all the time.

TM1637 and Arduno with external clock:
Sub Process_Globalsand 
    Public Serial1 As Serial
    Private tm As TM1637Display
    Private btn As Pin
    Private counter As Int = 0
End Sub

Private Sub AppStart
    Serial1.Initialize(115200)
    Log("AppStart")
    tm.Initialize(2, 3) ' Initialize the TM1637 using pins 2 and 3

    btn.Initialize(btn.A0, btn.MODE_INPUT_PULLUP) ' Using the internal pull-up resistor to prevent the pin from floating.
    btn.AddListener("Btn_StateChanged")
End Sub

Sub Btn_StateChanged (State As Boolean)
    If State = False Then  ' Button pressed
        ' Increase the counter and display it
        counter = counter + 1
        If counter > 99 Then counter = 0 ' Reset to 0 if the counter exceeds 99
        tm.ShowNumberDec(counter) ' Display the counter value
        Log("Counter: ", counter)
    End If
End Sub
 
Last edited:
Upvote 0

Beja

Expert
Licensed User
Longtime User
Edit:
At the end of Btn_StateChanged sub, (after line 23) you can add "Delay(200)" to debounce the button and get rid of the generated noise. (tested)
This is if you are usig mechanical/manual switch button.
 
Upvote 0

emexes

Expert
Licensed User
the debounce which I am still working on.. probably I will use a .1 mF across the switch pins

If you're doing debouncing in hardware, key thing is to make sure the signal that when the signal passes from the analog domain to digital, that it is via a digital input with hysteresis, usually a schmitt trigger.

Particularly 1/ for counting and keypad applications, where doubled-up edges will result in erroneous values, and 2/ when used as an interrupt input.

0.1 millifarads seems a bit high (and battery hungry) but, hey: if it works, it works. ?
 
Upvote 0

Beja

Expert
Licensed User
Longtime User
If you're doing debouncing in hardware, key thing is to make sure the signal that when the signal passes from the analog domain to digital, that it is via a digital input with hysteresis, usually a schmitt trigger.

Particularly 1/ for counting and keypad applications, where doubled-up edges will result in erroneous values, and 2/ when used as an interrupt input.

0.1 millifarads seems a bit high (and battery hungry) but, hey: if it works, it works. ?

I thought a schmitt trigger will square up the hysteresis instead of removing them.
 
Upvote 0

emexes

Expert
Licensed User
I thought a schmitt trigger will square up the hysteresis instead of removing them.

It will square up the bouncy pulses, but not remove the bounces. Hysteresis is the means by which analog signals (continuous) are converted to digital signals (discrete).

When the input is below a different (lower) chosen threshold the output is low, and when the input is between the two levels the output retains its value. This dual threshold action is called hysteresis and implies that the Schmitt trigger possesses memory and can act as a bistable multivibrator (latch or flip-flop).
https://en.wikipedia.org/wiki/Schmitt_trigger

Digital inputs generally don't like inputs that dawdle within or through the transition zone between the low and high thresholds. The worst cases include lockup. More often, there can be oscillation. But you might be lucky: perhaps the digital input on the microcontroller that you're using, already handles the analog-to-digital transition for you, no added Schmitt conditioning required. ?

But if you find yourself testing counting on a batch of (say) 100 parts, but counting more than that, and no capacitor value is curing the problem, then I'm just giving a head's up as to what the problem might then be.
 
Last edited:
Upvote 0

Beja

Expert
Licensed User
Longtime User
The best bet is a combination of schmitt trigger and debouncing. This way you can get rid of the noise and also condition the signal to look better to the TM1637.
 
Upvote 0
Top