Как скрыть изображение испорченного Icon используя только CSS / HTML?

194

Как я могу скрыть значок сломанного изображения? Пример : пример

У меня есть изображение с ошибкой SRC:

<img src="Error.src"/>

Решение должно работать во всех браузерах.

Герай Суинов
источник
1
Я попытался установить alt = "" и установить фоновое изображение, чтобы бросить CSS вживую: {background: url (src), width: ...; высота: ..} но это не так. Мой тег img должен скрыться, тогда src не работает.
Герай Суинов
Смотрите возможное решение здесь - stackoverflow.com/questions/18484753/…, но требует JS, хотя. Вы не можете сделать это только с помощью CSS.
JohanVdR
См. W3schools.com/jsref/event_onerror.asp "onerror" атрибут
Amy.js

Ответы:

274

У CSS / HTML нет возможности узнать, не является ли изображение неработающей ссылкой, поэтому вам придется использовать JavaScript независимо от того, что

Но вот минимальный способ либо скрыть образ, либо заменить источник резервной копией.

<img src="Error.src" onerror="this.style.display='none'"/>

или

<img src="Error.src" onerror="this.src='fallback-img.jpg'"/>

Обновить

Вы можете применить эту логику к нескольким изображениям одновременно, выполнив что-то вроде этого:

document.addEventListener("DOMContentLoaded", function(event) {
   document.querySelectorAll('img').forEach(function(img){
  	img.onerror = function(){this.style.display='none';};
   })
});
<img src="error.src">
<img src="error.src">
<img src="error.src">
<img src="error.src">

Обновление 2

Для варианта CSS см . Ответ michalzuber ниже. Вы не можете скрыть все изображение, но вы изменяете, как выглядит сломанный значок.

Кевин Янцер
источник
3
Вы можете сделать это с помощью HTML только с помощью тега объекта, так как он может использоваться для отображения изображений так же, как тег img, и не отображает неработающую ссылку, если изображение не существует, он работает во всех браузерах и даже в далеком прошлом. Поскольку IE8 сам по себе, вы даже можете использовать изображения по умолчанию с этим методом, я опубликовал ответ с деталями ниже.
Ник Стил
1
Это сработало для меня вместо подхода <object>, потому что мне нужно, чтобы изображение имело объявленное поле, но только если было найдено правильное изображение, в противном случае мне нужно, чтобы оно занимало нулевое пространство. У <object> нет события onerror, так что это было невозможно. Правило стиля для удаления поля с использованием псевдокласса: empty никогда не срабатывало на объекте.
Джон Хаттон,
У меня есть вопрос. есть ли способ дать сценарию общее правило для применения к каждому тегу изображения на странице вместо указания этой конкретной строки сценария в каждом теге изображения. спасибо @Kevin jantzer
Лемдор
1
@Lemdor - да, вам нужно будет найти изображения под нагрузкой и прикрепить общую функцию к каждому. Вы можете использовать jQuery или vanilla JS для этого (я обновил свой ответ примером)
Кевин Джанцер
В реакции это очень легко сделать, там применяется тот же принцип. Нашел этот урок здесь - youtu.be/90P1_xCaim4 . Также добавление preloader ( youtu.be/GBHBjv6xfY4 ) для изображения скрывает переход и помогает обеспечить хороший UX.
Прем
143

Несмотря на то, что люди говорят здесь, вам вообще не нужен JavaScript, вам даже не нужен CSS !!

Это на самом деле очень выполнимо и просто только с HTML. Вы даже можете показать изображение по умолчанию, если изображение не загружается . Вот как...

Это также работает во всех браузерах, даже начиная с IE8 (из 250 000+ посетителей сайтов, которые я принимал в сентябре 2015 года, пользователи ZERO использовали что-то хуже, чем IE8, что означает, что это решение работает буквально для всего ).

Шаг 1: Ссылка на изображение как объект, а не img . Когда объекты терпят неудачу, они не показывают сломанные значки; они просто ничего не делают. Начиная с IE8, вы можете использовать теги Object и Img взаимозаменяемо. Вы можете изменить размер и сделать все великолепные вещи, которые вы можете с обычными изображениями тоже. Не бойтесь тега объекта; это просто тег, ничего большого и громоздкого не загружается и ничего не тормозит. Вы просто будете использовать тег img под другим именем. Тест скорости показывает, что они используются одинаково.

Шаг 2: (Необязательно, но потрясающе) Вставьте изображение по умолчанию внутри этого объекта. Если нужное изображение действительно загружается в объект , изображение по умолчанию отображаться не будет. Так, например, вы могли бы показать список пользовательских аватаров, и если у кого-то еще нет изображения на сервере, он мог бы показать изображение заполнителя ... никакой JavaScript или CSS не требуется вообще, но вы получаете возможности того, что принимает большинство людей JavaScript.

Вот код ...

<object data="avatar.jpg" type="image/jpg">
    <img src="default.jpg" />
</object>

... Да, это так просто.

Если вы хотите реализовать изображения по умолчанию с помощью CSS, вы можете сделать это еще проще в своем HTML, как это ...

<object class="avatar" data="user21.jpg" type="image/jpg"></object>

... и просто добавьте CSS из этого ответа -> https://stackoverflow.com/a/32928240/3196360

Ник Стил
источник
6
Каким-то образом я полностью упустил эту идею, когда она так очевидна в ретроспективе! К сожалению, я не думаю, что тег объекта может изящно обрабатывать адаптивные изображения, как мы начинаем видеть в свойстве img.srcset :(
Windgazer
2
Отличная идея, спасибо за это! С другой стороны, тег объекта блокирует колесо прокрутки (по крайней мере, в моей реализации) ... если это происходит с вами, просто используйте object { pointer-events: none; }в своем CSS (Источник: stackoverflow.com/a/16534300 )
DHainzl
4
Однако это нарушает семантику тегов изображений. Я не знаю, понравится ли поисковым системам использование <object>тегов вместо <img>тегов. Является ли этот подход HTML5-совместимым и корректно отображается во всех основных браузерах?
Питер
6
Он совместим с HTML4 (совместим с 1997 года) и корректно отображается во всех основных браузерах начиная с IE8 / 2009 (другие браузеры делали это намного раньше). Если поисковая система не понимает, что объект с типом изображения - это изображение, у него было 19 лет, чтобы наверстать упущенное, так что это, вероятно, не очень хороший двигатель ... Подростки, которые ездят на автомобилях, теперь не были даже задумано, когда это решение соответствует спецификациям ... Как далеко вы хотите вернуться? :) Это надежное решение.
Ник Стил
6
@MonsterMMORPG, потому что он не использует JavaScript, и вам не всегда разрешено (например, в теле сообщения электронной почты).
ForNeVeR
63

Нашел отличное решение на https://bitsofco.de/styling-broken-images/

img {  
  position: relative;
}

/* style this to fit your needs */
/* and remove [alt] to apply to all images*/
img[alt]:after {  
  display: block;
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  background-color: #fff;
  font-family: 'Helvetica';
  font-weight: 300;
  line-height: 2;  
  text-align: center;
  content: attr(alt);
}
<img src="error">
<br>
<img src="broken" alt="A broken image">
<br>
<img src="https://images-na.ssl-images-amazon.com/images/I/218eLEn0fuL.png" alt="A bird" style="width: 120px">

michalzuber
источник
1
Отличное решение, использующее CSS, которое должно быть принятым ответом. Ссылка на статью устарела, поскольку поддержка браузеров теперь составляет 97,87%: caniuse.com/#feat=css-gencontent .
holm50
1
В связанной статье содержится отличное объяснение того, как браузеры обрабатывают изображения, но имейте в виду, что это решение работает только в том случае, если у вас сплошной фон и вы хотите покрыть все другим блоком того же сплошного цвета или другим изображением. Это решение на самом деле не удаляет и не скрывает значок разбитого изображения, оно просто закрывает его.
Клаудио Флореани
3
На Chrome 70 он показывает птицу + значок с разбитым изображением :(
Саймон Арнольд,
2
^ То же самое на Firefox 63
беспокойный
1
@dailysleaze - в Firefox 64+ это перемещено в img[alt]::before. Вы можете использовать, display:inline-blockесли хотите, так как он ближе к оригиналу.
Адам Кац
41

Если вы добавите alt с текстом alt = "abc", он покажет миниатюру показа поврежденных файлов и alt сообщение abc.

<img src="pic_trulli.jpg" alt="abc"/>

первый

Если вы не добавите Alt, то покажет миниатюру шоу.

<img src="pic_trulli.jpg"/>

второй

Если вы хотите скрыть поврежденный файл, просто добавьте alt = "", он не будет отображать поврежденный эскиз и любое сообщение alt (без использования js)

<img src="pic_trulli.jpg" alt=""/>

Если вы хотите скрыть сломанный, просто добавьте alt = "" & onerror = "this.style.display = 'none'", он не будет отображать поврежденный эскиз и какое-либо сообщение alt (с js)

<img src="pic_trulli.jpg" alt="abc" onerror="this.style.display='none'"/>

В-четвертых, это немного опасно (не совсем), если вы хотите добавить какое-либо изображение в событие onerror, оно не будет отображаться, даже если Image существует в виде style.display, как при добавлении. Таким образом, используйте его, когда вам не нужно альтернативное изображение для отображения.

display: 'none'; // in css

Если мы дадим его в CSS, то элемент не будет отображаться (например, image, iframe, div и т. Д.).

Если вы хотите отобразить изображение и вы хотите отобразить полностью пустое пространство в случае ошибки, вы можете использовать, но также будьте осторожны, это не займет никакого места. Таким образом, вы должны держать его в div

Ссылка https://jsfiddle.net/02d9yshw/

П Сатиш Патро
источник
2
ДА! Просто добавь alt=""! Это буквально это! Спасибо. Так рада, что прокрутила до конца страницы. Я использую ленивую загрузку, и изображения в кадре, которые еще не загружены (потому что браузер ошибочно считает, что область просмотра еще не прокрутила их), отображаются как поврежденные изображения. Немного свитка, и они появляются снова. Разбитые изображения на их месте были такими уродливыми
velkoon
25

Я думаю, что самый простой способ - скрыть значок разбитого изображения с помощью свойства text-indent.

img {
    text-indent: -10000px
}

Очевидно, это не сработает, если вы хотите увидеть атрибут «alt».

Burnee
источник
1
Самый простой способ.
Theerasan Tonthongkam
17

в случае, если вы хотите сохранить / использовать изображение в качестве заполнителя, вы можете изменить непрозрачность до 0 с помощью ошибки onerror и некоторого CSS, чтобы установить размер изображения. Таким образом, вы не увидите неработающую ссылку, но страница загрузится как обычно.

<img src="<your-image-link->" onerror="this.style.opacity='0'" />

img {
    width: 75px;
    height: 100px;
}
Эвальд Бос
источник
16

Мне понравился ответ на Ника и играл вокруг с этим решением. Нашел более чистый метод. Поскольку псевдо: :: before / :: after не работают с заменяемыми элементами, такими как img и object, они будут работать только в том случае, если данные объекта (src) не загружены. Он сохраняет HTML-код более чистым и добавляет псевдо, только если объект не загружается.

object {
  position: relative;
  float: left;
  display: block;
  width: 200px;
  height: 200px;
  margin-right: 20px;
  border: 1px solid black;
}
object::after {
  position: absolute;
  top: 0;
  left: 0;
  display: block;
  width: 100%;
  height: 100%;
  content: '';
  background: red url("http://placehold.it/200x200");
}
<object data="http://lorempixel.com/200/200/people/1" type="image/png"></object>

<object data="http://broken.img/url" type="image/png"></object>

Bartezz
источник
9

Если вам все еще нужно видеть контейнер с изображениями из-за того, что он будет заполнен позже, и вы не хотите показывать и скрывать его, вы можете вставить прозрачное изображение 1x1 внутри src:

<img id="active-image" src="data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7"/>

Я использовал это для этой конкретной цели. У меня был контейнер изображений, который собирался загрузить изображение через Ajax. Поскольку изображение было большим и потребовало немного времени для загрузки, требовалось установить background-image в CSS панели загрузки Gif.

Однако из-за того, что src был пуст, значок неработающего изображения все еще появлялся в браузерах, которые его используют.

Установка прозрачного GIF 1x1 решает эту проблему просто и эффективно без добавления кода через CSS или JavaScript.

user2596313
источник
Единственный ответ, который сработал, все остальные оставили белый контур
futurelucas4502
8

Использовать только CSS сложно, но вы можете использовать CSS background-imageвместо <img>тегов ...

Что-то вроде этого:

HTML

<div id="image"></div>

CSS

#image {
    background-image: url(Error.src);
    width: //width of image;
    height: //height of image;

}

Вот рабочая скрипка .

Примечание: я добавил границу в CSS на скрипке, чтобы продемонстрировать, где будет изображение.

Драйден Лонг
источник
Это хорошо, но это решение не для меня :) Тег img скрыт, тогда src не работает, div - нет :(
Герай Суинов
@GeraySuinov Тогда вам, возможно, придется использовать Javascript
Dryden Long
4

Используйте тег объекта. Добавьте альтернативный текст между тегами следующим образом:

<object data="img/failedToLoad.png" type="image/png">Alternative Text</object>

http://www.w3schools.com/tags/tag_object.asp

ThomasAFink
источник
3

С 2005 года браузеры Mozilla, такие как Firefox, поддерживают нестандартный :-moz-brokenпсевдокласс CSS, который может выполнить именно этот запрос:

td {
  min-width:64px; /* for display purposes so you can see the empty cell */
}

img[alt]:-moz-broken {
  display:none;
}
<table border="1"><tr><td>
  <img src="error">
</td><td>
  <img src="broken" alt="A broken image">
</td><td>
  <img src="https://images-na.ssl-images-amazon.com/images/I/218eLEn0fuL.png"
       alt="A bird" style="width: 120px">
</td></tr></table>

img[alt]::beforeтакже работает в Firefox 64 (хотя когда-то это было img[alt]::afterтак, что это не надежно). Я не могу заставить кого-то из них работать в Chrome 71.

Адам Кац
источник
Интересно ... знаете ли вы, если Chrome имеет подобный псевдокласс?
1000 Гбит / с
1
@ 1000 Гбит / с - я не смог найти его, когда сделал этот ответ, и не могу найти его сейчас, по крайней мере, с помощью быстрых веб-запросов и просмотра ошибки 11011 в mozilla . На самом деле вы могли бы запросить такую ​​вещь в Chromium (апстрим для Chrome), если хотите, но, поскольку это нестандартно, нет уверенности, что они это сделают.
Адам Кац
Я очень сомневаюсь, что они сделают это за короткое время, учитывая, что им было трудно справиться с некоторыми неприятными ошибками, о которых я там сообщал ... Независимо от того, что встроенные псевдоклассы, подобные этому, будут удалены из в фреймворках много JS-кода, написанного по той же причине
1000Gbps
2

Вы можете следовать по этому пути в качестве решения CSS

img {
        width:200px;
        height:200px;
        position:relative
   }
img:after {
        content: "";
        position: absolute;
        top: 0;
        left: 0;
        width: inherit;
        height: inherit;
        background: #ebebeb url('http://via.placeholder.com/300?text=PlaceHolder') no-repeat center;
        color: transparent;
    }
<img src="gdfgd.jpg">

Дженк ЯГМУР
источник
Сначала я думал, что это хорошее решение, но это не работает в IE. Также не при добавлении отображения блока в после CSS
Гленн Франке
1

Отсутствующие изображения либо просто ничего не отобразят, либо отобразят [? ] поле стиля, когда их источник не может быть найден. Вместо этого вы можете заменить это графическим изображением «отсутствующего изображения», которое, как вы уверены, существует, поэтому существует лучшая визуальная обратная связь, если что-то не так. Или вы можете скрыть это целиком. Это возможно, потому что изображения, которые браузер не может найти, запускают событие JavaScript «ошибка», которое мы можем наблюдать.

    //Replace source
    $('img').error(function(){
            $(this).attr('src', 'missing.png');
    });

   //Or, hide them
   $("img").error(function(){
           $(this).hide();
   });

Кроме того, вы можете захотеть инициировать какое-либо действие Ajax, чтобы отправить электронное письмо администратору сайта, когда это произойдет.

Али Панахян
источник
1

Трюк с img::after хороша, но имеет как минимум 2 недостатка:

  1. не поддерживается всеми браузерами (например, не работает на Edge https://codepen.io/dsheiko/pen/VgYErm )
  2. Вы не можете просто спрятать изображение, вы его закрываете - так что не очень полезно, когда вам нужно показать изображение по умолчанию в случае

Я не знаю универсального решения без JavaScript, но для Firefox есть только одно:

img:-moz-broken{
  opacity: 0;
}
Дмитрий Шейко
источник
0

В React работает та же идея, что и у других:

<img src='YOUR-URL' onError={(e) => e.target.style.display='none' }/>
Кристиан Фриц
источник
-3

Основной и очень простой способ сделать это без какого-либо требуемого кода - просто предоставить пустой оператор alt. Браузер вернет изображение как пустое. Это выглядело бы так, как если бы изображения там не было.

Пример:

<img class="img_gal" alt="" src="awesome.jpg">

Попробуйте, чтобы увидеть! ;)

user45678
источник
10
Это зависит от браузера. В Chrome у вас все еще будут рамка с изображением и значок разорванного изображения в дополнение к (здесь пустому) альтернативному тексту.
Panzi
Если изображение носит декоративный характер и не является обязательным для содержимого, пустое значение alt вполне подойдет. На самом деле это рекомендовано более чем вообще. В противном случае это крайне нежелательно. Разбитое изображение - это изображение, которое невозможно увидеть, но если у него есть alt-тег, его все равно можно услышать. Если вы уберете тег alt, он не будет виден или услышан.
JP DeVries
2
@panzi Я протестировал решение, и похоже, что Chrome изменил свое поведение. Он не будет отображать значок сломанного изображения, если alt="". То же самое касается Firefox.
Филипп Миттерер
-4

Для будущих гуглеров, в 2016 году в браузере есть безопасный чистый CSS способ скрытия пустых изображений с помощью селектора атрибутов:

img[src="Error.src"] {
    display: none;
}

Изменить: я вернулся - для будущих Google, в 2019 году есть способ стилизации фактического текста alt и изображения текста alt в Shadow Dom, но он работает только в инструментах разработчика. Таким образом, вы не можете использовать это. Сожалею. Это было бы так мило.

#alttext-container {
    opacity: 0;
}
#alttext-image {
    opacity: 0;
}
#alttext {
    opacity: 0;
}
VerticalGrain
источник
1
img[src=''] { display: none; } Это снова стало актуальным для шаблонов eBay html only
imos