Scroll to top when navigate through interfaces

Certified Lead Developer

I am not sure it is a basic or i am missing a point .

We're working with a multi-interface navigation in Appian (6 interfaces navigated via buttons). When a user clicks a button to go to the next interface, the interface loads correctly, but the page does not scroll to the top.

We do not want to use a process model with chaining to reload the form. We also tried using formLayout(focusOnFirstInput: true) but that didn’t help.

How can we make the form automatically scroll to the top on each interface load using only SAIL/interface logic?

Setup :headercontent layout hosts - header, contents {two interfaces}.
interface1 have 2 columns , first column hosts navigation and other one hosts subinterfaces
interface 2 have buttons : Go Back , Save & Continue

How it works:
On the first page (interface), the user fills out the details and scrolls down to click the "Save & Continue" button. When clicked, the navigation counter increments, and the user is taken to the next page(second interface)—but the view does not scroll back to the top.

  Discussion posts and replies are publicly visible

  • 0
    Certified Lead Developer

    It is not possible to make a form automatically scroll to the top when navigating between interfaces using only interface logic. When you dynamically switch content (whether using conditional logic, choose() functions, or calling different sub-interfaces), Appian's framework intentionally preserves the current scroll position to maintain user context.

    The only way to achieve automatic scroll-to-top is by using a process model with chaining (which reloads the form) or by navigating to separate Site pages.

    AFAIK, This is a fundamental limitation of Appian's client-side framework design, not a configuration issue that can be solved through interface logic alone.

    Workaround(If possible) : Keep form sections short enough to fit on one screen, so users naturally reach navigation buttons without scrolling. Use collapsible sections for optional fields and secondary content - this reduces form height while keeping everything accessible.

  • 0
    Certified Lead Developer

    Yeah there is no way to control scroll behavior apart from making small or carcading interfaces! Also Generally when a form loads the cursor (and thereby scroll position) moves to the first editable field in the form. Does your second form has editable fields at bottom of page? 

  • 0
    Certified Lead Developer
    in reply to Stefan Helzle

    a!localVariables(
      local!activeStep: 1,
      local!text,
      local!checkbox,
      local!paragraph,
      local!steps: {"Basic Info", "Additional Info", "Review"},
      if(
        local!activeStep = 1,
        a!formLayout(
          formWidth: "MEDIUM",
          label: "Example: Onboarding Wizard",
          contents: {
            a!columnsLayout(
              columns: {
                a!columnLayout(
                  contents: {
                    a!milestoneField(
                      label: "Wizzard",
                      steps: {
                        "Step 1", 
                        "Step 2" 
                      },
                      active: local!activeStep,
                      color: "ACCENT"
                    )
                  }
                )
              },
              marginBelow: "STANDARD",
              stackWhen: {
                "PHONE" },
              showDividers: false
            ),
            a!sectionLayout(
              label: if(
                /* This logic hides the step name at the top of the form on PHONE widths 
                      since the step label is already displayed at the top when the screen is narrow */
                a!isPageWidth(pageWidths: { "PHONE" }),
                "",
                /* This uses local!activeStep as the index of local!steps to display the name of the current step */
                local!steps[local!activeStep]
              ),
              labelSize: "MEDIUM",
              labelColor: "STANDARD",
              contents: {
                a!textField(
                  label: "Text Box Label",
                  value: local!text,
                  saveInto: local!text
    
                ),
                a!textField(
                  label: "Text Box Label",
                  value: local!text,
                  saveInto: local!text
    
                ),
                a!textField(
                  label: "Text Box Label",
                  value: local!text,
                  saveInto: local!text
    
                ),
                a!textField(
                  label: "Text Box Label",
                  value: local!text,
                  saveInto: local!text
    
                ),
                a!paragraphField(value:local!paragraph,height: "TALL"),
                a!paragraphField(value:local!paragraph,height: "TALL"),
                a!paragraphField(value:local!paragraph,height: "TALL"),
                a!paragraphField(value:local!paragraph,height: "TALL")
              },
              marginAbove: "STANDARD"
            )
          },
          buttons: a!buttonLayout(
            primaryButtons: {
              a!buttonWidget(
                label: "Next",
                value: local!activeStep + 1,
                saveInto: local!activeStep,
                style: "SOLID",
                showWhen: or(local!activeStep = { 1, 2 }),
                validate: true
              ),
              a!buttonWidget(
                label: "Onboard Employee",
                submit: true,
                style: "SOLID",
                showWhen: local!activeStep = 3
              )
            },
            secondaryButtons: {
              a!buttonWidget(
                label: "Back",
                value: local!activeStep - 1,
                saveInto: local!activeStep,
                showWhen: or(local!activeStep = { 2, 3 })
              )
            }
          )
        ),
        if(
          local!activeStep = 2,
          a!formLayout(
            formWidth: "MEDIUM",
            label: "Example: Onboarding Wizard",
            contents: {
              a!columnsLayout(
                columns: {
                  a!columnLayout(
                    contents: {
                      a!milestoneField(
                        label: "Wizzard",
                        steps: {
                          "Step 1", 
                          "Step 2" 
                        },
                        active: local!activeStep,
                        color: "ACCENT"
                      )
                    }
                  )
                },
                marginBelow: "STANDARD",
                stackWhen: { "PHONE" }
              ),
              a!sectionLayout(
                label: if(
                  /* This logic hides the step name at the top of the form on PHONE widths 
                      since the step label is already displayed at the top when the screen is narrow */
                  a!isPageWidth(pageWidths: { "PHONE" }),
                  "",
                  /* This uses local!activeStep as the index of local!steps to display the name of the current step */
                  local!steps[local!activeStep]
                ),
                labelSize: "MEDIUM",
                labelColor: "STANDARD",
                contents: {
                  a!checkboxField(
                    label: "CheckBox Label",
                    choiceLabels: { "Yes", "No" },
                    choiceValues: { "Yes", "No" },
                    value: local!checkbox,
                    saveInto: local!checkbox
                  ),
                  a!checkboxField(
                    label: "CheckBox Label",
                    choiceLabels: { "Yes", "No" },
                    choiceValues: { "Yes", "No" },
                    value: local!checkbox,
                    saveInto: local!checkbox
                  ),
                  a!checkboxField(
                    label: "CheckBox Label",
                    choiceLabels: { "Yes", "No" },
                    choiceValues: { "Yes", "No" },
                    value: local!checkbox,
                    saveInto: local!checkbox
                  ),
                  a!checkboxField(
                    label: "CheckBox Label",
                    choiceLabels: { "Yes", "No" },
                    choiceValues: { "Yes", "No" },
                    value: local!checkbox,
                    saveInto: local!checkbox
                  ),
                  a!paragraphField(value:local!paragraph,height: "TALL"),
                  a!paragraphField(value:local!paragraph,height: "TALL"),
                  a!paragraphField(value:local!paragraph,height: "TALL"),
                  a!paragraphField(value:local!paragraph,height: "TALL"),
                },
                marginAbove: "STANDARD"
              )
            },
            buttons: a!buttonLayout(
              primaryButtons: {
                a!buttonWidget(
                  label: "Next",
                  value: local!activeStep + 1,
                  saveInto: local!activeStep,
                  style: "SOLID",
                  showWhen: or(local!activeStep = { 1, 2 }),
                  validate: true
                ),
                a!buttonWidget(
                  label: "Onboard Employee",
                  submit: true,
                  style: "SOLID",
                  showWhen: local!activeStep = 3
                )
              },
              secondaryButtons: {
                a!buttonWidget(
                  label: "Back",
                  value: local!activeStep - 1,
                  saveInto: local!activeStep,
                  showWhen: or(local!activeStep = { 2, 3 })
                )
              }
            )
          ),
          {}
        )
      )
    )
    
    Thank you Stefan,

    Insightful as always . Not sure why but it does not works (means not scroll to top) when you have more components (i may be doing something wrong) . PFA code.

  • 0
    Certified Lead Developer
    in reply to gauravp013908

    I'm interested to see if automatic vertical scrolling to the top happens.
    Keep me posted

  • 0
    Certified Lead Developer
    in reply to gauravp013908

    What Appian version is this? I did not test it with the all new formLayout.

    In our review app, I use a paneLayout. Each section is a separate pane. Below some screenshots of the scrolling behaviour:

    Scrolling down

    Going to next section with scroll position on top

  • 0
    Certified Lead Developer
    in reply to Stefan Helzle

    Thank you for replying, We are on 25.2 .