Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/398.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript Can';不能从上下文对象继承吗?_Javascript_Inheritance_Html5 Canvas - Fatal编程技术网

Javascript Can';不能从上下文对象继承吗?

Javascript Can';不能从上下文对象继承吗?,javascript,inheritance,html5-canvas,Javascript,Inheritance,Html5 Canvas,我试图创建一个从上下文对象继承的对象。但是从我继承的对象调用函数时,浏览器(Chrome)会声明未捕获的TypeError:invalical invocation。以下是基本代码: 为什么会失败 变通办法 我编写了一个makeForwardingObject()函数,它实现了我想要的功能。可以找到它 //makeForwardingObject(对象、函数、属性) // //obj—转发到的对象 //funcs-要转发到的不可枚举函数成员名称数组 //attribs-要转发到的不可枚举属性数

我试图创建一个从上下文对象继承的对象。但是从我继承的对象调用函数时,浏览器(Chrome)会声明未捕获的TypeError:invalical invocation。以下是基本代码:

为什么会失败

变通办法 我编写了一个
makeForwardingObject()
函数,它实现了我想要的功能。可以找到它

//makeForwardingObject(对象、函数、属性)
//
//obj—转发到的对象
//funcs-要转发到的不可枚举函数成员名称数组
//attribs-要转发到的不可枚举属性数组
//
//生成转发所有函数调用和属性的转发对象
//对转发对象的请求。通过这种方式,原始对象是
//直接执行,而您可以删除或修改您的
//对象而不干扰原始对象。
//
//使用成员始终可以访问转发到的对象
//函数applyParent()、callParent()、setParentAttrib()和
//getParentAttrib()。
//
//如果func或attrib在对象中是可枚举的,则不会添加它们
//第二次。
函数makeForwardingObject(对象、函数、属性)
{
var={};
对象。定义属性{
_:{value:obj},
//与obj.apply()类似,只是它适用于转发到的对象。
applyParent:{value:函数applyParent(func,args)
{
返回此.[func].apply(此.z,args);
}},
//与obj.call()类似,只是它适用于转发到的对象。
callParent:{值:函数callParent(func)
{
//FF至少不理解参数。slice(),
//参数.splice()或参数.shift().WTF?!?!
var args=[];

对于(i=1;i一个肤浅的答案是因为无法构造画布渲染上下文。使用
CanvasRenderingContext2d()
函数(与DOM中的许多其他构造函数一样)将抛出
类型错误:“非法构造函数”
,因为它们只能通过工厂函数的一种特定方式创建。在本例中,画布的
.getContext()
方法

尽管使用RenderingContext2d作为原型创建了一个新对象,但通过使用

ctx2=Object.create(CanvasRenderingContext2D.prototype);

为您提供一个完全空白的无状态(且无用)呈现上下文对象,它实际上抛出与克隆上下文相同的异常。它甚至没有指定画布

这不起作用的原因是,您只继承了对RenderingContext原型的公共方法的引用,而在您的克隆中,有一个对通过原型链创建它的上下文的所有状态的引用,但除此之外,它是一个空心体。没有私有
var
和私有声明CanvasRenderingContext
构造函数中声明的ode>函数通过原型继承

如果你好奇,你可以自己写这种东西

function nonConstructable(factoryVar){
    if(arguments.callee.caller !== Factory){
        throw TypeError("Invalid constructor");
    }
    var privateVar = privateMethod();
    privateVar+=factoryVar;
    this.publicVar= privateVar;

    function privateMethod(){
        return 123;
    }
}
function Factory(){
    var privateFactoryVar = 321;
    return new nonConstructable(privateFactoryVar );
}
您可以看到这两个对象是以这种方式链接的,您在
非结构化
构造函数中执行操作的唯一方法是通过特定的
工厂
构造它


做更多的研究,
CanvasRenderingContext2D
WebGLRenderingContext
似乎是上下文的有效构造函数,它们可以渲染到任何画布,并且都应该在工作线程中工作。我无法找出实现的当前状态,似乎人们很复杂Tly两年前因为某种原因停止了关于它的写作。

一些对象坚持认为
this
的值是特定类型对象的实际实例。
window.requestAnimationFrame
函数也是这样。这很烦人。我想扩展这个对象:-(是否有任何文档说明了这一点?是否有一种无需编写所有函数并将调用转发到上下文对象的解决方法?上下文对象的非函数属性无论如何都会遇到问题。当您尝试在子类上设置它们时,属性将始终在本地设置。)d不在父级上。@Pointy.+1到你的最后一条评论。完全同意你关于子类化的警告。也许更保守的做法是封装和扩展而不是继承。是的,你可以用代码委托给所有函数属性,然后用代码为可设置属性使用setter定义。把它放在github上而且出名:)很有趣。我确实找到了一款可以在上面成功运行我的原始代码的浏览器,名为Dolphin。所以,尽管它是这样的,但也不一定非得如此。哇,你做了一些认真的研究。另外,感谢你的灵感:)在完成一点工作后,我将在几个小时后回到这里。但是,@Pointy是正确的,继承时属性不会正确分配。它将在派生对象中设置,除非原型中有setter?
ctx2=Object.create(CanvasRenderingContext2D.prototype);
ctx2=Object.create(ctx.constructor.prototype);
function nonConstructable(factoryVar){
    if(arguments.callee.caller !== Factory){
        throw TypeError("Invalid constructor");
    }
    var privateVar = privateMethod();
    privateVar+=factoryVar;
    this.publicVar= privateVar;

    function privateMethod(){
        return 123;
    }
}
function Factory(){
    var privateFactoryVar = 321;
    return new nonConstructable(privateFactoryVar );
}