Funktioniert: vorher nicht an img Elementen?

262

Ich versuche, mit dem :beforeSelektor ein Bild über einem anderen Bild zu platzieren, aber ich stelle fest, dass es einfach nicht funktioniert, ein Bild vor einem imgElement zu platzieren, sondern nur vor einem anderen Element. Insbesondere sind meine Stile:

.container
{
   position: relative;
   display: block;
}

.overlay:before
{
    content: url(images/[someimage].png);
    position: absolute;
    left:-20px;
    top: -20px;
}

und ich finde, dass dies gut funktioniert:

<a href="[url]" class="container">
  <span class="overlay"/>
  <img width="200" src="[url]"/>
</a>

aber das geht nicht:

<a href="[url]" class="container">
  <img width="200" src="[url]" class="overlay"/>
</a>

Ich kann stattdessen ein divoder p-Element verwenden span, und der Browser überlagert mein Bild korrekt mit dem Bild im imgElement. Wenn ich die Overlay-Klasse jedoch auf sich imgselbst anwende , funktioniert dies nicht.

Ich würde das gerne zum Laufen bringen, weil spanmich das zusätzlich beleidigt, aber was noch wichtiger ist, ich habe ungefähr 100 Blog-Beiträge, die ich ändern möchte, und ich kann dies auf einmal tun, wenn ich nur das Stylesheet ändern könnte. aber wenn ich zurück zu gehen und fügen Sie ein zusätzliches spanElement zwischen den aund imgElementen, wird dies viel mehr Arbeit sein.

Joshua Frank
quelle
5
Dies ist seltsam, zumal der CSS-Standard selbst ein Beispiel für die Verwendung von: Vorher mit einem IMG-Element gibt…
@chharvey: Diese Frage wurde nach dieser gestellt.
Joshua Frank

Antworten:

262

Leider unterstützen die meisten Browser die Verwendung von :afteroder :beforefür img-Tags nicht.

http://lildude.co.uk/after-css-property-for-img-tag

Mit JavaScript / jQuery können Sie jedoch das erreichen, was Sie benötigen. Schauen Sie sich diese Geige an:

http://jsfiddle.net/xixonia/ahnGT/

$(function() {

    $('.target').after('<img src="..." />');

});

Bearbeiten :

Lesen Sie die Antwort von coreyward , um herauszufinden, warum dies nicht unterstützt wird .

cwharris
quelle
3
deine Geige fehlt. Das ist das Schöne an jsFiddle-Links.
Roko C. Buljan
Behoben. Das tut mir leid.
Cwharris
1
Diese Antwort erklärt nicht, warum img vorher oder nachher nicht haben kann. Die vorgeschlagene Javascript-Lösung ist auch kein geeigneter Ersatz dafür.
Jasper Kennis
3
Es wird nicht erwartet, dass die vorgeschlagene Lösung in jedem Szenario funktioniert. Es ist nur ein Beispiel dafür, wie man das Problem umgehen könnte. Wenn Sie eine allgemeinere Lösung vorschlagen möchten, können Sie gerne eine Antwort posten.
Cwharris
141

Die Vorher- und Nachher-Pseudoselektoren fügen keine HTML-Elemente ein - sie fügen Text vor oder nach dem vorhandenen Inhalt des Zielelements ein. Da Bildelemente enthalten keinen Text oder haben Nachkommen, weder img:beforeoder img:afterwerden Sie etwas Gutes tun. Dies gilt auch für Elemente wie <br>und <hr>aus demselben Grund.

Coreyward
quelle
Img-Tags sind eindeutig Elemente an und für sich, und dennoch dürfen wir sie vor oder nach anderen Elementen mit den Pseudo-Selektoren: before und: after einfügen. Ist das nicht in der CSS-Spezifikation?
Cwharris
13
Das ist ein bisschen anders. Sie können ein Bild einfügen, aber kein Bild-Tag verwenden - Sie müssen die content: url(/img/foo.jpg);Syntax verwenden. Weitere Informationen finden Sie unter w3.org/TR/CSS21/generate.html .
Coreyward
4
Kleine Korrektur: Sie fügen Pseudo-Elemente ein, die eher Elementen als Textknoten ähneln.
Chris Calo
Generierter Inhalt wird Teil des Shadow DOM. Diese neuen Elemente, Attribute und Textknoten sind sehr real. Sie können sie zB im Chrome Inspector sehen.
Marc Diethelm
@coreyward Vielleicht werden Sie MDN (Replaced Element)
Marc Diethelm
41

Ich habe einen Weg gefunden, diese Arbeit in reinem CSS zu machen:

Der Ich bin nur gefälschter Inhalt -Methode

eine reine CSS-Methode, um img: after zu aktivieren.

Sie können den CodePen überprüfen : Ich bin nur gefälschter Inhalt oder sehe die Quelle .

Quelle & Snippet

img {
    /* hide the default image */
    height:0;
    width:0;

    /* hide fake content */
    font-size:0;
    color:transparent;

    /* enable absolute position for pseudo elements */
    position:relative;

    /* and this is just fake content */
    content:"I'm just fake content";
}

/* initial absolute position */
img:before,
img:after {
    position:absolute;
    top:0;
    left:0;    
}

/* img:before - chrome & others */
img:before {
    content:url(http://placekitten.com/g/250/250);
}

/* img:before - firefox */
body:not(:-moz-handler-blocked) img:before {
    padding:125px;
    background:url(http://placekitten.com/g/250/250) no-repeat;
}

/* img:after */
img:after {
    /* width of img:before */
    left:250px;

    content:url(http://lorempixel.com/350/200/city/1);
}
<img
    alt="You are watching the ~ I'm just fake content ~ method"  
/>

Browser-Unterstützung

✓ Chrome 10+

✓ Firefox 11+

✓ Opera 9.8+

✓ Safari

Keine Unterstützung

⊗ Internet Explorer 8/9

Bitte testen Sie in anderen Browsern

TimPietrusky
quelle
1
Im Grunde genommen fügen Sie einfach Inhalt: "" zum Stil des img-Tags hinzu und: vor und: nach Arbeitsbeginn. Schöner Fund, ich frage mich, wie browserübergreifend es ist.
w00t
2
Ich habe einen Symboltest für jsbin.com/esewow/edit#html,live eingerichtet und kann bestätigen, dass er unter IE8 nicht funktioniert, unter Chrome und Safari jedoch einwandfrei .
w00t
14
Das CodePen-Beispiel funktioniert in Firefox nur, wenn der src des img-Tags ungültig ist. Dadurch wird das alt-Attribut als Element gerendert, das tatsächlich Folgendes zulässt: vorher und nachher. Wenn das img src existiert, funktioniert es nicht mehr: codepen.io/anon/pen/EjtDu
thenickdude
2
Stoppen Sie mich, wenn ich falsch
liege
5
img: vorher und img: nachher arbeite überhaupt nicht in Safari . Nicht einmal das, was mich anfangs aufgeregt hatte. Guter Versuch.
Wray Bowling
9

Aufgrund der Art <img>, ein ersetztes Element zu sein , hat das Dokument-Styling keinen Einfluss darauf.

Um es trotzdem zu referenzieren, <picture>bietet es einen idealen, nativen Wrapper, an den Pseudoelemente angehängt werden können, wie folgt:

img:after, picture:after{
    content:"\1F63B";
    font-size:larger;
    margin:-1em;
}
<img src="//placekitten.com/110/80">

<picture>
    <img src="//placekitten.com/110/80">
</picture>

Dakab
quelle
3

Hier ist eine andere Lösung, bei der ein div-Container für img verwendet wird :hover::after, um den Effekt zu erzielen.

Der HTML wie folgt:

<div id=img_container><img src='' style='height:300px; width:300px;'></img></div>

Das CSS wie folgt:

#img_container { 
    margin:0; 
    position:relative; 
} 

#img_container:hover::after { 
    content:''; 
    display:block; 
    position:absolute; 
    width:300px; 
    height:300px; 
    background:url(''); 
    z-index:1; 
    top:0;
} 

Schauen Sie sich die Geige an, die ich erstellt habe , um sie in Aktion zu sehen . Nur damit Sie wissen, dass dies browserübergreifend ist und Sie den Code nicht mit "gefälschten Inhalten" austricksen müssen.

truleighsyd
quelle
Es ist hilfreich , anzuwenden display: inline-blockauf #img_container. Dadurch entspricht die Breite des Containers bei allen Bildschirmgrößen dem Bild. Sie haben also keinen :afterInhalt, der außerhalb des Bildes schwebt.
Anonym
1

Ich denke, der beste Weg, um herauszufinden, warum dies nicht funktioniert, ist folgender: vor und nach dem Einfügen des Inhalts vor oder nach dem Inhalt des Tags, auf das Sie sie anwenden. Es funktioniert also mit Divs oder Spans (oder den meisten anderen Tags), da Sie Inhalte in diese einfügen können.

<div>
:before
Content
:after
</div>

Ein img ist jedoch ein in sich geschlossenes, sich selbst schließendes Tag. Da es kein separates schließendes Tag enthält, können Sie nichts darin einfügen. (Das müsste so aussehen <img>Content</img>, aber das funktioniert natürlich nicht.)

Ich weiß, dass dies ein altes Thema ist, aber es taucht zuerst bei Google auf. Hoffentlich hilft dies anderen beim Lernen.

BevansDesign
quelle
1

Dieser funktioniert für mich:

html

<ul>
    <li> name here </li>
</ul>

CSS

ul li::before {
    content: url(../images/check.png);
}
Schwert I.
quelle
1

::after kann verwendet werden, um das Fallback-Bild eines Bildes anzuzeigen


Im folgenden Beispiel zeigen die ersten imgbeiden Tags auf die fehlerhaften URLs. Das zweite zeigt jedoch das Fallback-Bild anstelle des standardmäßig defekten Logos des Browsers an. Ich bin mir jedoch nicht sicher, ob dies praktikabel ist. Ich finde es schwierig, es richtig zum Laufen zu bringen.

img {
  position: relative;
  display: inline-block;
  width: 300px;
  height: 200px;
  vertical-align: top;
}
img:not(:first-child)::after {
  position: absolute;
  left: 0; top: 0; right: 0; bottom: 0;
  content: "<" attr(alt) "> NOT FOUND";
  border: 1px dashed #999;
  background: url(https://cdn.dribbble.com/users/1012566/screenshots/4187820/topic-2.jpg) center/100%;
}
<img src="https://source.unsplash.com/random/100/75" alt="logo">
<img src="https://source.unsplash.com/random/100/75" alt="logo">
<img src="https://source.unsplash.com/random/100x75" alt="logo">

Loi Nguyen Huynh
quelle
0

Versuchen Sie diesen Code

.button:after {
    content: ""
    position: absolute
    width: 70px
    background-image: url('../../images/frontapp/mid-icon.svg')
    display: inline-block
    background-size: contain
    background-repeat: no-repeat
    right: 0
    bottom: 0
}
subindas pm
quelle
-1

Ich habe versucht, eine einfachere Methode zu finden. Hier ist der HTML:

    <img id="message_icon" src="messages2.png">
    <p id="empty_para"></p>

Ich habe ein leeres <p>Tag nach meinem Bild-Tag platziert. Jetzt werde ich p :: before verwenden, um das Bild anzuzeigen und es gemäß meinen Anforderungen zu positionieren. Hier ist das CSS:

#empty_para
{
    display:inline;
    font-size:40;
    background:orange;
    border:2px solid red;
    position:relative;
    top:-400px;
    left:100px;
}
#empty_para::before
{
    content: url('messages.png');
}

Versuch es.

Tajveer Singh Nijjar
quelle
-1

Versuchen Sie :: after für das vorherige Element.

Dmytro Yurchenko
quelle
Würden Sie Ihren Beitrag ausarbeiten?
Zmag