Menu

Not confident with Interrupt.

Help
mkstevo
2019-01-03
2019-01-10
  • mkstevo

    mkstevo - 2019-01-03

    I have always steered away from using interrupts, as I was never confident I knew what I was doing and found myself confused whenever I tried to read how to use them. As things are not too busy this week, I thought I'd have a look at trying to make sense of them. I am also experimenting with Chris Roper's millis() function. That section works very well, and I'm grateful to Chris for his excellent work and generousity in sharing it. I'm rather less confident in my work on the Interrupt, although it does seem to 'work'...

    Here's my code:

    '#Chip 16F874, 20 'This selects Crystal Oscillator of 20MHz
    #Option explicit
    #Config OSC = RC 'This selects RC Oscillator
    #Chip 16F874, 4  '2k7 and 30pf on pin 13 just over 4MHz
    
    #include "millis.h"       ' Include the Millis() Library
    
    'Note:
    'Pin 1 MUST connect to +5V to prevent being held in reset.
    
    #Define     LED_Pin         PortA.0 'Pin2
    #Define     LED_Pin2        PortA.1 'Pin3
    #Define     LEDRate         1000    'Flash rate in mS
    #Define     Int_Pin         PortB.4 'Pin37
    
    
    'This includes an example of the use of the 'Millis() library
    'millis() returns the number of milliseconds elapsed since the
    'processor was powered up. It returns a Long variable value
    'that will return to zero after 49 days of running. If checking
    'for values being greater than millis() in programs intended to
    'run for long periods, remember to watch for it resetting to zero.
    
    Dim         CurMs           As Word
    Dim         LstMs           As Word
    Dim         Int_En          As Byte
    
    Dir         LED_Pin         Out
    Dir         LED_Pin2        Out
    
    Dir         Int_Pin         In
    
    '**********************************************************************
    'Interrupt setup
    '**********************************************************************
    Let Int_En = INTCON       'Get Interrupt status
    
    'INTCON.0        Change on PortB happened
    'INTCON.1        External Interrupt on PortB
    'INTCON.2        Timer0
    'INTCON.3        PortB Change Enable
    'INTCON.4        External Interrupt PortB Enable
    'INTCON.5        Timer0 Enable
    'INTCON.6        Peripheral Interrupt Enable
    'INTCON.7        Global Interrupt Enable
    
    Let Int_En.3 = 1 'Enable IOC for PortB
    Let Int_En.0 = 0 'Clear any Interrupts
    
    Let INTCON = Int_En       'Set Interrupt status
    
    On Interrupt PortBChange Call Interrupt_Sub
    '**********************************************************************
    'Interrupt setup
    '**********************************************************************
    
    Let CurMs = 0
    Let LstMs = 0
    
    Do
    
        CurMs = millis()
        If CurMs - LstMs >= LEDRate Then    'Required Time has Elapsed
            Let LED_Pin = !LED_Pin          'So Toggle state of LED
            Let LstMs = CurMs               'And Record Toggle Time
        End If
    
        'This section tests to see if the IOC interrupts have been disabled.
        'They are turned off once we've responded to the button press.
        'We only want to re-enable them once the button has been released to
        'prevent multiple presses being recorded when only one has ocurred.
    
        If Int_En.3 = 0 Then                'IOC Interrupts are disabled
            Reset_Interrupt_Sub
        End If
    
    Loop
    
    Sub Interrupt_Sub
        Let Int_En    = INTCON              'Get Interrupt status
        If Int_En.0 = 1 Then
            If Int_Pin = 1 Then             'Button pressed
                Wait 10 mS
                If Int_Pin = 1 Then         'Still pressed
                    Let LED_Pin2 = !LED_Pin2
                    Let Int_En.0 = 0        'Reset the Interrupt On Change
                    Let Int_En.3 = 0        'Stop the Interrupt On Change Service
                End If
            End If
        End If
        Let INTCON = Int_En
    End Sub
    
    Sub Reset_Interrupt_Sub
        If Int_Pin = 0 Then                 'Button released
            Wait 10 mS
            If Int_Pin = 0 Then             'Still released
                Let Int_En    = INTCON      'Get Interrupt status
                Let Int_En.3  = 1           'Enable IOC for PortB
                Let Int_En.0  = 0           'Clear any Interrupts
                Let INTCON    = Int_En      'Set Interrupt status
            End If
        End If
    End Sub
    

    As I said, this does work. If I press my button, I can toggle the state of the LED on Pin3 (PortA.1) whilst the LED on Pin2 (PortA.0) flashes under control of Chris's millis() function. If the button is held in, it is ignored until it has been released, and then presssed again. Super.

    My lack of confidence is that the setup and implementation of the interrupt all seems a little 'messy'. I keep thinking that there should be a simpler way of doing this than the one I'm using.

    I tried using one of the examples from the help pages that used this:

        'Setup the Interrupt
            Set IOCA.3 on
            Dir porta.3 in
            On Interrupt PORTABCHANGE Call Setir
    

    I changed it to:

        'Setup the Interrupt
            Set IOCB.4 on
            Dir PortB.4 in
            On Interrupt PORTBCHANGE Call Interrupt_Sub
    

    But this fails to compile, giving the error message "Error: Variable IOCB was not explicitly declared".

    I just wondered if my approach could be improved?

     
  • mkstevo

    mkstevo - 2019-01-04

    I have managed to cobble something similar for the 16F1825, but again, it all seems rather untidy. The 16F1825 and 1829 seem to only have one external interrupt available (or I really misunderstood the datasheet) INTE, interrupt on edge. This requires two registers to be set, INTCON (bit 4) and the OPTION_REG (bit 6) which if set to 1 interrupts on a rising edge, if set to 0 interrupts on a falling edge. All of this assumes I did interpret the datasheet correctly, although it does seem to be working...

    Any help would be most useful.

    #Option explicit
    #Chip 16F1825, 32
    
    #Define OutPin     PortC.5 'Pin  5
    #Define Int_Pin    PortA.2 'Pin  11
    
    Dim     Int_En     As Byte
    
    'Set pin directions
    Dir OutPin          Out    'Pin  5
    
    
    '**********************************************************************
    'Interrupt setup
    '**********************************************************************
    Let Int_En = OPTION_REG   'Get Option status
    Let Int_En.6 = 1 'Interrupt on rising edge
    Let OPTION_REG = Int_En
    
    Let Int_En = INTCON       'Get Interrupt status
    
    'INTCON.0        Change on PortA happened
    'INTCON.1        External Interrupt on PortA
    'INTCON.2        Timer0
    'INTCON.3        PortA Change Enable
    'INTCON.4        External Interrupt PortA Enable
    'INTCON.5        Timer0 Enable
    'INTCON.6        Peripheral Interrupt Enable
    'INTCON.7        Global Interrupt Enable
    
    Let Int_En.4 = 1 'Enable INTE for PortA - Only Pin = Pin 11
    Let Int_En.1 = 0 'Clear any Interrupts
    
    Let INTCON = Int_En       'Set Interrupt status
    
    
    On Interrupt ExtInt0 Call Interrupt_Sub
    '**********************************************************************
    'Interrupt setup
    '**********************************************************************
    
    Do
    
        'Do useful stuff here
    
    
        'This section tests to see if the INTE interrupts have been disabled.
        'They are turned off once we've responded to the button press.
        'We only want to re-enable them once the button has been released to
        'prevent multiple presses being recorded when only one has ocurred.
    
    
        If Int_En.4 = 0 Then                'INTE Interrupts are disabled
            Reset_Interrupt_Sub
        End If
    Loop
    
    Sub Interrupt_Sub
    
        Let Int_En    = INTCON              'Get Interrupt status
    
        If Int_En.1 = 1 Then
            If Int_Pin = 1 Then             'Button pressed
                Wait 10 mS
                If Int_Pin = 1 Then         'Still pressed
                    Let OutPin = !OutPin
                    Let Int_En.1 = 0        'Reset the Interrupt On Edge
                    Let Int_En.4 = 0        'Stop the Interrupt On Edge Service
                End If
            End If
        End If
        Let INTCON = Int_En
    
    End Sub
    
    Sub Reset_Interrupt_Sub
        If Int_Pin = 0 Then                 'Button released
            Wait 10 mS
            If Int_Pin = 0 Then             'Still released
                Let Int_En    = INTCON      'Get Interrupt status
                Let Int_En.1 = 0            'Reset the Interrupt On Edge
                Let Int_En.4 = 1            'Start the Interrupt On Edge Service
                Let INTCON    = Int_En      'Set Interrupt status
            End If
        End If
    End Sub
    

    Thanks for looking.

     
  • Anobium

    Anobium - 2019-01-04

    I think a little simplification of the code may help.

    Can I just check? What exactly is the result you need?

     
  • mkstevo

    mkstevo - 2019-01-04

    What I'm initially aiming for is to familiarise myself with using interrupts triggered by an external source such as a switch.

    At the moment everything I've designed and written the software for, continually polls the input(s) if a 'pulse' arrives, counts it once only, by waiting for the pulse to return to it's rest state then returns to updating the display, polling the input(s), sending serial data out if required and so on.

    I was thinking that my software might be more elegant if I could use interrupts to monitor the input(s) which would count each pulse once only, whilst remaining vigilant for further potential pulses instead of hoping that any time taken updating the displays and whatever else didn't exceed the few mS of any pulse widths that might arrive at any time.

    So something that allows me to catch a pulse width of between 10 mS - 500 mS without hogging the entire processor for the duration of that pulse, count each pulse once only and then be ready for another pulse almost immediately after the preceeding pulse finishes.

    Which the above code does manage, if not very elegantly.

     
  • Anobium

    Anobium - 2019-01-04

    The code is a lot easier. Look at the demos: C:\GCB@Syn\GreatCowBasic\Demos\vendor_boards\microchip_low_pin_count_demo_board\pickit2_board\16f1825\13_eeprom.gcb

    This demo has a switch on a.3. Same chip also.

     
  • mkstevo

    mkstevo - 2019-01-04

    Thanks, I'll check that out next week.

    I looked at the 'Help' but found it rather confusing. I never thought of looking at the examples after not finding much in the 'Help'.

    I appreciate your reply and will report back once I've had another look.

     
  • mkstevo

    mkstevo - 2019-01-09

    Inspired by the example from the demos folder pointed out by Anobium, I have adjusted my program for the 16F1825. I couldn't get the Interrupt on Change example from the demos folder to work well for me. This seemed to fire the interrupt when the 'millis' function changed the LED state, and sometimes when the timer overflowed within the 'millis' function too. Whilst the interrupt still worked, the button needed to be pressed very firmly, and for at least 500mS. As I was hoping to capture short(ish) pulses in my final version this was a retrograde step.

    I then looked at the example and wondered where the definitions for the interrupt constants were listed. I opened up the 16F1825.dat file and lo and behold, there they were.

    Taking the defined constants as opposed to reading the entire contents of the INTCON register and the OPTION_REG regiter, setting the relevant bits and then writing them back to the PIC has tidied up the code by some measure. I also took the time to swap the interrupt from a rising to a falling edge to detect button presses and releases to ensure each button press is registered only once.

    The changes have sped the detection of the button press then release quite significantly, keeping the button pressed and then held does not slow the operation of the program down either.

    Whilst I'm not confident in using interrupts, I'm vastly less reluctant to use them now!

     
  • mkstevo

    mkstevo - 2019-01-09

    Here is the new and improved version:

    'Uses 16F1825 and Millis_Zero
    
    #Chip 16F1825, 32
    #Option explicit
    #Config CP=On
    
    #Include "millis_zero.h"
    
    'This includes an example of the use of the Millis() library
    'millis() returns the number of milliseconds elapsed since the
    'processor was powered up. It returns a Long variable value
    'that will return to zero after 49 days of running. If checking
    'for values being greater than millis() in programs intended to
    'run for long periods, remember to watch for it resetting to zero.
    
    'The version millis_zero.h starts from zero
    'each time the processor is powered on.
    
    #Define OutPin     PortC.5 'Pin  5
    #Define Button     PortA.2 'Pin  11
    #Define Beeper     PortC.3 'Pin  7
    
    #Define LEDRate    1000 'mS
    
    
    Dim         Count           As Byte
    Dim         Pressed         As Bit
    
    Dim         CurMs           As Word
    Dim         LstMs           As Word
    
    Dim         Cur_Millis      As Long
    Dim         Int_Millis      As Long
    Dim         Rel_Millis      As Long
    Dim         Milli_Del       As Word
    
    Dim         Reset_Trigger   As Bit
    Dim         Trigger         As Bit
    
    
    'Set pin directions
    Dir OutPin      Out         'Pin  5
    Dir Beeper      Out         'Pin  7
    Dir Button      In          'Pin  11
    
    
    Let CurMs         = 0
    Let LstMs         = 0
    Let Reset_Trigger = 0
    Let Trigger       = 0
    Let Count         = 0
    
    Initialise
    Test_Millis
    
    Sub Test_Millis
    
    
        Do
    
            If Trigger = 1 Then
                Let Trigger = 0
                DoBip(1,25)  'Sound the buzzer
            End If
    
            If Reset_Trigger = 1 Then
                Let Reset_Trigger = 0
                DoBip(1,25)  'Sound the buzzer
            End If
    
            CurMs = millis()
            If CurMs - LstMs >= LEDRate Then    'Required Time has Elapsed
                Let OutPin = !OutPin            'So Toggle state of LED
                Let LstMs = CurMs               'And Record Toggle Time
            End If
    
        Loop
    
    End Sub
    
    Sub Initialise
    
        Do
            If Button = Pressed Then
                Let Pressed = !Button
                Let Count = 0
            End If
            Wait 5 mS
            Count++
        Loop Until Count > 125 'Get the idle state of the pin
    
        '**********************************************************************
        'Interrupt setup
        '**********************************************************************
    
        'Interrupt flags
    
        'PS0,OPTION_REG,0
        'PS1,OPTION_REG,1
        'PS2,OPTION_REG,2
        'PSA,OPTION_REG,3
        'TMR0SE,OPTION_REG,4
        'T0SE,OPTION_REG,4 'Alias?
        'TMR0CS,OPTION_REG,5
        'T0CS,OPTION_REG,5 'Alias?
        'INTEDG,OPTION_REG,6
        'NOT_WPUEN,OPTION_REG,7
    
        'Option_Reg for rising/falling edge
        'INTEDG
        '
        'INTEDG = 1 'Rising Edge
        'INTEDG = 0 'Falling Edge
    
        Let INTEDG = Pressed      'Interrupt on switch pressed state
    
        'ExtInt0:INTE,INTF
    
        'IOCIF,INTCON,0
        'INTF,INTCON,1
        'TMR0IF,INTCON,2
        'IOCIE,INTCON,3
        'INTE,INTCON,4
        'TMR0IE,INTCON,5
        'PEIE,INTCON,6
        'GIE,INTCON,7
        'T0IF,INTCON,2
        'T0IE,INTCON,5
    
        'INTE = 1 'Interrupt on Edge enabled
        'INTE = 0 'Interrupt on Edge disabled
    
        'INTF = 1 'Edge Interrupt happened
        'INTF = 0 'No Edge Interrupt
    
        Let INTE   = 1 'Interrupt on Edge enabled
        Let INTF   = 0 'Clear any interrupts
    
        On Interrupt ExtInt0 Call Interrupt_Sub
        '**********************************************************************
        'Interrupt setup
        '**********************************************************************
    
    End Sub
    
    
    Sub Interrupt_Sub
    
        If INTF = 1 Then
            If Button = Pressed Then             'Button pressed
                Wait 10 mS
                If Button = Pressed Then         'Still pressed
                    Let Trigger  = 1
                    Let INTEDG = !Pressed        'Change to interrupt on release
                End If
            End If
            If Button <> Pressed Then            'Button released
                Wait 10 mS
                If Button <> Pressed Then        'Still released
                    Let Reset_Trigger = 1
                    Let INTEDG = Pressed         'Change back to interrupt on press
                End If
            End If
        Let INTF   = 0 'Clear interrupt
        End If
    
    End Sub
    
    Sub DoBip(In NumberOfBips As Byte, LengthOfBips As Word)
        For Count = 1 To NumberOfBips
            SoundBeep(1) 'Beep on
            Wait LengthOfBips mS
            SoundBeep(0) 'Beep off
            Wait LengthOfBips mS
        Next
    End Sub
    
    Sub SoundBeep(In Sound As Bit)
        Let Beeper = Sound
        'Turn on or off the beeper
    End Sub
    
     
  • Anobium

    Anobium - 2019-01-09

    I removed all the code that was not needed show below.

    A few points.
    1. Not sure what millis_one.h is but I may be out of the loop with version of millis.h posted.
    2. Let INTF = 0 'Clear interrupt. This may be needed initially but the interrupt service handler built in with Great Cow BASIC will clear INF for you. Try removing from your interrupt handler to verify the clear is happening (I can see it in the ASM but do check yourselve).

    Looks very good! A demo in the making!!

    'Basic
    'Uses 16F1825 and Millis_Zero
    
    #Chip 16F1825, 32
    #Option explicit
    #Config CP=On
    
    #Include <millis.h>
    
    'This includes an example of the use of the Millis() library
    'millis() returns the number of milliseconds elapsed since the
    'processor was powered up. It returns a Long variable value
    'that will return to zero after 49 days of running. If checking
    'for values being greater than millis() in programs intended to
    'run for long periods, remember to watch for it resetting to zero.
    
    'The version millis_zero.h starts from zero
    'each time the processor is powered on.
    
    #Define OutPin     PortC.5 'Pin  5
    #Define Button     PortA.2 'Pin  11
    #Define Beeper     PortC.3 'Pin  7
    
    #Define LEDRate    1000 'mS
    
    
    Dim         Count           As Byte
    Dim         Pressed         As Bit
    
    Dim         CurMs           As Word
    Dim         LstMs           As Word
    
    Dim         Cur_Millis      As Long
    Dim         Int_Millis      As Long
    Dim         Rel_Millis      As Long
    Dim         Milli_Del       As Word
    
    Dim         Reset_Trigger   As Bit
    Dim         Trigger         As Bit
    
    
    'Set pin directions
    Dir OutPin      Out         'Pin  5
    Dir Beeper      Out         'Pin  7
    Dir Button      In          'Pin  11
    
    
    Let CurMs         = 0
    Let LstMs         = 0
    Let Reset_Trigger = 0
    Let Trigger       = 0
    Let Count         = 0
    
    Initialise
    Test_Millis
    
    Sub Test_Millis
    
    
        Do
    
            If Trigger = 1 Then
                Let Trigger = 0
                DoBip(1,25)  'Sound the buzzer
            End If
    
            If Reset_Trigger = 1 Then
                Let Reset_Trigger = 0
                DoBip(1,25)  'Sound the buzzer
            End If
    
            CurMs = millis()
            If CurMs - LstMs >= LEDRate Then    'Required Time has Elapsed
                Let OutPin = !OutPin            'So Toggle state of LED
                Let LstMs = CurMs               'And Record Toggle Time
            End If
    
        Loop
    
    End Sub
    
    Sub Initialise
    
        Do
            If Button = Pressed Then
                Let Pressed = !Button
                Let Count = 0
            End If
            Wait 5 mS
            Count++
        Loop Until Count > 125 'Get the idle state of the pin
    
        Let INTEDG = Pressed      'Interrupt on switch pressed state
        Let INTE   = 1 'Interrupt on Edge enabled
        Let INTF   = 0 'Clear any interrupts
    
        On Interrupt ExtInt0 Call Interrupt_Sub
        '**********************************************************************
        'Interrupt setup
        '**********************************************************************
    
    End Sub
    
    
    Sub Interrupt_Sub
    
        If INTF = 1 Then
            If Button = Pressed Then             'Button pressed
                Wait 10 mS
                If Button = Pressed Then         'Still pressed
                    Let Trigger  = 1
                    Let INTEDG = !Pressed        'Change to interrupt on release
                End If
            End If
            If Button <> Pressed Then            'Button released
                Wait 10 mS
                If Button <> Pressed Then        'Still released
                    Let Reset_Trigger = 1
                    Let INTEDG = Pressed         'Change back to interrupt on press
                End If
            End If
        Let INTF   = 0 'Clear interrupt
        End If
    
    End Sub
    
    Sub DoBip(In NumberOfBips As Byte, LengthOfBips As Word)
        For Count = 1 To NumberOfBips
            SoundBeep(1) 'Beep on
            Wait LengthOfBips mS
            SoundBeep(0) 'Beep off
            Wait LengthOfBips mS
        Next
    End Sub
    
    Sub SoundBeep(In Sound As Bit)
        Let Beeper = Sound
        'Turn on or off the beeper
    End Sub
    
     
  • mkstevo

    mkstevo - 2019-01-10

    Thanks for your suggestions.

    I have removed the "Let INTF = 0 'Clear interrupt" statement as suggested. I hadn't realised the interrupt was cleared by GCB automatically. Is that cleared when exiting the interrupt handling sub routine?

    I have also removed the references to 'Millis_Zero.h' and have re-incorporated the original 'millis.h'. I had been experimenting with setting the value returned by the millis() funtion to zero when the processor is first started. 'Millis_Zero.h' was a modified version of the original. I have moved the command that resets milis() to zero into my code, leaving the original unmodified.

     
    • Anobium

      Anobium - 2019-01-10

      Yes, the Great Cow BASIC does clear the interrupt flags it handles. So, if INTE is enabled via the On Interrupt then the related INTF is cleared upon exit.

      Good to read about the tidy up - when you are good and ready it would be very good to publish as a demonstration.

      :-)

       
  • mkstevo

    mkstevo - 2019-01-10
    '**************************************************************************
    'Enhanced 16F1825 version
    
    'Uses 16F1825, millis and interrupts for a button.
    
    'The interrupt triggers on a rising then falling edge to enable 
    'counting of buttons only when a button is pressed and released.
    
    'The button state is stored at startup to allow for buttons that
    'may idle high or low automatically.
    
    #Chip 16F1825, 32
    #Option explicit
    #Config CP=On
    
    #Include "millis.h"
    
    'This includes an example of the use of the 'Millis() library
    'millis() returns the number of milliseconds elapsed since the
    'processor was powered up. It returns a Long variable value
    'that will return to zero after 49 days of running. If checking
    'for values being greater than millis() in programs intended to
    'run for long periods, remember to watch for it resetting to zero.
    
    #Define OutPin     PortC.5 'Pin  5
    #Define Button     PortA.2 'Pin  11
    #Define Beeper     PortC.3 'Pin  7  'This connects directly to the positive connection
                                        'of  12V Piezo buzzer. The fact that a 12V buzzer
                                        'is driven from a 5V pin does not matter.
                                        'It is loud enough to hear!
    
    #Define LEDRate    1000 'mS
    
    
    Dim         Count           As Byte
    Dim         Pressed         As Bit
    
    Dim         CurMs           As Word
    Dim         LstMs           As Word
    
    Dim         Reset_Trigger   As Bit
    Dim         Trigger         As Bit
    
    
    'Set pin directions
    Dir OutPin      Out         'Pin  5
    Dir Beeper      Out         'Pin  7
    Dir Button      In          'Pin  11
    
    
    Let CurMs         = 0
    Let LstMs         = 0
    Let Reset_Trigger = 0
    Let Trigger       = 0
    Let Count         = 0
    
    Initialise
    Test_Millis
    
    Sub Test_Millis
    
        Do
    
            If Trigger = 1 Then
                Let Trigger = 0
                DoBip(1,25)
            End If
    
            If Reset_Trigger = 1 Then
                Let Reset_Trigger = 0
                DoBip(1,25)
            End If
    
            CurMs = millis()
            If CurMs - LstMs >= LEDRate Then    'Required Time has Elapsed
                Let OutPin = !OutPin            'So Toggle state of LED
                Let LstMs = CurMs               'And Record Toggle Time
            End If
    
        Loop
    
    End Sub
    
    Sub Initialise
    
        Let MsCtr_ = 4294967295 'Set the value returned by the millis() function to it's
                                'maximum value. This effectively resets millis() to zero.
                                'If 'millis.h' cannot be found, this raises an error that
                                'a byte value cannot be set to 4294967295, that is why
                                'MsCtr_ is not set to 0 (zero) here.
    
        Do
            If Button = Pressed Then
                Let Pressed = !Button
                Let Count = 0
            End If
            Wait 5 mS
            Count++
        Loop Until Count > 125 'Get the idle state of the button pin
    
        '**********************************************************************
        'Interrupt setup
        '**********************************************************************
    
        'Option_Reg for rising/falling edge
        'INTEDG
    
        'INTEDG = 1 'Rising Edge
        'INTEDG = 0 'Falling Edge
    
        Let INTEDG = Pressed      'Interrupt on switch pressed state
    
        'INTE = 1 'Interrupt on Edge enabled
        'INTE = 0 'Interrupt on Edge disabled
    
        'INTF = 1 'Edge Interrupt happened
        'INTF = 0 'No Edge Interrupt
    
        'INTE = 1 'Interrupt on Edge enabled
        'INTE = 0 'Interrupt on Edge disabled
    
        Let INTE   = 1 'Interrupt on Edge enabled
        Let INTF   = 0 'Clear any interrupts
    
        On Interrupt ExtInt0 Call Interrupt_Sub
        '**********************************************************************
        'Interrupt setup
        '**********************************************************************
    
    End Sub
    
    Sub Interrupt_Sub
    
        If INTF = 1 Then
            If Button = Pressed Then             'Button pressed
                Wait 10 mS
                If Button = Pressed Then         'Still pressed
                    Let Trigger  = 1
                    Let INTEDG = !Pressed         'Set the interrupt to trigger on release
                End If
            End If
            If Button <> Pressed Then             'Button released
                Wait 10 mS
                If Button <> Pressed Then         'Still released
                    Let Reset_Trigger = 1
                    Let INTEDG = Pressed            'Set the interrupt back to trigger on press
                End If
            End If
        End If
    
    End Sub
    
    Sub DoBip(In NumberOfBips As Byte, LengthOfBips As Word)
        For Count = 1 To NumberOfBips
            SoundBeep(1) 'Beep on
            Wait LengthOfBips mS
            SoundBeep(0) 'Beep off
            Wait LengthOfBips mS
        Next
    End Sub
    
    Sub SoundBeep(In Sound As Bit)
        Let Beeper = Sound
        'Turn on or off the beeper
    End Sub
    
     

    Last edit: mkstevo 2019-01-12

Log in to post a comment.

Want the latest updates on software, tech news, and AI?
Get latest updates about software, tech news, and AI from SourceForge directly in your inbox once a month.