将动画html5画布设置为背景而不与其他元素交互?

时间:2015-11-09 05:37:55

标签: css html5 canvas background

我让画布工作,我在尝试定位它时遇到了问题。 具体来说,我想实现它们的效果如下:

html {
  background: url(back.jpg) no-repeat center center fixed;
  background-size: cover;
}

表示静态图像。基本上没有与其他元素的交互,并且关于堆叠上下文的位置尽可能低。另外,我希望将画布背景尽可能地与其余代码一起划分/分段。

通过细分,我的意思是这样的:

<body>
    <div id="backgroundContainer">
        <canvas id="myCanvas"></canvas>
    </div>
    <div id="everythingElseContainer">
        ....
    </div>
    <script src="canvasAnimation.js"></script>
</body>

或者这个:

<body>
    <div id="container">
        <canvas id="myCanvas"></canvas>
        <div id="everythingElse">
            ....
        </div>
    </div>
    <script src="canvasAnimation.js"></script>
</body>

尽量减少css冲突的可能性。

var WIDTH;
var HEIGHT;
var canvas;
var con;
var g;
var pxs = new Array();
var rint = 60;

$(document).ready(function(){
	WIDTH = window.innerWidth;
	HEIGHT = window.innerHeight;
	canvas = document.getElementById('canvas');
	$(canvas).attr('width', WIDTH).attr('height',HEIGHT);
	con = canvas.getContext('2d');
	for(var i = 0; i < 100; i++) {
		pxs[i] = new Circle();
		pxs[i].reset();
	}
	setInterval(draw,rint);
});

function draw() {
	con.clearRect(0,0,WIDTH,HEIGHT);
	for(var i = 0; i < pxs.length; i++) {
		pxs[i].fade();
		pxs[i].move();
		pxs[i].draw();
	}
}

function Circle() {
	this.s = {ttl:8000, xmax:5, ymax:2, rmax:10, rt:1, xdef:960, ydef:540, xdrift:4, ydrift: 4, random:true, blink:true};

	this.reset = function() {
		this.x = (this.s.random ? WIDTH*Math.random() : this.s.xdef);
		this.y = (this.s.random ? HEIGHT*Math.random() : this.s.ydef);
		this.r = ((this.s.rmax-1)*Math.random()) + 1;
		this.dx = (Math.random()*this.s.xmax) * (Math.random() < .5 ? -1 : 1);
		this.dy = (Math.random()*this.s.ymax) * (Math.random() < .5 ? -1 : 1);
		this.hl = (this.s.ttl/rint)*(this.r/this.s.rmax);
		this.rt = Math.random()*this.hl;
		this.s.rt = Math.random()+1;
		this.stop = Math.random()*.2+.4;
		this.s.xdrift *= Math.random() * (Math.random() < .5 ? -1 : 1);
		this.s.ydrift *= Math.random() * (Math.random() < .5 ? -1 : 1);
	}

	this.fade = function() {
		this.rt += this.s.rt;
	}

	this.draw = function() {
		if(this.s.blink && (this.rt <= 0 || this.rt >= this.hl)) this.s.rt = this.s.rt*-1;
		else if(this.rt >= this.hl) this.reset();
		var newo = 1-(this.rt/this.hl);
		con.beginPath();
		con.arc(this.x,this.y,this.r,0,Math.PI*2,true);
		con.closePath();
		var cr = this.r*newo;
		g = con.createRadialGradient(this.x,this.y,0,this.x,this.y,(cr <= 0 ? 1 : cr));
		g.addColorStop(0.0, 'rgba(255,255,255,'+newo+')');
		g.addColorStop(this.stop, 'rgba(77,101,181,'+(newo*.6)+')');
		g.addColorStop(1.0, 'rgba(77,101,181,0)');
		con.fillStyle = g;
		con.fill();
	}

	this.move = function() {
		this.x += (this.rt/this.hl)*this.dx;
		this.y += (this.rt/this.hl)*this.dy;
		if(this.x > WIDTH || this.x < 0) this.dx *= -1;
		if(this.y > HEIGHT || this.y < 0) this.dy *= -1;
	}

	this.getX = function() { return this.x; }
	this.getY = function() { return this.y; }
}
html, body, div, button, canvas, .containr {
  padding: 0;
  border: none;
  margin: 0;
}
html, body, .containr{
  height: 100%;
  width: 100%;
  background: none;
}
html, body {
  font-size: 13px;
  text-decoration: none;
  font-family: Verdana, Geneva, sans-serif !important;
}

button {
  transition: all 0.24s ease;
}

h1 {
	font-size: 4rem;
}
button {
	font-size: 5.6rem;
}

#pixie {
  position:fixed;
  z-index: 0;
  background: black;
}


.containr>div {
  background: blue;
}

.containr {
  overflow:hidden;
  color: #ffffff;
  z-index: 9;
	font-size: 256%;
	white-space: nowrap;
  display: flex;
  flex-flow: column nowrap;
  justify-content: space-around;
  align-items: center;
  align-content: center;
}


.btnz {
  margin-left: 2.4%;
  margin-right: 2.4%;
  background: #ffffff;
  background: rgba(0, 0, 0, .36);
  text-shadow: 1px 1px 3px #000;
  padding: 2rem;
}

.btnz:hover {
  background: #3cb0fd;
  text-shadow: none;
  text-decoration: none;
}


/* Outline Out */
.hvr {
  display: inline-block;
  vertical-align: middle;
  -webkit-transform: translateZ(0);
  transform: translateZ(0);
  box-shadow: 0 0 1px rgba(0, 0, 0, 0);
  -webkit-backface-visibility: hidden;
  backface-visibility: hidden;
  -moz-osx-font-smoothing: grayscale;
  position: relative;
}
.hvr:before {
  content: '';
  position: absolute;
  border: #e1e1e1 solid 5px;
  top: -4px;
  right: -4px;
  bottom: -4px;
  left: -4px;
  -webkit-transition-duration: 0.3s;
  transition-duration: 0.3s;
  -webkit-transition-property: top, right, bottom, left;
  transition-property: top, right, bottom, left;
}
.hvr:hover:before, .hvr:focus:before, .hvr:active:before {
  top: -18px;
  right: -18px;
  bottom: -18px;
  left: -18px;
  border: #ffffff solid 8px;
}
<!doctype html>
<html lang="en">
<head datetime="2015-10-31">
	<link rel="stylesheet" href="main.css">
</head>

<body>
	<div class="containr">
		<canvas id="canvas"></canvas>
		<div>
			<h1>Main Title</h1>
		</div>
		<div>
			<button class="btnz hvr">
				Button Butt
			</button>
		</div>
	</div>


	<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
	<script src="js.js"></script>
</body>
</html>

1 个答案:

答案 0 :(得分:1)

要以视觉顺序向下移动对象,请使用CSS样式z-index较小的数字将元素向下移动到其他元素下方,较高的数字会将其显示出来。有关详细信息,请参阅MDN z-index

要将元素的背景设置为画布,请使用

element.style.background= "url(" + canvas.toDataURL() + ")";

要隔离某些代码,最简单的方法是将其包装在匿名函数中并调用它。里面的一切都是孤立的。使用'use strict'指令确保您不会意外地创建全局范围变量。

普通的匿名函数什么都不做,无法使用。

function(){ console.log(42); };  // does nothing

但是如果你将它包装在()中,然后将函数调用标记添加到结尾( ),你可以像任何函数一样调用它。

(function(){ console.log(42); })(); // send the meaning of life, 
                                    // the universe, and everything 
                                    // to the console.

下面的函数包含了a,在匿名函数之外没有任何东西可以访问a

(function(){
   var a = 1; 
})();

但是你很容易忘记将var放在变量前面,使变量对整个页面可见。

(function(){
   var a = 1; 
   outThere = 2;   // Oh no this is has been placed in
                   // global scope because it is missing
                   // the var token.
})();

要停止使用'use strict'指令。

(function(){
   "use strict";   // this must be the very first line of the function
   var a = 1;   
   outThere = 2;   // this will cause the javascript to throw a 
                   // ReferenceError: outThere is not defined
})();

它会抛出一个错误并停止运行,但至少你会知道你有泄漏。

匿名函数中的所有内容都将自行管理。不再需要时自行删除。如果Javascript引擎持有内部引用,则保留在内存中。

下一个函数启动并调用它自己的函数doSomething然后退出并完全删除,包括大数组。

(function(){
    var bigArray = new Array(100000000);
    function doSomething(){
         console.log("Whats up?");
    }
    doSomething();
})();

下一个将创建一个大数组并将该数组保存在内存中10秒(lifeTime)。这是因为setTimeout为javascript引擎提供了对doSomething的内部引用。只要该引用存在,bigArray将保留(因为关闭)。在超时之后,他不再需要参考,因此处理所有相关的参考也会消失并因此消失。所有这一切都通过垃圾收集的魔力完成。 关于Clouser的信息 有关垃圾收集MDN的信息已过期,但我确信快速搜索StackOverflow会有所帮助。

(function(){
    var bigArray = new Array(100000000);
    function doSomething(){
         console.log("Big Array has had its time.");
    }
    setTimeout(doSomething,10000);
})();

将对象附加到匿名函数作用域之外的项目会将该对象中的数据公开给全局作用域。

下一个函数将属性添加到DOM元素。这对于全局范围是可见的,并且还意味着函数的生存期将与该元素存在一样长。

(function(){
    function Info(){
        ... create info ..
    }
    var element = document.getElementById("thisOutsideWorld");
    var importantPrivateInfo = new Info();
    element.keepThis = importantPrivateInfo;
})();

但是这不适用于原始类型,因为它们被复制而未被引用。这些是NumbersStringsBooleansUndefinedNull ......

因此,要通过分隔函数将背景设置为画布,请参阅以下函数

(function(){
    'use strict';
    var myCanvas =  document.createElement("canvas"); 
    myCanvas .width = 1024;
    myCanvas .height =1024;
    var ctx = canvas.getContext("2d");
    // toDo
    // draw the stuff you want.
    var el = document.getElementById("myElement");
    if(el !== null){
        el.style.background = "url("+canvas.toDataURL()+")";
    }
    // all done
})();  // once run it will delete the canvas and ctx and leave only the copied dataURL

您可能认为这会暴露画布。但它是安全的,因为画布被转换为字符串并且字符串被复制而未被引用。

如果您需要将画布保留一段时间,请使用计时器创建对匿名函数的内部引用

以下函数将创建一个画布并每秒更新一次,持续100秒。之后它将被删除并完全消失。

(function(){
    'use strict';
    var myCanvas =  document.createElement("canvas"); 
    myCanvas .width = 1024;
    myCanvas .height =1024;
    var lifeCounter = 0;
    var ctx = canvas.getContext("2d");
    // toDo
    // draw the stuff you want.
    var el = document.getElementById("myElement");
    function update(){
        // draw stuff on the canvas
        if(el !== null){
            el.style.background = "url("+canvas.toDataURL()+")";
        }
        lifeCounter += 1;
        if(lifeCounter < 100){
            setTimeout(update,1000);
        }
     }
     update(); //start the updates
    // all done
})(); 

希望这有帮助。