效果图:
代码
1.html结构
<div class="wrapper">
<audio autoplay loop></audio>
<div class="title">拖动地球远近来控制音量大小</div>
<div class="circle sun"></div>
<div class="circle moon"></div>
<div class="per"></div>
</div>
2.css
色彩模式
- RGB色彩模式:可以理解为大自然的颜色都是由红、绿、蓝三种光学颜色混合而成的。所以我们可以用RGB色彩模式来表示某种颜色。颜色最小是0最大值是255,相应位置上是255表示那种颜色最纯,是0没有那种颜色。譬如rgb(255,0,0)纯红,rgb(0,255,0)纯绿,rgb(0,0,255)纯蓝,rgb(255,255,255)就是黑了。
- 十六进制颜色(简称HEX):则是使用 # 的符号来表示十六进制,形如#RRGGBB的格式,每两位上的值就是RGB上的数字转换16进制后的值。
- HSL色彩模式:就是色调(Hue)、饱和度(Saturation)、亮度(Lightness)三个颜色通道的改变以及它们相互之间的叠加来获得各种颜色,色调(Hue)色调最大值360,饱和度和亮度有百分比表示0-100%之间。
div{
width: 100px; height: 20px;}
.red{
background-color: red}
.red_hex{
background-color: #ff0000}
.red_rgb{
background-color: rgb(255,0,0);}
.red_hsl{
background-color: hsl(0,100%,54%);}
.green_hex{
background-color:#00ff00;}
.blue_hex{
background-color: #0000ff;}
hsla模式和rgba模式与opacity的区别
其实hsla模式和rgba模式就是hsl模式和rgb模式增加一个opacity值,opacity 的Alpha值表示不透明度,取值在0到1之间。hsla模式和rgba模式与opacity的区别就是前两者不会影响子类的透明度;而opacity会影响子类的透明度,从而导致子类元素的颜色产生色差
div{
width: 100px; height: 20px;}
.red_rgb_alpha{
background-color: rgba(255,0,0,0.3);}
.red_hsl_alpha{
background-color: hsla(0,100%,54%,0.3);}
.red_hsl_opacity{
background-color:red; opacity: 0.3}
css完整代码:
* {
margin: 0;
padding: 0;
}
body {
background-color: hsl(194, 64%, 49%)
/* 色调 饱和度 亮度 */
}
.wrapper {
width: 70%;
height: 500px;
margin: 50px auto;
position: relative;
}
.title {
color: #fff;
font-size: 20px;
font-weight: bolder;
margin: 20px;
}
.circle {
width: 20%;
padding-top: 20%;
/* 内容撑起高度 */
border-radius: 50%;
position: absolute;
left: 30%;
top: 30%;
}
.sun {
background-color: #ff7;
box-shadow: 0 0 50px #ff7;
}
.moon {
left: 52%;
cursor: pointer;
box-shadow: inset 5px 5px 50px rgba(255, 255, 119, 0.3);
/* 内外阴影 阴影的X轴(可以使用负值) 阴影的Y轴(可以使用负值) 阴影模糊值(大小)阴影的颜色*/
}
.per {
position: absolute;
bottom: 10%;
width: 100%;
text-align: center;
color: #fff;
font-weight: bolder;
}
3.js
思路:
1.音频的插入
2.拖动鼠标,让地球移动
3.鼠标移动,改变背景颜色,越近颜色越深
4.鼠标移动计算两球接触的距离,改变音频音量
- 插入音乐路径
function Index(mus){
this.music = mus.music;
this.dom = {
sun: $('.sun'),
moon: $('.moon'),
audio: $('audio'),
perc: $('.per')
}
this.flag = false;//监控是否在拖拽
this.top = this.dom.moon.offset().top - $('.wrapper').offset().top;
this.init();
}
new Index({
'music':'music/summer.mp3'});
- 初始函数
Index.prototype.init = function(){
var source = $('<source src="'+this.music+'"></source>');
this.dom.audio.append(source);//加载音乐
this.bindEvent();
this.change(0);
}
- 鼠标绑定事件
Index.prototype.bindEvent = function(){
//拖拽 mousedown-->mousemove-->mouseup
var self = this;
var moon = self.dom.moon;
var disX;
moon.on('mousedown',function(e){
//鼠标落下
self.flag = true;
disX = e.clientX - moon.offset().left;//鼠标距元素左边距离
});
moon.on('mousemove',function(e){
//鼠标移动
if(!self.flag){
return;
}
var left = e.clientX - disX - $('.wrapper').offset().left;//获得当前鼠标距离wrapper的left
moon.css({
'left': left + 'px',
'top': self.top + 'px'
})
self.getVoice();
})
moon.on('mouseup',function(e){
//鼠标抬起
self.flag = false;
})
}
- 计算球移动的距离
Index.prototype.getVoice = function(){
var self = this;
var d = parseInt(self.dom.moon.css('width'));
var per,
moonL = self.dom.moon.offset().left;
moonR = moonL + d;
sunL = self.dom.sun.offset().left;
sunR = sunL + d;
//两球没有接触
if(sunL > moonR || moonL > sunR){
per = 0;
} else{
//moon在sun右边
if(sunL < moonL){
per = (sunR - moonL)/d;
//moon在sun左边
}else if(moonR >=sunL){
per = (moonR - sunL)/d;
}
}
self.change(per);
}
- 改变音乐的音量
Index.prototype.change = function(per){
var self = this;
self.dom.audio[0].volume = per; // 设置音频音量
self.dom.perc.html((per*100).toPrecision(4) + '%');//取4位小数
self.dom.moon.css({
//月亮颜色的变化
'background': 'hsl(194,56%,'+(1-per)*60 +'%)'
})
$('body').css({
//背景颜色的变化
'background': 'hsl(' + (194 + Math.floor(166*per)) + ",66%,"+(1-per)*50+'%)'
})
}