Этот виджет может найти применение для сайта дизайнера или фотографа, которые занимаются реставрацией или обработкой изображений. Наверное, приложений можно придумать много : везде, где мы имеем две одинаковые картинки, одна из которых — «до», а вторая «после». Можно, конечно, просто выложить начальное и конечное изображение рядом. Но мне пришла в голову следующая идея (видимо, где то подсмотрел).
Мы наложим две картинки друг на друга и специальным разделителем как ширмой будем открывать то одну, то другую из картинок. Так они займут вдвое меньше места, а их сравнение будет более наглядным.
Виджета у меня пока нет, давайте его сварганим.
Для тестирования мне понадобилась картинка.
И её обработанная версия, в которой я убрал красный цвет.
Это могут быть любые картинки, важно, что они одинакового размера.
Я хочу, чтобы работало это так: я размещаю две картинки в каком то контейнере и передаю id этого контейнера некой функции, которая делает всю остальную работу, т.е. создаёт описанный выше виджет. Т.е. работала html вида:
1 2 3 4 5 6 7 |
<div id="before-after-slider"> <img src="earth-500.jpg" /> <img src="earth-500-green.jpg" /> </div> <script> build_slider('before-after-slider'); </script> |
Осталось только написать код функции build_slider(id). :)
Понятно, что функцию я заранее написал и протестировал, потому я расскажу как она работает. Функция создает вместо двух картинок три контейнера : два с картинками и один служит специальным разделителем. Потом я подцепляю обработчики мыши так, чтобы разделитесь начал выполнять свою функцию.
Для разделителя я создаю вот такие стили:
1 2 3 4 5 6 7 |
.splitter { width: 3px; background-color: #ffffff; border-radius: 3px; position: absolute; cursor: ew-resize; } |
Это будет тонкая вертикальная белая полоска. Курсор над ней будет принимать вид двойной стрелки — как будто для изменения размера по горизонтали.
А вот код функции:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 |
<script type="javascript"> function build_slider(id) { id = '#' + id; //читаем данные об изображениях var im = $(id + ' img'); var h = $(im).height(); var w = $(im).width(); var src1 = $(im).attr('src'); var src2 = $(im.get(1)).attr('src'); //заменяем картинки нашими контейнерами $(id).html('<div class="layer1"></div><div class="layer2"></div><div class="splitter"></div>'); //первый слой выполняет роль первой картинки $(id + ' .layer1').css({ width: w, height: h, backgroundImage: 'url(' + src1 + ')' }); //второй - роль второй, но она наложена //поверх первой, частично её закрывая $(id + ' .layer2').css({ position: 'absolute', marginLeft: w / 2, marginTop: -h, width: w / 2, height: h, backgroundImage: 'url(' + src2 + ')', backgroundPosition: 'right top' }); //слайдер занимает позицию на границе между картинками //изначально он делит картинки 50/50 $(id + ' .splitter').css({ height: h, marginLeft: w / 2, marginTop: -h, }) //мы зацепляемся за разделитесь при движении мыши над ним //так начинается фаза - drug-start .mouseover(function(ev) { $(id).attr('data-drag', 1); $(id).attr('data-x', ev.pageX); }); //основной контейнер принимает оставшиеся два события //при перемещении мыши мы рассчитываем новые размеры и позиции $(id).mousemove(function(ev) { if ($(this).attr('data-drag') == 1) { var newShift = String($(id + ' .splitter').css('marginLeft')); newShift = Number(newShift.substring(0, newShift.length - 2)); newShift += - $(this).attr('data-x') + ev.pageX; if (newShift < 10) { newShift = 10; $(this).attr('data-drag', 0); } if (newShift > w - 10) { newShift = w - 10; $(this).attr('data-drag', 0); } $(this).attr('data-x', ev.pageX); $(id + ' .splitter').css({ marginLeft: newShift }); $(id + ' .layer2').css({ marginLeft: newShift, width: w - newShift }); } }) //при нажатии на кнопку мыши можно остановить следование //разделителя за мышью, зафиксировав его положение .mouseup(function(ev) { $(this).attr('data-drag', 0); }); } </script> |
Следование разделителя также прекращается за 10 пикселей от краёв картинки, чтобы не потерять разделитель из виду. Для временного хранения данных я использую атрибуты основного контейнера. Осталось только показать виджет в действии.
Вуаля!
Дай Бог тебе здоровья