我正在测试Raphael javascript库,我会遇到一个小问题。我在画布上画了四个形状。然后,我通过单击允许对象成为当前选定的对象。然后我添加一个事件处理程序,监听按下删除键。这工作正常但我似乎无法调用函数。下面是用来说明我的问题的代码。
这是一个代表画布上每个cirlces的类:
var Shape = new Class({
initialize: function(x, y, color)
{
this.shape = paper.circle(x, y, 25);
this.shape.attr("fill", color);
this.shape.click(function()
{
if(selectedObj == null)
{
selectedObj = this;
selectedObj.attr({'stroke':'orange', 'stroke-width':'5'});
}
else if(selectedObj != this)
{
selectedObj.attr({'stroke':'orange', 'stroke-width':'0'});
selectedObj = this;
selectedObj.attr({'stroke':'orange', 'stroke-width':'5'});
}
else if(selectedObj == this)
{
selectedObj.attr({'stroke':'orange', 'stroke-width':'0'});
selectedObj = null;
}
});
},
deleteThis: function()
{
alert("Inside The deleteThis() Function.");
}
});
这会创建一个形状,单击它时会执行以下操作:
selectedObj
为空,则点击的形状将设置为selectedObj
,并在形状周围绘制一个小的彩色边框。selectedObj
不是单击的形状,则采用先前所选对象的小边框,然后将新单击的形状设置为当前选定的项目。然后我将四个形状推到画布上:
objShapes.push(new Shape(50, 50, "red"));
objShapes.push(new Shape(250, 50, "blue"));
objShapes.push(new Shape(50, 250, "yellow"));
objShapes.push(new Shape(250, 250, "green"));
现在我可以成功选择和取消选择画布上的对象,我需要能够调用所选对象的功能。要触发我正在使用键盘的功能。以下代码是我使用的:
$(document).keydown(function(event)
{
if(event.keyCode == 46)
{
if(selectedObj == null)
{
alert("nothing to delete");
}
else
{
alert("Deleting " + selectedObj.attr('fill') + " Circle.");
selectedObj.deleteThis();
}
}
});
只有部分事件处理程序可以正常工作。当我点击删除键并且没有选择任何内容时,警报窗口告诉我没有选择删除任何内容,但是,当我选择了一个对象并点击删除键时,会出现警报并告诉我我要删除的是什么圈子但是然后它无法调用deleteThis()
函数。我不明白为什么它会调用.attr()
函数而不调用deleteThis()
函数。
无法调用此功能的原因是什么?
答案 0 :(得分:1)
问题是selectedObj
引用了内部shape
变量,而不是类的对象。您可以使它引用对象本身(请参阅下面的代码;基本上将对象缓存在变量中,通常称为self
或that
,然后在闭包内使用它作为您要存储的对象) 。然后引用形状selectedObj.shape
而不仅仅是selectedObj
。这种混淆是由于您的类名为Shape
且,您有一个名为shape
的成员变量。也许可以考虑改变这些名称中的一个或另一个来避免这种混淆。
此外,您应该使用带有javascript控制台的调试器。如果你是,你会看到一条错误消息,例如“deleteThis
未在对象上定义”,这可以帮助你跟踪它。
无论如何,这是具有上述变化的代码:
var Shape = new Class({
initialize: function(x, y, color)
{
// To keep track of the object itself
var self = this;
this.shape = paper.circle(x, y, 25);
this.shape.attr("fill", color);
this.shape.click(function()
{
if(selectedObj == null)
{
selectedObj = self; // Assign the object, not the shape
selectedObj.shape.attr({'stroke':'orange', 'stroke-width':'5'});
}
else if(selectedObj != self) // Compare the object, not the shape
{
selectedObj.shape.attr({'stroke':'orange', 'stroke-width':'0'});
selectedObj = this; // Assign the object, not the shape
selectedObj.shape.attr({'stroke':'orange', 'stroke-width':'5'});
}
else if(selectedObj == self) // Compare the object, not the shape
{
selectedObj.shape.attr({'stroke':'orange', 'stroke-width':'0'});
selectedObj = null;
}
});
},
deleteThis: function()
{
alert("Inside The deleteThis() Function.");
}
});
然后在另一部分进行相同的调整:
$(document).keydown(function(event)
{
if(event.keyCode == 46)
{
if(selectedObj == null)
{
alert("nothing to delete");
}
else
{
alert("Deleting " + selectedObj.shape.attr('fill') + " Circle."); // Reference the shape here
selectedObj.deleteThis(); // This is the object now
}
}
});