Ein CSS-Selektor, um das letzte sichtbare Div zu erhalten

161

Eine knifflige CSS-Auswahlfrage, ich weiß nicht, ob es überhaupt möglich ist.

Nehmen wir an, dies ist das HTML-Layout:

<div></div>
<div></div>  
<div></div>  
<div style="display:none"></div>
<div style="display:none"></div>  

Ich möchte den letzten auswählen div, der angezeigt wird (dh nicht display:none), der divim gegebenen Beispiel der dritte wäre . Wohlgemerkt, die Anzahl der divs auf der realen Seite kann unterschiedlich sein (sogar die display:none).

Vishal Shah
quelle

Antworten:

62

Sie können dies mit JavaScript oder jQuery auswählen und formatieren, aber CSS allein kann dies nicht.

Wenn Sie beispielsweise jQuery auf der Site implementiert haben , können Sie Folgendes tun:

var last_visible_element = $('div:visible:last');

Obwohl Sie hoffentlich eine Klasse / ID um die von Ihnen ausgewählten Divs haben, würde Ihr Code in diesem Fall folgendermaßen aussehen:

var last_visible_element = $('#some-wrapper div:visible:last');
Surreale Träume
quelle
22
Die Frage sagt eindeutig nein "ein JQuery CSS Selector", sagt "A CSS SELECTOR", dies sollte die akzeptierte ANTWORT = P
AgelessEssence
2
Dies ist in der Tat die Antwort auf die ursprüngliche Frage. Der Fragesteller erwähnte nie Javascript oder JQuery und diese Tags wurden von einem anderen Antwortenden hinzugefügt. 1nfected - möchten Sie tatsächlich jQuery? Wenn ja, setzen Sie das bitte tatsächlich in Ihre Frage ein. Andernfalls sollten Sie diese Antwort stattdessen akzeptieren.
Jep
Ich denke, jQuery ist für das OP akzeptabel. Das war schließlich die akzeptierte Lösung.
Surreal Dreams
7
Warum ist die erste Antwort allllwaaayyysss jquery? Dies ist eine Javascript- Antwort auf eine CSS- Frage. CSS! == Javascript
Dudewad
2
@dudewad: Siehe den letzten Teil des ersten Satzes: "Aber CSS allein kann das nicht." Die Antwort könnte es dabei belassen, ohne dass eine Alternative in Sicht ist ... oder eine Alternative bieten. Aber diese Antwort hat zumindest ihre gebührende Sorgfalt darauf verwendet, tatsächlich zu behaupten, dass CSS nicht das tun kann, was gefragt wird (obwohl es nicht näher erläutert, warum ). Auf der anderen Seite, eine Antwort , die auf einer JavaScript - Lösung erlischt nur , ohne die CSS Art der Frage anzuerkennen ist Kritik wert.
BoltClock
23

Die eigentliche Antwort auf diese Frage lautet: Sie können es nicht tun. Alternativen zu Nur-CSS-Antworten sind keine korrekten Antworten auf diese Frage. Wenn JS-Lösungen für Sie akzeptabel sind, sollten Sie hier eine der JS- oder jQuery-Antworten auswählen. Wie ich oben sagte, ist die wahre, richtige Antwort jedoch, dass Sie dies in CSS nicht zuverlässig tun können, es sei denn, Sie sind bereit, den :notOperator mit den [style*=display:none]und anderen solchen negierten Selektoren zu akzeptieren , was nur bei Inline-Stilen funktioniert und insgesamt schlecht ist Lösung.

Dudewad
quelle
Erstens stimme ich Ihnen zu, aber ich denke, dass die Verwendung des :notvon Ihnen angegebenen Operators unter bestimmten Umständen funktionieren kann. Zum Beispiel funktioniert dies perfekt für meine Situation, in der JS Elemente bedingt versteckt, die dann Inline-Stile hinzufügen, und somit funktioniert Ihre Lösung tatsächlich perfekt :)
doz87
1
Nun, dann denke ich, was funktioniert :) Ich bin nur ein bisschen ein Idealist und ich betone gerne, wo die Dinge nicht die besten sind. Es ist wichtig zu unterscheiden, was "hacky" ist und was nicht, weil es macht uns alle zu besseren Programmierern.
Dudewad
Ja, ich höre ja, ich stimme zu, dass diese Lösung nicht als reine CSS-Lösung für die OP-Abfrage verwendet werden sollte. Ich denke jedoch, dass dies in Verbindung mit JS sehr gut funktioniert.
doz87
Sie können auch eine CSS-Klasse verwenden, um Elemente auszublenden (anstelle eines Inline-Stils). Wenn dies der Fall ist, können Sie den Selektor für diese versteckte Klasse genauso gut negieren. Dadurch wird immer dasselbe ausgewählt, was ausgeblendet ist, da beide von derselben CSS-Klasse festgelegt werden. Ihre Antwort geht also in die richtige Richtung, aber nicht weit genug. :-)
ygoe
8

Wenn Sie Inline-Stile verwenden können, können Sie dies nur mit CSS tun.

Ich verwende dies, um CSS für das nächste Element auszuführen, wenn das vorherige sichtbar ist:

div [style = 'display: block;'] + table {
  Filter: Unschärfe (3px);
}}
Alex Grande
quelle
1
Ich würde es ändern, [style*='display: block']da es haben könnte display: block !important;oder nur <div style="display: block">:-)
OZZIE
Es funktioniert für mich in einer CSS-Datei wie dieser .btn-group > .btn.d-none + .btn(wird für die Eingabegruppen von Bootstrap verwendet "
Jean-Charbel VANNIER
7

Ich denke, es ist nicht möglich, durch einen CSS-Wert auszuwählen (Anzeige)

bearbeiten:

Meiner Meinung nach wäre es sinnvoll, hier ein bisschen jquery zu verwenden:

$('#your_container > div:visible:last').addClass('last-visible-div');
Guillaume86
quelle
6

Reine JS-Lösung (z. B. wenn Sie jQuery oder ein anderes Framework nicht für andere Zwecke verwenden und diese nicht nur für diese Aufgabe herunterladen möchten):

<div>A</div>
<div>B</div>  
<div>C</div>  
<div style="display:none">D</div>
<div style="display:none">E</div>    

<script>
var divs = document.getElementsByTagName('div');
var last;

if (divs) {
    for (var i = 0; i < divs.length; i++) {
        if (divs[i].style.display != 'none') {
            last = divs[i];           
        }
    }
}

if (last) {
    last.style.background = 'red';
}
</script>

http://jsfiddle.net/uEeaA/90/

Panther
quelle
Vielen Dank für das Snippet, die einzige Antwort ohne jQuery! Dies funktioniert jedoch nicht, wenn mehrere übergeordnete Elemente angewendet werden müssen : jsfiddle.net/uEeaA/100 - Können Sie mir helfen, eine Lösung für andere zu erstellen , die funktioniert? Ich brauche es, andere brauchen es, also bitte helfen Sie :)
mnsth
Mir ist klar, dass dies ein alter Thread ist, aber für zukünftige Besucher könnten Sie etwas in der Art von jsfiddle.net/uEeaA/103
xec
Ich wollte dies nur deshalb abstimmen, weil du jQuery fallen gelassen hast - gut auf dich. Meine einzige Beschwerde ist, dass ein Div auf viele Arten ausgeblendet werden kann, nicht nur basierend auf dem Stilparameter. Ganz schnell: [1] Breite und Höhe können auf 0 gesetzt werden, [2] Transformationsskala kann 0 sein, [3] und wir können sie außerhalb des sichtbaren Bereichs platzieren.
Markus
4

Versuchen

div: not ([style * = "display: none"])

Tyler Wayne
quelle
2

Auf andere Weise können Sie dies mit Javascript tun. In Jquery können Sie Folgendes verwenden:

$('div:visible').last()

* überarbeitet

Evaevans
quelle
2

Mit CSS ist dies nicht möglich, Sie können dies jedoch mit jQuery tun.

JSFIDDLE DEMO

jQuery:

$('li').not(':hidden').last().addClass("red");

HTML:

<ul>
        <li>Item 1</li>
        <li>Item 2</li>
        <li>Item 3</li>
        <li class="hideme">Item 4</li>    
</ul>

CSS:

.hideme {
    display:none;
}

.red {
    color: red;
}

jQuery (vorherige Lösung):

var $items = $($("li").get().reverse());

$items.each(function() {

    if ($(this).css("display") != "none") {
        $(this).addClass("red");
        return false;
    }

});
Martynas
quelle
3
Das ist viel jQuery für $('li:visible:last').addClass('red').
Alex
Huh? $('li').not(':hidden').last().addClass("red");
Martynas
0

Wenn Sie die ausgeblendeten Elemente nicht mehr benötigen, verwenden Sie einfach element.remove()anstelle von element.style.display = 'none';.

Masoud Shariati
quelle
-6

Das hat bei mir funktioniert.

.alert:not(:first-child){
    margin: 30px;
}
kmukku
quelle
3
Sie beantworten die Frage nicht
Serginho