<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>互动星空</title><style>
html,body {margin:0;overflow:hidden;width:100%;height:100%;cursor:none;background:black;background:linear-gradient(to bottom,#000000 0%,#5788fe 100%);
}
.filter {width:100%;height:100%;position:absolute;top:0;left:0;background:#fe5757;animation:colorChange 30s ease-in-out infinite;animation-fill-mode:both;mix-blend-mode:overlay;
}
@keyframes colorChange {0%,100% {opacity:0;
}
50% {opacity:.9;
}
}.landscape {position:absolute;bottom:0px;left:0;width:100%;height:100%;
background-image:url('http://www.jq22.com/css/img/xkbg.png');background-size:1000px 250px;background-repeat:repeat-x;background-position:center bottom;
}
</style>
</head>
<body><div class="landscape"></div>
<div class="filter"></div>
<canvas id="canvas"></canvas><script>
function Star(id, x, y){this.id = id;this.x = x;this.y = y;this.r = Math.floor(Math.random()*2)+1;var alpha = (Math.floor(Math.random()*10)+1)/10/2;this.color = "rgba(255,255,255,"+alpha+")";
}Star.prototype.draw = function() {ctx.fillStyle = this.color;ctx.shadowBlur = this.r * 2;ctx.beginPath();ctx.arc(this.x, this.y, this.r, 0, 2 * Math.PI, false);ctx.closePath();ctx.fill();
}Star.prototype.move = function() {this.y -= .15;if (this.y <= -10) this.y = HEIGHT + 10;this.draw();
}Star.prototype.die = function() {stars[this.id] = null;delete stars[this.id];
}function Dot(id, x, y, r) {this.id = id;this.x = x;this.y = y;this.r = Math.floor(Math.random()*5)+1;this.maxLinks = 2;this.speed = .5;this.a = .5;this.aReduction = .005;this.color = "rgba(255,255,255,"+this.a+")";this.linkColor = "rgba(255,255,255,"+this.a/4+")";this.dir = Math.floor(Math.random()*140)+200;
}Dot.prototype.draw = function() {ctx.fillStyle = this.color;ctx.shadowBlur = this.r * 2;ctx.beginPath();ctx.arc(this.x, this.y, this.r, 0, 2 * Math.PI, false);ctx.closePath();ctx.fill();
}Dot.prototype.link = function() {if (this.id == 0) return;var previousDot1 = getPreviousDot(this.id, 1);var previousDot2 = getPreviousDot(this.id, 2);var previousDot3 = getPreviousDot(this.id, 3);if (!previousDot1) return;ctx.strokeStyle = this.linkColor;ctx.moveTo(previousDot1.x, previousDot1.y);ctx.beginPath();ctx.lineTo(this.x, this.y);if (previousDot2 != false) ctx.lineTo(previousDot2.x, previousDot2.y);if (previousDot3 != false) ctx.lineTo(previousDot3.x, previousDot3.y);ctx.stroke();ctx.closePath();
}function getPreviousDot(id, stepback) {if (id == 0 || id - stepback < 0) return false;if (typeof dots[id - stepback] != "undefined") return dots[id - stepback];else return false;
}Dot.prototype.move = function() {this.a -= this.aReduction;if (this.a <= 0) {this.die();return}this.color = "rgba(255,255,255,"+this.a+")";this.linkColor = "rgba(255,255,255,"+this.a/4+")";this.x = this.x + Math.cos(degToRad(this.dir))*this.speed,this.y = this.y + Math.sin(degToRad(this.dir))*this.speed;this.draw();this.link();
}Dot.prototype.die = function() {dots[this.id] = null;delete dots[this.id];
}var canvas = document.getElementById('canvas'),ctx = canvas.getContext('2d'),WIDTH,HEIGHT,mouseMoving = false,mouseMoveChecker,mouseX,mouseY,stars = [],initStarsPopulation = 80,dots = [],dotsMinDist = 2,maxDistFromCursor = 50;setCanvasSize();
init();function setCanvasSize() {WIDTH = document.documentElement.clientWidth,HEIGHT = document.documentElement.clientHeight; canvas.setAttribute("width", WIDTH);canvas.setAttribute("height", HEIGHT);
}function init() {ctx.strokeStyle = "white";ctx.shadowColor = "white";for (var i = 0; i < initStarsPopulation; i++) {stars[i] = new Star(i, Math.floor(Math.random()*WIDTH), Math.floor(Math.random()*HEIGHT));}ctx.shadowBlur = 0;animate();
}function animate() {ctx.clearRect(0, 0, WIDTH, HEIGHT);for (var i in stars) {stars[i].move();}for (var i in dots) {dots[i].move();}drawIfMouseMoving();requestAnimationFrame(animate);
}window.onmousemove = function(e){mouseMoving = true;mouseX = e.clientX;mouseY = e.clientY;clearInterval(mouseMoveChecker);mouseMoveChecker = setTimeout(function() {mouseMoving = false;}, 100);
}function drawIfMouseMoving(){if (!mouseMoving) return;if (dots.length == 0) {dots[0] = new Dot(0, mouseX, mouseY);dots[0].draw();return;}var previousDot = getPreviousDot(dots.length, 1);var prevX = previousDot.x; var prevY = previousDot.y; var diffX = Math.abs(prevX - mouseX);var diffY = Math.abs(prevY - mouseY);if (diffX < dotsMinDist || diffY < dotsMinDist) return;var xVariation = Math.random() > .5 ? -1 : 1;xVariation = xVariation*Math.floor(Math.random()*maxDistFromCursor)+1;var yVariation = Math.random() > .5 ? -1 : 1;yVariation = yVariation*Math.floor(Math.random()*maxDistFromCursor)+1;dots[dots.length] = new Dot(dots.length, mouseX+xVariation, mouseY+yVariation);dots[dots.length-1].draw();dots[dots.length-1].link();
}
function degToRad(deg) {return deg * (Math.PI / 180);
}
</script></body>
</html>