Make Views AJAX scroll to top optional

Created on 2 April 2022, about 3 years ago
Updated 7 July 2023, almost 2 years ago

Problem/Motivation

Views uses an automatic "scroll to top" behaviour when using AJAX. While it can be useful in some situations (eg. switching to the next page of a long list) in other situations it can be annoying (eg. Views block with exposed filter in the middle of a page).

Steps to reproduce

Create Views block with exposed filter that uses AJAX and place it in the middle of a page. Use the filter. The page will scroll to the top, above the view.

Proposed resolution

Add a setting option to Views AJAX UI to disable the "scroll to top" behaviour. It should be possible to set at the display level.

Remaining tasks

โ€ฆ

User interface changes

The Views UI will have a setting option for AJAX on every display to disable the "scroll to top" behaviour.

API changes

โ€ฆ

Data model changes

โ€ฆ

Release notes snippet

โ€ฆ

โœจ Feature request
Status

Needs work

Version

10.0 โœจ

Component
Viewsย  โ†’

Last updated about 2 hours ago

Created by

๐Ÿ‡ญ๐Ÿ‡บHungary thamas Hungary

Live updates comments and jobs are added and updated live.
Sign in to follow issues

Merge Requests

Comments & Activities

Not all content is available!

It's likely this issue predates Contrib.social: some issue and comment data are missing.

  • ๐Ÿ‡บ๐Ÿ‡ธUnited States chucksimply

    #4 patch works for me on 10.1.1. This is a small but necessary option.

  • last update almost 2 years ago
    29,804 pass
  • ๐Ÿ‡ซ๐Ÿ‡ฎFinland lauriii Finland
  • ๐Ÿ‡บ๐Ÿ‡ธUnited States bduell

    This is great - thank you @skyredwang

  • Open in Jenkins โ†’ Open on Drupal.org โ†’
    Environment: PHP 8.1 & MariaDB 10.3.22
    last update over 1 year ago
    30,341 pass
  • ๐Ÿ‡ป๐Ÿ‡ณVietnam mrddthi

    That's cool, thanks @skyreddwang,
    Tested on D9.5.8 /PHP 8.1/MariaDB 10.3

  • Open in Jenkins โ†’ Open on Drupal.org โ†’
    Environment: PHP 8.1 & MariaDB 10.3.22
    last update about 1 year ago
    29,722 pass
  • ๐Ÿ‡บ๐Ÿ‡ฆUkraine bobi-mel

    Hi @skyredwang
    I applied the patch #4. Works well.
    Thanks

  • Status changed to RTBC 7 months ago
  • ๐Ÿ‡บ๐Ÿ‡ฆUkraine Znak

    I think it's reviewed and tested by community, so I think we can change status of this issue

  • Status changed to Needs work 7 months ago
  • ๐Ÿ‡ซ๐Ÿ‡ทFrance nod_ Lille

    Thanks for working on this, the patch should be moved to a Merge Request so that tests can run. Talking about tests, a test should be added per #7 to make sure we don't break that feature down the line.

    Thanks!

  • ๐Ÿ‡ฎ๐Ÿ‡ณIndia Sahana _N

    sahana _n โ†’ made their first commit to this issueโ€™s fork.

  • Pipeline finished with Success
    7 months ago
    Total: 1352s
    #290356
  • ๐Ÿ‡ฎ๐Ÿ‡ณIndia Sahana _N

    Hi

    I tried to reproduce the issue issue is replaceable in 11. x.

    And I created the MR for 11. x and tests are passed.

    RTBC++

    Please let me know if I missed anything happy to take suggestions.

  • ๐Ÿ‡บ๐Ÿ‡ธUnited States smustgrave

    Previously tagged for tests which are still needed.

    Did not review.

  • First commit to issue fork.
  • Pipeline finished with Failed
    3 months ago
    Total: 464s
    #382027
  • ๐Ÿ‡จ๐Ÿ‡ฆCanada b_sharpe

    Added unit test to prove new functionality.

    Attaching patch simply for composer.

  • Pipeline finished with Success
    3 months ago
    Total: 1997s
    #382087
  • ๐Ÿ‡บ๐Ÿ‡ธUnited States smustgrave

    So I imagine with this config change we will need a schema update for the new setting.

    Existing view config will have to probably be updated.

    Also imagine there will have to be a post_update hook to set the new key for existing views (should be batch)

  • ๐Ÿ‡ฌ๐Ÿ‡งUnited Kingdom oily Greater London
  • ๐Ÿ‡ฌ๐Ÿ‡งUnited Kingdom oily Greater London

    A unit test is in place. Test-only test fails as it should. Removing 'Needs tests' tag. If further test coverage is needed, please update.

  • ๐Ÿ‡บ๐Ÿ‡ธUnited States Chris Burge

    +1 for this addition to core. In the meantime, you can also accomplish this with an event subscriber:

    namespace Drupal\my_module\EventSubscriber;
    
    use Drupal\views\Ajax\ViewAjaxResponse;
    use Symfony\Component\EventDispatcher\EventSubscriberInterface;
    use Symfony\Component\HttpKernel\Event\ResponseEvent;
    use Symfony\Component\HttpKernel\KernelEvents;
    
    /**
     * Change the scroll-to-top behavior for the my_view view.
     */
    class AjaxResponseEventSubscriber implements EventSubscriberInterface {
    
      /**
       * {@inheritdoc}
       *
       * @return array
       *   The event names to listen for, and the methods that should be executed.
       */
      public static function getSubscribedEvents() {
        return [
          KernelEvents::RESPONSE => 'alterCommands',
        ];
      }
    
      /**
       * React to ResponseEvent.
       *
       * @param \Symfony\Component\HttpKernel\Event\ResponseEvent $event
       *   Response event.
       */
      public function alterCommands(ResponseEvent $event) {
        $response = $event->getResponse();
    
        if ($response instanceof ViewAjaxResponse
          && $response->getView()->id() === 'my_view'
          ) {
    
          $commands = &$response->getCommands();
          foreach($commands as $key => $command) {
            if ($command['command'] == 'scrollTop') {
              unset($commands[$key]);
            }
          }
          $commands = array_values($commands);
        }
      }
    
    }
    

    In my case, I wanted to modify the selector to the views' .view-content class, which is only a minor change:

          $commands = &$response->getCommands();
          foreach($commands as $key => $command) {
            if ($command['command'] == 'scrollTop') {
    -         unset($commands[$key]);
    +         $commands[$key]['selector'] = $command['selector'] . ' .view-content';
            }
          }
    -     $commands = array_values($commands);
        }
    

    It'd be worthwhile to consider allowing a site builder to set the scrollTop selector instead of adding a toggle. It would meet my use case, which is necessitated by responsive design (where the exposed filters stack atop the content on mobile).

Production build 0.71.5 2024