Question

jQuery a actuellement .next(filter) et .nextAll(filter) mais je besoin de quelque chose qui correspond au milieu de ces -. Efficacement, un .nextWhile(filter) qui fait à plusieurs reprises suivant jusqu'à ce que le filtre ne soit plus vrai, arrête (plutôt que de continuer à la fin)

Pour le démontrer, ce qui suit est une HTML simplifiée -. (En réalité, il est généré dynamiquement, un ordre aléatoire / données, plusieurs colonnes, les noms de classe appropriés, etc.)

<table>
    <thead>
        <tr>
            <th>...</th>
        </tr>
    </thead>
    <tbody>

        <tr class="x"><td>a <button>Show/Hide</button></td></tr>
            <tr class="x y"><td>a1</td></tr>
            <tr class="x y"><td>a2</td></tr>

        <tr class="z"><td>b</td></tr>

        <tr class="z"><td>c</td></tr>

        <tr class="x"><td>d <button>Show/Hide</button></td></tr>
            <tr class="x y"><td>d1</td></tr>
            <tr class="x y"><td>d2</td></tr>
            <tr class="x y"><td>d3</td></tr>

        <tr class="z"><td>e</td></tr>

        <tr class="x"><td>f</td></tr>

        <tr class="x"><td>g <button>Show/Hide</button></td></tr>
            <tr class="x y"><td>g1</td></tr>
            <tr class="x y"><td>g2</td></tr>

    </tbody>
</table>

Et contre ce peu de JavaScript est exécuté:

<script type="text/javascript">
    var $j = jQuery.noConflict();

    $j().ready(init);

    function init()
    {
        $j('tr.y').hide();
        $j('tr.x button').click( toggleRelated );
    }

    function toggleRelated()
    {
        // Only toggles one row
        // $j(this).parents('tr').next('.y').toggle();

        // Toggles unrelated ones also
        $j(this).parents('tr').nextAll('.y').toggle();

        // Not currently a jQuery construct
        // $j(this).parents('tr').nextWhile('.y').toggle();
    }

</script>

Y at-il un moyen facile de mettre en œuvre cette construction nextWhile?

Idéalement cela doit être réalisé sans modifier le code HTML en cours.

Était-ce utile?

La solution

méthode et nextWhile() équivalent en utilisant nextUntil() a href = "http: / /api.jquery.com/not-selector/ » rel = "nofollow"> :not sélecteur . Autrement dit, while (condition is true) { do something } est la même que dire until (condition is false) { do something } .

Considérez cet exemple de truc où vous devez sélectionner tous les éléments .child qui suivent la première .parent:

<ul id="test">
  <li class="parent"></li>
  <li class="child"></li>
  <li class="child"></li>
  <li class="child"></li>
  <li class="divider"></li>
  <li class="parent"></li>
  <li class="child"></li>
  <li class="child"></li>
  <li class="child"></li>
</ul>

Le code suivant est à peu près équivalent à .nextWhile(".child") et sélectionne les trois éléments de .child:

$("#test .parent:first").nextUntil(":not(.child)");

Autres conseils

Mise à jour:. Gave sur l'idée de récursivité et a décidé de compter et tranche (voir l'exemple dernier)

initial Tentative: Ce code est bogué - il ne retourne que les deux derniers éléments, donc ne fonctionne pas pour 3 articles

.
jQuery.fn.nextWhile = function(f)
{
    if( this.next(f).html() )
    {
        return this.next(f).nextWhile(f).andSelf();
    }
    else
    {
        return this;
    }
};

Version actuelle:

jQuery.fn.nextWhile = function(f)
{
    var Next = this.next(f);
    var Pos = 0;

    while( Next.length > 0 )
    {
        Pos++;
        Next = Next.next(f);
    }

    return this.nextAll(f).slice(0,Pos);
}

Cela semble fonctionner très bien, mais je ne sais pas s'il y a des pénalités de performance pour sélectionner tout, puis trancher seulement une poignée de celui-ci?

Ma version:

$.fn.extend({
  nextWhile: function(selector) {
    var $result = $([]);
    this.each(function() {
      var $next = $(this).next();
      while ($next.is(selector)) {
        $result = $result.add($next);
        $next = $next.next();
      }
    });
    return $result;
  }
});
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top