Use Arrow Keys to Navigate Continuous Form Records

A nice feature to add to any continuous form is the ability to navigate up and down between the records by simply using the keyboard arrow keys. Luckily for us, we have a couple options available to us to make that happen and enhance our user experience.
 

Changing The Client Settings

As pointed out in the comments below, by Jack Perry, as of Access 2019 we now have the ability to add such functionality to a database by changing a database client setting.

File -> Options -> Client Settings
Under the Editing section (at the top), look for the setting entitled Continuous Form Record Navigation Keys and set it to either Up/Down or Left/Right to suit your personal preference.

Remember, this change needs to be made on each user’s PC and as noted previously is only available in newer versions of Microsoft Access. Although I haven’t tried it yet, since this is a database property you should be able to enable it via some simple automation.

I tried locating information on this setting from the official documentation:

sadly, it does not appear! I reported the issue, but have no clue if the Access Dev Team will do any updates to include it.
 

The Coding Approach

Now, simple Google search and we can find the code to add to a form, but I wanted something a little cleaner, a reusable function that I could simply call.  And so taking the typically suggested code, I tweaked it into the following:

'---------------------------------------------------------------------------------------
' Procedure : EnableArrowsScroll
' Author    : Daniel Pineault, CARDA Consultants Inc.
' Website   : http://www.cardaconsultants.com
' Purpose   : Enable using the up and down arrows to move between records on a
'             continuous form
' Req'd Refs: None
' The Form's Key Preview property must be set to True for this code to work.
'
' Input Variables:
' ~~~~~~~~~~~~~~~~
' iKeyCode  : Keycode from the source form from the KeyDown event
' frm       : form object to apply the new behavior to
'
' Usage:
' ~~~~~~
' KeyCode = EnableArrowsScroll(KeyCode, Me) 'This is placed in the KeyDown event
'                            'Dont forget to set the Key Preview property to Yes
'
' Revision History:
' Rev       Date(yyyy/mm/dd)        Description
' **************************************************************************************
' 1         2011-07-07              Initial Release
' 2         2017-04-08              Added DefaultView check
'---------------------------------------------------------------------------------------
Public Function EnableArrowsScroll(ByVal iKeyCode As Integer, frm As Access.Form) As Integer
    On Error GoTo Error_Handler

    If frm.DefaultView = 1 Then    'Only process for Continuous forms
        Select Case iKeyCode
            Case vbKeyDown
                '            If CurrentRecord <> RecordsetClone.RecordCount Then 'Restrict to existing records
                If frm.NewRecord = False Then    'Allow going to new record for data entry
                    DoCmd.GoToRecord , , acNext
                End If
                EnableArrowsScroll = 0
            Case vbKeyUp
                If frm.CurrentRecord <> 1 Then
                    DoCmd.GoToRecord , , acPrevious
                End If
                EnableArrowsScroll = 0
            Case Else
                EnableArrowsScroll = iKeyCode
        End Select
    Else
        EnableArrowsScroll = iKeyCode
    End If

Error_Handler_Exit:
    On Error Resume Next
    If Not frm Is Nothing Then Set frm = Nothing
    Exit Function

Error_Handler:
    If Err.Number <> 2105 Then
        MsgBox "The following error has occurred" & vbCrLf & vbCrLf & _
               "Error Number: " & Err.Number & vbCrLf & _
               "Error Source: EnableArrowsScroll" & vbCrLf & _
               "Error Description: " & Err.Description & _
               Switch(Erl = 0, "", Erl <> 0, vbCrLf & "Line No: " & Erl) _
               , vbOKOnly + vbCritical, "An Error has Occurred!"
    End If
    Resume Error_Handler_Exit
End Function

Then we can call the above with a single line of code in any Form’s On Key Down event, like:

Private Sub Form_KeyDown(KeyCode As Integer, Shift As Integer)
    On Error GoTo Error_Handler

    KeyCode = EnableArrowsScroll(KeyCode, Me)

Error_Handler_Exit:
    On Error Resume Next
    Exit Sub

Error_Handler:
    MsgBox "The following error has occurred" & vbCrLf & vbCrLf & _
           "Error Number: " & Err.Number & vbCrLf & _
           "Error Source: Form_KeyDown" & vbCrLf & _
           "Error Description: " & Err.Description & _
           Switch(Erl = 0, "", Erl <> 0, vbCrLf & "Line No: " & Erl) _
           , vbOKOnly + vbCritical, "An Error has Occurred!"
    Resume Error_Handler_Exit
End Sub

The last thing to remember to note, is for the above code to work properly, you must set the form’s Key Preview property to Yes.

9 responses on “Use Arrow Keys to Navigate Continuous Form Records

  1. Andy Rice

    Daniel:

    Merci pour ton exemple. Je l’ai essayé. C’est bon, mais je ai du changé les “Docmd.GoToRecord … ” á des “Formreference.Recordset …”. Je ne sais pas pourquoi, mais les Docmd.GoToRecord ont donné l’erreur: “You can’t go to the specified record…”, le nombre d’erreur 2105.

    Andy Rice

    ‘—————————————————————————————
    ‘ Call From : A continous form KeyDown event.
    ‘ MAKE SURE TO SET THE form’s Key Preview property to Yes.

    ‘ Purpose : Move up or down with the arrow keys.

    ‘ Parameters: A reference to the current form.
    ‘ The KeyCode in the calling form.
    ‘—————————————————————————————
    Public Function HandleContinuousFormKeyDown(ByRef frm As Form, KeyCode As Integer) As Integer
    On Error GoTo Error_Handler

    With frm

    If .ActiveControl.ControlType = acComboBox Then
    HandleContinuousFormKeyDown = KeyCode

    ElseIf .ActiveControl.ControlType = acTextBox Then
    If .ActiveControl.EnterKeyBehavior Then
    ‘ ControlSource is bound to a Long Text column.
    HandleContinuousFormKeyDown = KeyCode
    End If
    End If

    If HandleContinuousFormKeyDown = KeyCode Then
    ‘ Processed above.

    ElseIf KeyCode = vbKeyDown Then
    If .Dirty Then
    ‘ Try to save the current record. Will trigger the calling form’s BeforeUpdate.
    .Dirty = False
    End If

    ‘ A cleaner command, but errors with err.Number = 2105: “You can’t go to the specified record.”
    ‘DoCmd.GoToRecord , , acNext

    If .Recordset.EOF = False Then
    .Recordset.MoveNext
    If .Recordset.EOF _
    And .AllowAdditions Then
    .Recordset.AddNew
    End If
    End If

    HandleContinuousFormKeyDown = 0

    ElseIf KeyCode = vbKeyUp Then
    If .Dirty Then
    ‘ Try to save the current record. Will trigger the calling form’s BeforeUpdate.
    .Dirty = False
    End If

    ‘ A cleaner command, but errors with err.Number = 2105: “You can’t go to the specified record.”
    ‘DoCmd.GoToRecord , , acPrevious

    If .Recordset.BOF = False Then
    .Recordset.MovePrevious
    End If

    HandleContinuousFormKeyDown = 0

    Else
    ‘ Handle as a regular key.
    HandleContinuousFormKeyDown = KeyCode

    End If

    End With

    Exit Function

    Error_Handler:

    If Err.Number = 2001 Then
    ‘ Comes from invalid entry if frm.BeforeUpdate. Err.Description is “You canceled the previous operation.”
    Else
    ‘ Testing:
    ‘Stop
    ‘Resume
    Call MError.ErrorHandler(“HandleContinuousFormKeyDown in MForm”)
    End If
    End Function

  2. Luis Cortes

    Woow. thank you so much, it’s a great feature to add to my forms and works great.

  3. Ben Sacherich

    Adding this arrow key capability makes a big difference to keyboard users. Thanks for making this robust function.

    For 10+ years I have been using a version of this by another MVP and just today I noticed an bug. Because it has On Error Resume Next, if you press the down arrow key when a record is incomplete, no error message is shown to the user. They get stuck with no indication of a problem. I started writing handler for error #2105 but then I found your code that is even more robust.
    (original code for reference: http://msgroups.net/microsoft.public.access.formscoding/navigation-in-continuous/83347 )

  4. Ben Sacherich

    After using this I noticed that it doesn’t tell the user when they press the up/down arrow on a record that has an incomplete required field or generates a duplicate record. It just does nothing when the up/down arrow is pressed in this situation. How can this be improved to show the user the standard Access error when the user attempts to leave the record?
    I did some experimentation with Me.Dirty=False but that ends up causing more issues when the update fails.

  5. Jack Perry

    Go to File/Client Settings and scroll down right pane to “Continuous Form Record Navigation Keys”. “None” seems to be the default so select the “Up/Down” option.

    1. Daniel Pineault Post author

      Yes, in newer versions there is now that option. That said, I don’t like changing my user’s client settings and this will change the behavior on all continuous forms. So you have to make sure this is desirable. The VBA approach enables to give the functionality without changing the user’s preferences. It depends on the case and version of Access at hand.