web-dev-qa-db-fra.com

jQuery faites défiler jusqu'à l'ID d'une autre page

J'essayais d'utiliser le défilement de page de jQuery à l'intérieur de certaines pages et pouvais réussir à faire défiler une page en douceur. Le seul problème que j'ai maintenant est lorsque j'essaie de le faire depuis une autre page. Ce que je veux dire par là est que si je clique sur un lien dans une page, il devrait charger la nouvelle page, puis faire défiler jusqu'à l'élément div spécifique.

Voici le code que j'avais l'habitude de faire défiler à l'intérieur de la page:

var jump=function(e)
{
       //prevent the "normal" behaviour which would be a "hard" jump
       e.preventDefault();
   //Get the target
   var target = $(this).attr("href");
   //perform animated scrolling
   $('html,body').animate(
   {
           //get top-position of target-element and set it as scroll target
           scrollTop: $(target).offset().top
   //scrolldelay: 2 seconds
   },2000,function()
   {
           //attach the hash (#jumptarget) to the pageurl
           location.hash = target;
   });

}

$(document).ready(function()
{
       $('a[href*=#]').bind("click", jump);
       return false;
});

J'espère que l'idée est claire.

Merci 

Très important Remarque : Ce code que j'ai posté ci-dessus fonctionne très bien dans la même page, mais ce que je veux, c'est cliquer sur un lien d'une page pour aller à une autre et faire défiler jusqu'à la cible. J'espère que c'est clair maintenant. Merci 

46
Digital site

Vous devez essentiellement faire ceci:

  • inclure le hachage cible dans le lien pointant vers l'autre page (href="other_page.html#section")
  • dans votre gestionnaire ready, effacez le défilement forcé normalement dicté par le hachage et, dès que possible, faites défiler la page en haut et appelez jump() - vous devrez procéder de manière asynchrone.
  • dans jump() si aucun événement n'est donné, définissez location.hash comme cible
  • de plus, cette technique peut ne pas saisir le saut dans le temps, vous ferez donc mieux de cacher le html,body tout de suite et de le montrer une fois que vous l'aurez remis à zéro

Ceci est votre code avec ce qui précède ajouté:

var jump=function(e)
{
   if (e){
       e.preventDefault();
       var target = $(this).attr("href");
   }else{
       var target = location.hash;
   }

   $('html,body').animate(
   {
       scrollTop: $(target).offset().top
   },2000,function()
   {
       location.hash = target;
   });

}

$('html, body').hide();

$(document).ready(function()
{
    $('a[href^=#]').bind("click", jump);

    if (location.hash){
        setTimeout(function(){
            $('html, body').scrollTop(0).show();
            jump();
        }, 0);
    }else{
        $('html, body').show();
    }
});

Vérifié travaillant dans Chrome/Safari, Firefox et Opera. Je ne sais pas pour IE cependant.

62
Petr Vostrel

Sur le lien, mettez un hash:

<a href="otherpage.html#elementID">Jump</a>

Et sur une autre page, vous pouvez faire:

$('html,body').animate({
  scrollTop: $(window.location.hash).offset().top
});

Sur une autre page, vous devriez avoir un élément avec id défini sur elementID où faire défiler. Bien sûr, vous pouvez changer le nom de celui-ci.

21
Sarfraz

En combinant les réponses de Petr et de Sarfraz, j'arrive à ce qui suit. 

Sur page1.html: 

<a href="page2.html#elementID">Jump</a>

Sur page2.html: 

<script type="text/javascript">
    $(document).ready(function() {
        $('html, body').hide();

        if (window.location.hash) {
            setTimeout(function() {
                $('html, body').scrollTop(0).show();
                $('html, body').animate({
                    scrollTop: $(window.location.hash).offset().top
                    }, 1000)
            }, 0);
        }
        else {
            $('html, body').show();
        }
    });
</script>
9
zanetu

Je voudrais recommander l'utilisation du plugin scrollTo 

http://demos.flesler.com/jquery/scrollTo/

Vous pouvez définir le scrollto par le sélecteur jquery css.

$('html,body').scrollTo( $(target), 800 );

J'ai eu beaucoup de chance avec la précision de ce plugin et de ses méthodes, où d'autres méthodes pour obtenir le même effet, comme l'utilisation de .offset() ou .position(), ont échoué dans mon navigateur. Ne disant pas que vous ne pouvez pas utiliser de telles méthodes, je suis sûr qu’il existe un moyen de le faire avec plusieurs navigateurs. Je viens de trouver le paramètre scrollTo pour être plus fiable. 

6
Fresheyeball

J'ai créé un plug-in réutilisable qui peut faire cela ... J'ai laissé la liaison aux événements extérieurs au plug-in lui-même car je trouve que c'est trop intrusif pour un aussi petit assistant.

jQuery(function ($) {

    /**
     * This small plugin will scrollTo a target, smoothly
     *
     * First argument = time to scroll to the target
     * Second argument = set the hash in the current url yes or no
     */
    $.fn.smoothScroll = function(t, setHash) {
        // Set time to t variable to if undefined 500 for 500ms transition
        t = t || 500;
        setHash = (typeof setHash == 'undefined') ? true : setHash;

        // Return this as a proper jQuery plugin should
        return this.each(function() {
            $('html, body').animate({
                scrollTop: $(this).offset().top
            }, t);

            // Lets set the hash to the current ID since if an event was prevented this doesn't get done
            if (this.id && setHash) {
                window.location.hash = this.id;
            }
        });
    };

});

Maintenant, nous pouvons simplement charger ceci, vérifier s'il y a un hachage et s'il est là, essayez de l'utiliser directement comme sélecteur pour jQuery. À l'époque, je ne pouvais pas facilement tester cela, mais j'ai récemment créé des outils similaires pour les sites de production. Si cela ne fonctionne pas immédiatement, faites-le-moi savoir et je vais examiner la solution que j'ai trouvée.

(le script devrait être dans une section onload)

if (window.location.hash) {
    window.scrollTo(0,0);
    $(window.location.hash).smoothScroll();
}

Ensuite, nous lions le plugin à onclick d'ancres qui ne contiennent qu'un hachage dans leur attribut href.

(le script devrait être dans une section onload)

$('a[href^="#"]').click(function(e) {
    e.preventDefault();

    $($(this).attr('href')).smoothScroll();
});

Puisque jQuery ne fait rien si le match échoue, nous avons une solution de rechange intéressante si une cible sur une page ne peut pas être trouvée.

Mettre à jour

Autre gestionnaire onclick pour faire défiler vers le haut quand il n'y a qu'un hachage:

$('a[href^="#"]').click(function(e) {
    e.preventDefault();
    var href = $(this).attr('href');

    // In this case we have only a hash, so maybe we want to scroll to the top of the page?
    if(href.length === 1) { href = 'body' }

    $(href).smoothScroll();
});

Voici aussi un simple jsfiddle qui montre le défilement dans la page, onload est un peu difficile à configurer ... 

http://jsfiddle.net/sg3s/bZnWN/

Mise à jour 2

Vous pourriez donc avoir des problèmes avec la fenêtre qui défilait déjà jusqu'à l'élément onload. Cela corrige cela: window.scrollTo(0,0);, il suffit de faire défiler la page en haut à gauche. Ajoutez-le à l'extrait de code ci-dessus.

2
sg3s
function scroll_down(){
    $.noConflict();
    jQuery(document).ready(function($) {
        $('html, body').animate({
            scrollTop : $("#bottom").offset().top
        }, 1);
    });
    return false;
}

ici "en bas" est l'identifiant de la balise div où vous voulez faire défiler. Pour changer les effets d'animation, vous pouvez changer le temps de "1" à une valeur différente 

2
user1284907

J'ai écrit quelque chose qui détecte si la page contient l'ancre sur laquelle l'utilisateur a cliqué et sinon, passe à la page normale, sinon, on fait défiler la section spécifique:

$('a[href*=\\#]').on('click',function(e) {

    var target = this.hash;
    var $target = $(target);
    console.log(targetname);
    var targetname = target.slice(1, target.length);

    if(document.getElementById(targetname) != null) {
         e.preventDefault();
    }
    $('html, body').stop().animate({
        'scrollTop': $target.offset().top-120 //or the height of your fixed navigation 

    }, 900, 'swing', function () {
        window.location.hash = target;
  });
});
0
John-Henry