PIE для скрытых или динамических элементов
Дата публикации: 30.11.2011
Появление скрипта CSS3 PIE значительно упростило реализацию так полюбившихся дизайнерам скругленных углов и различного рода теней. Ведь теперь IE6-8 тоже могут вести себя так, как будто они понимают целый ряд CSS3-свойств.
И пускай это только эмуляция, за которой скрывается достаточно сложное (и, порой, капризное) действо с участием VML-объекта, для простого верстальщика важно, что сделать, например, скругление можно в несколько строк CSS.
Но, конечно, в реальной жизни все так радужно не бывает. Помимо прочих трудностей (перечень которых можно почитать в списке по ссылке, приведенной выше), есть еще одна серьезная проблема.
Проблема PIE и скрытых элементов
Пускай у нас есть какой-то элемент и всплывающая подсказка к нему. Причем подсказку попробуем красиво оформить — добавим скругление и теньку.
<div id="pic"> <img src="pic/pic.png" width="69" height="69" alt="тут нарисована морковь"> <div class="hint">Морковка</div> </div>
Добавляем стили:
#pic {
color: #fff;
position: relative; /* относительно этого блока позицонируем подсказку */
float: left;
}
.hint {
/* оформляем подсказку */
background: #880E00;
padding: 5px 15px 6px 15px;
position: absolute;
top: 20px;
left: 70px;
/* Наводим красоту: */
-moz-border-radius: 10px;
-webkit-border-radius: 10px;
border-radius: 10px;
-webkit-box-shadow: 0 0 10px #969696;
-moz-box-shadow: 0 0 10px #969696;
box-shadow: 0 0 10px #969696;
behavior: url(js/pie.htc); /* это правило лучше вынести в отдельный ie6-8 CSS */
}
На этом этапе все будет просто замечательно (если ты, конечно, не забудешь подключить скрипт PIE). Даже IE6 отобразит закругленную подсказку с тенькой.
А теперь давай добавим динамики. Самый простой вариант — мгновенное отображение подсказки. Использую свой любимый jQuery:
jQuery(document).ready(function(){
jQuery("#pic").hover(
function () {
jQuery(".hint").css("display","block");
},
function () {
jQuery(".hint").css("display","none");
}
);
});
Ну и, конечно, изначально подсказка должна быть не видна. Добавляем правило:
.hint {
display: none;
}
Вот собственно и все. Приплыли. PIE больше работать не будет. Да-да, в IE6-8 подсказка будет обычным прямоугольником:

Проблема на лицо. Если блок изначально скрыт (display: none) или вообще отсутствует в коде (вставляется позже, динамически), PIE для него не сработает.
Решение
Конечно, можно попытаться обмануть скрипт и вместо скрытия блока просто вынести его куда-нибудь за пределы какого-нибудь родителя с overflow: hidden. Однако такой трюк для динамически генерируемого блока не пройдет.
В качестве универсального решения предлагается подключать нужным блокам PIE «на лету».
Для этого определим специальные функции:
var ie = jQuery.browser.msie, ieV = jQuery.browser.version, ie6 = ie&&(ieV == 6), ltie7 = ie&&(ieV
Теперь в нужный момент PIE можно установить (или сбросить, во избежание глюков):
jQuery("#pic").hover(
function () {
jQuery(".hint").css("display","block");
ltie8 ? resetPie(".hint") : false;
}
...
Демо-пример — PIE в скрытом блоке.
Проверено в:
- IE 6-8
- Firefox 3.6+
- Opera 11
- Safari
- Chrome
Примечание для самых внимательных
В коде демо-примера есть малопонятная на первый взгляд строка:
p {
behavior: url(js/pie.htc);
}
Что это и как оно туда попало?
Дело в том, что при первом вызове функции resetPie произойдет загрузка pie.htc, а это почти 34Кб. Время загрузки может оказаться очень даже заметным — самый первый раз, при наведении на рисунок в IE6-8, подсказка сначала появится без CSS3-наворотов, которые «догонят» ее несколько позже.
В больших проектах этой неприятности несложно избежать. Если какой-либо статичный элемент уже использует PIE, то библиотека, конечно, уже будет загружена и глюка не произойдет. На простенькой страничке демо-примера мне пришлось искусственно загрузить PIE, подцепив его на «левый» элемент — абзац. Этот трюк чем-то сродни предварительной загрузке изображений.
Вывод
Теперь PIE можно смело применять для оформления скрытых или динамически генерирующихся блоков.
