基于JQuery和CSS3实现仿Apple TV海报背景视觉差特效源码分享


Posted in Javascript onSeptember 21, 2015

效果展示如下:

基于JQuery和CSS3实现仿Apple TV海报背景视觉差特效源码分享

查看演示     下载源码

HTML结构

Apple TV是由苹果公司继 Airport Express 之后推出的一款高清电视机顶盒产品。如果你曾经使用过,一定会被其中的炫酷电影海报视觉差特效所吸引。

该视觉差特效的HTML结构使用一个<div>作为容器,在它里面的每一个<div>都是一个“层”。

<div class="poster">
 <div class="shine"></div>
 <div class="layer-1"></div>
 <div class="layer-2"></div>
 <div class="layer-3"></div>
 <div class="layer-4"></div>
 <div class="layer-5"></div>
</div>
<div.shine>是用于制作流光效果的图层。

CSS样式

为了使包裹元素.poster制作出3D旋转效果,它的父元素需要设置透视和transform-style。

body {
 background: linear-gradient(to bottom, #f6f7fc 0%,#d5e1e8 40%);
 transform-style: preserve-3d;
 transform: perspective(800px);
}

这里的海报大小设置为固定的320x500像素,相对于页面居中,为它制作圆角效果和一些阴影效果。

.poster {
 width: 320px;
 height: 500px;
 position: absolute;
 top: 50%; left: 50%;
 margin: -250px 0 0 -160px;
 border-radius: 5px;
 box-shadow: 0 45px 100px rgba(0, 0, 0, 0.4);
 overflow:hidden;
}

海报的居中采用的是绝对定位居中法:left和top分别为50%,然后设置margin-left和margin-top为负的宽度值和高度值。

海报中所有的“层”可以通过div[class*="layer-"]选择器来选择。所有的图层都被设置为绝对定位,背景图片不重复,background-position设置到左上角位置,背景的大小设置为100%的宽度和自动高度。

div[class*="layer-"] {
 position: absolute;
 top: -10px;
 left: -10px;
 right: -10px; 
 bottom: -10px;
 background-size: 100% auto;
 background-repeat: no-repeat;
 background-position: 0 0;
 transition:0.1s;
}

注意上面代码中的top,left,right和bottom属性的值都是-10像素。它们用于使图层的尺寸比海报的尺寸大20像素。这样做的原因是在产生视觉差效果是可以隐藏图层的边部。

最后为每一个图层设置背景图片。

.layer-1 {
 background-image: url('images/1.png');
}
.layer-2 {
 background-image: url('images/2.png');
}
.layer-3 {
 top: 0; bottom: 0;
 left: 0; right: 0;
 background-image: url('images/3.png');
}
.layer-4 {
 background-image: url('images/4.png');
}
.layer-5 {
 background-image: url('images/5.png');
}

JavaScript

该视觉差效果的原理是每次用户移动鼠标是时候,.poster的transforms: translateY、rotate和rotateY属性将根据鼠标的位置发生变化。鼠标距离左上角越远,动画可见的区域就越多。

计算的公式类似于 offsetX = 0.5 ? 鼠标位置 / 窗口的宽度。

为了给各个层不同的动画速度,这里需要在乘以一个自定义的动画速率值,这个值由HTML标签上的data-offset="number"提供。

<div data-offset="-2" class="layer-1"></div>
<div class="layer-2"></div>
<div data-offset="1" class="layer-3"></div>
<div data-offset="3" class="layer-4"></div>
<div data-offset="10" class="layer-5"></div>

data-offset的值越大,可见的动画区域就越大。

整个视觉差效果的JS代码如下:

var $poster = $('.poster'),
 $shine = $('.shine'),
 $layer = $('div[class*="layer-"]');
$(window).on('mousemove', function(e) {
 var w = $(window).width(), //窗口宽度
  h = $(window).height(), /窗口高度
  offsetX = 0.5 - e.pageX / w, //鼠标X坐标
  offsetY = 0.5 - e.pageY / h, //鼠标Y坐标
  dy = e.pageY - h / 2, //@h/2 = 海报容器中心
  dx = e.pageX - w / 2, //@w/2 = 海报容器中心
  theta = Math.atan2(dy, dx), //鼠标和海报中心的RAD角度
  angle = theta * 180 / Math.PI - 90, //转换 rad 为 degrees
  offsetPoster = $poster.data('offset'),
  transformPoster = 'translateY(' + -offsetX * offsetPoster + 'px) rotateX(' + (-offsetY * offsetPoster) + 'deg) 
            rotateY(' + (offsetX * (offsetPoster * 2)) + 'deg)'; 
 //get angle between 0-360
 if (angle < 0) {
  angle = angle + 360;
 }
 //gradient angle and opacity
 $shine.css('background', 'linear-gradient(' + angle + 'deg, rgba(255,255,255,' + e.pageY / h * .5 + ') 0%,rgba(255,255,255,0) 80%)');
 //poster transform
 $poster.css('transform', transformPoster);
 //parallax foreach layer
 $layer.each(function() {
  var $this = $(this),
   offsetLayer = $this.data('offset') || 0,
   transformLayer = 'translateX(' + offsetX * offsetLayer + 'px) translateY(' + offsetY * offsetLayer + 'px)';
  $this.css('transform', transformLayer);
 });
Javascript 相关文章推荐
jquery 简单导航实现代码
Sep 11 Javascript
利用jquery的获取JS文件中的字符串内容
Feb 14 Javascript
学习从实践开始之jQuery插件开发 菜单插件开发
May 03 Javascript
jquery弹窗插件colorbox绑定动态生成元素的方法
Jun 20 Javascript
jquery使整个div区域可以点击的方法
Jun 24 Javascript
Bootstrap每天必学之按钮
Nov 26 Javascript
常见的javascript跨域通信方法
Dec 31 Javascript
详解Angular2中的编程对象Observable
Sep 17 Javascript
原生JavaScript制作计算器
Oct 16 Javascript
微信小程序云开发如何使用云函数生成二维码
May 18 Javascript
基于ssm框架实现layui分页效果
Jul 27 Javascript
JavaScript字符串转数字的简单实现方法
Nov 27 Javascript
Java Mybatis框架入门基础教程
Sep 21 #Javascript
JS实现仿微博可关闭弹出层效果
Sep 21 #Javascript
jQuery+HTML5美女瀑布流布局实现方法
Sep 21 #Javascript
JavaScript实现网页加载进度条代码超简单
Sep 21 #Javascript
Javascript验证方法大全
Sep 21 #Javascript
JavaScript验证Email(3种方法)
Sep 21 #Javascript
基于jQuery实现多层次的手风琴效果附源码
Sep 21 #Javascript
You might like
用PHP调用数据库的存贮过程
2006/10/09 PHP
PHP制作图型计数器的例子
2006/10/09 PHP
用php获取远程图片并把它保存到本地的代码
2008/04/07 PHP
PHP开发框架kohana中处理ajax请求的例子
2014/07/14 PHP
php实现将wav文件转换成图像文件并在页面中显示的方法
2015/04/21 PHP
ThinkPHP模板标签eq if 中区分0,null,false的方法
2017/03/24 PHP
laravel5.6中的外键约束示例
2019/10/23 PHP
解决表单中第一个非隐藏的元素获得焦点的一个方案
2009/10/26 Javascript
JavaScript高级程序设计 读书笔记之八 Function类及闭包
2012/02/27 Javascript
window.parent与window.openner区别介绍
2012/04/12 Javascript
jquery实现模拟百分比进度条渐变效果代码
2015/10/29 Javascript
jQuery解析json格式数据简单实例
2016/01/22 Javascript
Linux系统中利用node.js提取Word(doc/docx)及PDF文本的内容
2017/06/17 Javascript
jqgrid实现简单的单行编辑功能
2017/09/30 Javascript
vue-cli 打包后提交到线上出现 &quot;Uncaught SyntaxError:Unexpected token&quot; 报错
2018/11/06 Javascript
fastadmin中调用js的方法
2019/05/14 Javascript
借助云开发实现小程序短信验证码的发送
2020/01/06 Javascript
JS call()及apply()方法使用实例汇总
2020/07/11 Javascript
如何使用three.js 制作一个三维的推箱子游戏
2020/07/29 Javascript
浅谈python socket函数中,send与sendall的区别与使用方法
2017/05/09 Python
python实现数据图表
2017/07/29 Python
python 定时修改数据库的示例代码
2018/04/08 Python
python sys,os,time模块的使用(包括时间格式的各种转换)
2018/04/27 Python
python基于C/S模式实现聊天室功能
2019/01/09 Python
解决Python 异常TypeError: cannot concatenate 'str' and 'int' objects
2020/04/08 Python
关于探究python中sys.argv时遇到的问题详解
2021/02/23 Python
美国体育用品在线:Modell’s Sporting Goods
2018/06/07 全球购物
自荐信要包含哪些内容
2013/11/06 职场文书
四风存在的原因分析
2014/02/11 职场文书
《燕子》教学反思
2014/02/18 职场文书
学校运动会开幕词
2016/03/03 职场文书
实用求职信模板范文
2019/05/13 职场文书
2019毕业典礼主持词!
2019/07/05 职场文书
MongoDB orm框架的注意事项及简单使用
2021/06/20 MongoDB
springboot如何初始化执行sql语句
2021/06/22 Java/Android
纯html+css实现打字效果
2021/08/02 HTML / CSS