我经历了很多有描述的 Stack Overflow 问题,但我发现它们非常令人困惑。我想要的是一个简单的解释,请不要引用链接。
我完全糊涂了,完全混淆了:
我做了大量的研究,但我发现它们非常复杂。
有什么简单的解释吗??
最佳答案
你很幸运。有一个非常简单的解释:
第一步:创建一个对象
说你想圈:
var circle = {};
第二步:给它一些属性
可以绘制一个圆,所以让我们创建一个名为
draw
的属性:circle.draw = function () {
// drawing logic
};
因此,我们有一个名为
draw
的方法属于对象 circle
。第三步:扩展一个对象
现在我想要一个球,球有点像一个圆圈。所以让我们扩展
circle
来创建一个球:var ball = Object.create(circle);
circle
并使用它来创建一个名为 ball
的新对象。 ball
现在具有 circle
的所有属性。所以我们可以调用 ball.draw
。 circle
是 ball
的原型(prototype)。 第四步:给它一些属性
每个球都有一个
radius
,所以让我们给我们一个:ball.radius = 5;
第五步:创建一个构造函数
这里有问题。每次我想创建一个新球时,我都会扩展
circle
并手动定义球的 radius
。相反,我想要一个函数来创建球并给它一个半径。这个函数称为构造函数:function createBall(radius) {
var ball = Object.create(circle);
ball.radius = radius;
return ball;
}
var baseball = createBall(5);
var basketball = createBall(10);
baseball.draw();
basketball.draw();
这就是您需要了解的有关原型(prototype)、对象和构造函数的全部内容。
当然还有很多解释,但对于一个 StackOverflow 答案来说太多了。我写了一篇关于它的博客文章,我不打算在这里重写同样的东西。你应该阅读我的博客。值得:http://aaditmshah.github.io/why-prototypal-inheritance-matters
编辑: 当然,我会解释代码中发生的事情:http://cssdeck.com/labs/4ksohwya
首先,向下滚动到最后:
window.addEventListener(
'load',
init(null),
false);
当页面加载它执行
init
:function init(images) {
canvas= document.getElementById('s');
ctx= canvas.getContext('2d');
canvas.width= window.innerWidth;
canvas.height=window.innerHeight;
garden= new Garden();
garden.initialize(canvas.width, canvas.height, 300);
lerp(0,2000);
time= new Date().getTime();
interval = setInterval(_doit, 30);
}
init
函数创建 Garden
( garden = new Garden();
) 的一个实例并执行 initialize
的 garden
方法。它还以 30 毫秒的间隔调用 _doit
函数。initialize : function(width, height, size) {
this.width= width;
this.height= height;
this.grass= [];
for(var i=0; i<size; i++ ) {
var g= new Grass();
g.initialize(
width,
height,
50, // min grass height
height*2/3, // max grass height
20, // grass max initial random angle
40 // max random angle for animation
);
this.grass.push(g);
}
this.stars= [];
for( i=0; i<this.num_stars; i++ ) {
this.stars.push( Math.floor( Math.random()*(width-10)+5 ) );
this.stars.push( Math.floor( Math.random()*(height-10)+5 ) );
}
},
initialize
的 garden
方法然后创建 Grass
的一些实例,调用它们的 initialize
方法并将它们存储在一个数组中。function _doit() {
ctx.fillStyle= gradient;
ctx.fillRect(0,0,canvas.width,canvas.height);
var ntime= new Date().getTime();
var elapsed= ntime-time;
garden.paint( ctx, elapsed );
// lerp.
if ( elapsed>nextLerpTime ) {
lerpindex= Math.floor((elapsed-nextLerpTime)/nextLerpTime);
if ( (elapsed-nextLerpTime)%nextLerpTime<lerpTime ) {
lerp( (elapsed-nextLerpTime)%nextLerpTime, lerpTime );
}
}
}
_doit
函数调用 paint
的 garden
函数, paint
的 garden
函数调用每个草的 paint
函数。所以这里有两个构造函数:
Grass
Garden
下面是两个原型(prototype):
Grass.prototype
Garden.prototype
在
init
函数中,我们创建了 Garden
的单个实例(这是一个对象):var garden= new Garden();
在
initialize
的 garden
方法中,我们创建了 Grass
的多个实例:var g= new Grass();
就是这样。
关于Javascript 原型(prototype)、对象、构造函数??我很困惑,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16835451/