2016
1
Окт

Кроссбраузерность для internet explorer

grigoriev
4948
crossbrowser
посмотреть click css
DEMO

Тени элементов и текста, скругление углов блоков, линейные и радиальные градиенты давно стали использоваться в дизайне веб страниц. Все эти элементы в разные времена создавались разными технологиями. С приходом css 3 всё намного упростилось. Но старые браузеры, такие как ИЕ 8  не поддерживают многие css 3 свойства. В данном посте я опишу методы которые я использую для достижения кроссбраузерности в Ie. 

Expressions для ИЕ

В контексте данной статьи о кроссбраузерности ie затрону за одно и Expressions. Хоть это и актуально для ie7 (а он почти ушёл со сцены) но вдруг кому пригодится. Итак, с чем же мы имеем дело. Expressions - это конструкция в css файле, которую понимает только IE. С помощью этой конструкции мы можем писать в css файле полноценный javascript код.

    .box {
        width: 100px;
        height: 100px;
        zoom: expression(javascript код);
    }

Такой вот не сложный синтаксис. Часто встречается использование в выражениях волшебного слова "this" (ссылаются на данный объект), но на практике оказалось, что использовать это не обязательно. В основном, с помощью экспрешенов выводят, вычисляют, задают css-свойства элементов. Перед тем как попробовать написать expressions, давайте вспомним основные методы работы с css стилями в javascript под ИЕ 7.

  • style- дает доступ к стилю элемента. Свойство читается и переписывается. Пример: element.style.height='50px'
  • currentStyle (IE)- отдаёт вычисленное (computed) значение, которое получено после исполнения всех правил CSS. Работает только в IEgetComputedStyle
  • runtimeStyle (IE) - позволяет читать и переопределять значение стиля

Используя данные методы, напишем несколько expressions.

Изменяем блочную модель для ИЕ

В браузерах отличных от ИЕ 7 ширина дива будет вычисляться с учётом границы слева (граница будет входить в ширину). В ИЕ ширина блока и границы будут складываться. Чтобы этого не происходило, мы написали экспрешен, который вычисляет ширину блока в ИЕ с вычитанием из его ширины толщину границы.

.myDiv{
    border-left: 1px solid #fff;
    border-bottom: 1px solid #fff;
    -moz-box-sizing: border-box;
    box-sizing: border-box;/*отменяем блочную модель*/
    zoom:expression(
        runtimeStyle.zoom = '1',
        runtimeStyle.width=parentNode.clientWidth-parseInt(currentStyle.borderLeftWidth)+'px'
    );
}

Эмуляция after и before и контента в них

Задает + и - как элементы after и before

.box{
    zoom:expression(
        runtimeStyle.zoom = 1,
        insertAdjacentHTML('afterBegin','+'),
        insertAdjacentHTML('beforeEnd', '-')
    );
 }

Создаём элемент small, и делаем для него первого "ребёнка" и назначаем ему класс before, создаём последнего "ребёнка", и назначаем ему класс after.

.plus {
    *zoom: expression(
        this.runtimeStyle.zoom="1",    
        this.insertBefore( document.createElement("small"), this.firstChild ).className="before",
        this.appendChild( document.createElement("small") ).className="after"
    );
}

Задаём значения для элементов after и before

.plus .before{
    *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = '+');
}
.plus .after{
    *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = '-');
}

Min-width и max-width

.class { 
  min-width : 500px ; 
  width : expression ( 
    document.body.clientWidth < 500? "500px" : "auto" 
  );
}

Давайте для начала создадим тестовый стенд. 

<div class="block">
  <div class="gradient">Фильтр Shadow</div>
  <!--[if lt IE 9]><div class="shadow"></div><![endif]-->
</div>

 Забегу вперёд, мы будем применять разные фильтры для браузера IE. У меня не получилось применить несколько фильтров к одному блоку. Работала либо тень либо градиент. Поэтому я решил создать отдельный блок для тени и подключать его через условный комментарий только для ИЕ. Ну теперь можно начинать. А начнём мы с градиента.

Градиент для ИЕ

 Для включения градиента в ИЕ будем использовать его фильтр:

filter: progid:DXImageTransform.Microsoft.gradient (GradientType=0, startColorstr=#097FBA, endColorstr=#F5F9FB);

- startColorstr=#097FBA, endColorstr=#F5F9FB - начальный и конечный цвет градиента

- GradientType=0 - направление градиента (1-горизонтальный, 0-вертикальный)

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<style type="text/css">
.block {
   position: relative;
   margin: 30px 0  50px 90px;
   width: 200px;
   height: 200px;
   float: left;
}
.gradient {
    position: absolute;
    width: 200px;
    height: 200px;
    background-color: #F5F9FB;
    z-index: 1;
    text-align: center;
    line-height: 70px;
    font-size: 20px;
    color: #ffffff;
    font-family: Arial, Helvetica, sans-serif;
    font-weight: bold;
   
/*для старых браузеров*/
    -webkit-box-shadow: 5px 5px 10px 1px rgba(0,0,0, 0.5);
    -moz-box-shadow: 5px 5px 10px 1px rgba(0,0,0, 0.5);
    box-shadow: 5px 5px 10px 1px rgba(0,0,0, 0.5);
    /*для всех других браузеров*/
    background: linear-gradient(to top, #F5F9FB, #097FBA);
    
/*градиент для ие 6 7 8*/
    filter: progid:DXImageTransform.Microsoft.gradient
   (GradientType=0, startColorstr=#097FBA, endColorstr=#F5F9FB);
}
.shadow {
    width: 200px;
    height: 200px; 
}
</style>
</head>
<body>
    <div class="block">
        <div class="gradient">Фильтр Shadow</div>
        <!--[if lt IE 9]><div class="shadow"></div><![endif]-->
    </div>
</body>

Теперь градиент будет отображаться и в ИЕ 7-8. Перейдём к теням.

Тени для ИЕ

У эксплорера есть несколько фильтров для создания теней. Эти фильтры мы будем применять к блоку с классом "shadow". И так первый фильтр:

Фильтр Shadow

ms-filter:"progid:DXImageTransform.Microsoft.Shadow(color=#868383, direction=135, strength=8)"; filter:progid:DXImageTransform.Microsoft.Shadow(color=#868383, direction=135, strength=8);

- color - цвет тени
- direction - определяет направление тени в градусах с шагом 45 градусов
   0 - вверх
   45 - вверх и вправо
   90 - вправо
   135 - вниз и вправо
   180 - вниз
   225 - вниз и влево
   270 - влево
   315 - вверх и влево
- strength - определяет величину области тени в пикселях в заданном направлении 1-255

 
.shadow{
  width: 200px;
  height: 200px;
  ms-filter:"progid:DXImageTransform.Microsoft.Shadow
  (color=#868383, direction=135, strength=8)";
  filter:progid:DXImageTransform.Microsoft.Shadow
  (color=#868383, direction=135, strength=8);
}

Фильтр Drop Shadow

-ms-filter:"progid:DXImageTransform.Microsoft.DropShadow (color=#50000000, offX=8px, offY=8px)"; filter:progid:DXImageTransform.Microsoft.DropShadow (color=#50000000, offX=8px, offY=8px);

Для прозрачных пикселей
-ms-filter:"progid:DXImageTransform.Microsoft.DropShadow (color=#8000ff00, offX=8px, offY=8px positive=false)"; filter:progid:DXImageTransform.Microsoft.DropShadow (color=green, offX=8px, offY=8px, positive=false);

- color - цвет тени например #8000ff00 первые две цифры это альфа канал (прозрачность) 00-полностью прозрачный FF - полностью не прозрачный. Остальные цифры цвет RGB в шестнадцатеричной системе.
-offX - смещение тени в пикселях по оси x (положительное значение вправо отрицательное влево)
-offY - смещение тени в пикселях по оси y (положительное значение вправо отрицательное влево) positive -флаг, определяющий для каких пикселей элемента создаётся тень прозрачных или нет. По умолчанию true не прозрачные пиксели.

Фильтр Blur

Элемент с радиусом размытия 10px
-ms-filter:"progid:DXImageTransform.Microsoft.Blur(pixelRadius=10)"; filter:progid:DXImageTransform.Microsoft.Blur(pixelRadius=10);

Полупрозрачная тень с радиусом размытия 5 px -ms-filter:"progid:DXImageTransform.Microsoft.Blur(makeShadow=true, pixelRadius=5, shadowOpacity=0.5)"; filter:progid:DXImageTransform.Microsoft.Blur(makeShadow=true, pixelRadius=5, shadowOpacity=0.5);

-makeShadow - элемент отображается тенью
-pixelRadius определяет - радиус размытия
-shadowOpacity - прозрачность тени

Как отображаются тени, созданные разными фильтрами мы можем увидеть в demo примере. На мой взгляд самый оптимальный фильтр это blur c opacity. К недостаткам создания теней в ИЕ через его фильтры можно отнести несемантичность html разметки. Приходится создавать отдельный контейнер для тени. Можно конечно использовать псевдоэлементы after и befor, но у ИЕ 7 сложности с их пониманием. К ещё одному минусу можно отнести невозможность скруглить углы у контейнеров с тенью без javascript.  И вот мы переходим к вопросу о круглых уголках.

Скругление углов в ИЕ

У браузеров, отличных от ИЕ закругление углов задаётся свойством border-radius. ИЕ это свойство не понимает и не имеет фильтров для его эмуляции. Для задания скруглений в ИЕ можно использовать два варианта. Первый это canvas, а второй использование javascript библиотек. Начнём с использования canvas.

Canvas

Canvas поддерживаются у нас в html 5, а IE 7-8 html 5 не поддерживают. Для того что бы научить ИЕ понимать canvas нам нужно будет подключить js библиотеку Explorer Canvas. Скачать её можно здесь . О возможностях почитать в моём посте о js библиотеках для IE. И так подключаем библиотеку. 

<!--[if IE]><script type="text/javascript" src="/excanvas.js"></script><![endif]-->

Теперь создаём рабочий холст в html разметке

<div class="block">
   <div class="txt">Canvas and explorercanvas<br>
    (нет тени в IE)
   </div>
   <canvas id=c width="210" height="210"> </canvas>
</div>

Теперь вставляем между тегами <head> такой вот код

<script type="text/javascript">
function viewCanvas(){
var canvas = document.getElementById('c');
ctx = canvas.getContext('2d');
var gradient = ctx.createLinearGradient(0, 0, 0, canvas.height);
gradient.addColorStop(0, '#097FBA');
gradient.addColorStop(1, '#F5F9FB');
ctx.fillStyle = gradient;    
ctx.beginPath();
ctx.arc(15, 185, 15,  Math.PI, Math.PI*0.5, true); 
ctx.arc(185, 185, 15,  Math.PI*0.5, 0, true); 
ctx.arc(185, 15, 15,  0, Math.PI*1.5, true);
ctx.arc(15, 15, 15, Math.PI*1.5, Math.PI, true);         
ctx.shadowOffsetX = 5;  
ctx.shadowOffsetY = 5;  
ctx.shadowBlur = 10;  
ctx.shadowColor = "rgba(0, 0, 0, 0.5)";
ctx.fill();
}
window.onload = viewCanvas;
</script>

Не буду описывать синтаксис canvas, результаты вы можете увидеть в demo. Мы скруглили углы у блока. Минусы данного метода на мой взгляд в том, что приходится создавать отдельный блок canvas. Так же у меня не получилось отобразить в IE при помощи библиотеки  Explorer Canvas тени блока и текста.

Библиотека css3 PIE - progressive internet explorer 

На мой взгляд применение данной библиотеки самый оптимальный вариант достижения кроссбраузерности для ИЕ. Скачать библиотеку pie можно здесь . О возможностях  и подключении css3 PIE читаем в моём посте.  Подключить библиотеку можно разными способами. Я выбрал подключение с помощью javascript. Так же нам нужно будет подключить библиотеку jquery.

<script type="text/javascript" src="/jquery.js" ></script>
<script type="text/javascript" src="/PIE.js" ></script>

Применяем нашу библиотеку к блоку с css классом ".gradientPIE"

<script type="text/javascript">
$(function() {
  if (window.PIE) {
    $('.gradientPIE').each(function() {
        PIE.attach(this);
    });
  }
});
</script>

Css свойства блока будут выглядеть так:

.gradientPIE{
    position: absolute;
    width: 200px;
    height: 200px;
    background-color: #097FBA;
    z-index: 1;
    text-align: center;
    line-height: 70px;
    font-size: 20px;
    color: #ffffff;
    font-family: Arial, Helvetica, sans-serif;
    font-weight: bold;
    
    -webkit-border-radius: 10px;
    -moz-border-radius: 10px;
    -ms-border-radius: 10px;
    -o-border-radius: 10px;
    border-radius: 10px;
   
    -webkit-box-shadow: 5px 5px 10px 1px rgba(0,0,0, 0.5);
    -moz-box-shadow: 5px 5px 10px 1px rgba(0,0,0, 0.5);
    box-shadow: 5px 5px 10px 1px rgba(0,0,0, 0.5);
        
    background: linear-gradient(to top, #097FBA, #F5F9FB);
    
    background: -webkit-linear-gradient(top, #097FBA, #F5F9FB); 
    background: -moz-linear-gradient(top, #097FBA, #F5F9FB);  
    background: -o-linear-gradient(top, #097FBA, #F5F9FB);   
    background: -ms-linear-gradient(top, #097FBA, #F5F9FB);

/*градиент для PIE*/    
    -pie-background: linear-gradient(#097FBA, #F5F9FB);    
}

Скрипту нужно было только объяснить свойство градиент записью -pie-background. С помощью css3 PIE мы объяснили ИЕ что блока есть градиент, тень и скругленные углы.

Тени для текста в ИЕ

Теперь мы подошли к последнему пункту нашего поста, это создание теней для текста. Первый вариант создания тени для текста в ИЕ это использование его фильтра DropShadow. Второй вариант опять же использование javascript библиотек. Создадим в блоке textShd заголовок h3 с текстом DropShadow параграф р с текстом JsShadow. К заголовку h3 будем применять фильтр ИЕ, а к параграф js скрипт.

<div class="block">
  <div class="textShd">
    <h1>C тенью на:</h1><h3>DropShadow</h3><p>JsShadow</p>
  </div>
</div>

 DropShadow

Применяем фильтр ИЕ к h3 заголовку.

.textShd h3{
    color: #fff;
    text-shadow: 4px 4px 5px #000;
    font-family: serif;
    font-size: 30px;
    margin: 0;
    padding: 0;
    
    filter:progid:DXImageTransform.Microsoft.DropShadow
    (color="#666666", offX=4,offY=4,positive="true");
    zoom: 1;
}

Мы получили тень для текста в ИЕ, но здесь есть один нюанс. Тень получается угловатая с неровными краями. Особенно это заметно на крупных шрифтах при большом смещении тени. Это является недостатком данного метода.

Библиотека Textshadow

<script type="text/javascript"> src="/jquery.textshadow.js"</script>

Применяем к параграфу с текстом "JsShadow"

<script type="text/javascript">
$(document).ready(function(){
  $(".textShd p").textShadow();
})
</script>
.textShd p{
    color: #fff;
    font-family: serif;
    font-size: 30px;
    margin: 0;
    padding: 0;
    text-shadow: 4px 4px 3px #000;
}

При применении js библиотеки тени выглядят лучше

И так подведём итог. Моё мнение такое. Быстрее и проще обучить ИЕ скруглению углов, градиенту и теням, это использовать js библиотеки css3 PIE и textshadow. Мы добились кроссбраузерности для ie, но скорей бы старые ишаки ушли со сцены.

Поделиться:

You have no rights to post comments

Используя данный сайт, вы даете согласие на использование файлов cookie, помогающих мне сделать его удобнее для вас. Уведомление о cookie