I am testing out the Raphael javascript library and would i’m experiencing a small problem. I am drawing four shapes onto a canvas. I am then allowing an object to be the currently selected object via clicking. I then add an event handler listening for the press of the delete key. This works fine but i dont seem to be able to call a function. Below is the code to illustrate my problem.
This is a class that represents each of the cirlces on the canvas:
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.");
}
});
This creates a shape and the when clicked it does the following:
- If the
selectedObjis null, the shape that was clicked is set to theselectedObjand draws a small orangle colored rim around the shape. - If the
selectedObjis not the clicked shape, it takes the small border of the previously selected object and then sets the newly clicked shape as the currently selected item. - If the shape is the selected object, when clicked again, it deselects it.
I then push four shapes onto the canvas:
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"));
Now that i can select and deselect an object on the canvas successfully, i need to be able to call functions of the selected object. To trigger the function i am using the keyboard. The following code is what i use:
$(document).keydown(function(event)
{
if(event.keyCode == 46)
{
if(selectedObj == null)
{
alert("nothing to delete");
}
else
{
alert("Deleting " + selectedObj.attr('fill') + " Circle.");
selectedObj.deleteThis();
}
}
});
Only part of the event handler work. When i hit the delete key and nothing is selected, an alert windows tells me nothing is selected to delete, However, when i have selected an object and hit the delete key, an alert does come up and tells me what circle i am deleting but it then fails to call the deleteThis() function. I dont understand why it will call the .attr() function but not the deleteThis() function.
What is the reason for not being able to call the function?
The problem is
selectedObjis referencing the internalshapevariable, not the object of your class. You can make it reference the object itself (see the code below; basically cache the object in a variable, typically calledselforthat, and then use it inside the closure as the object you are storing). Then to reference the shape doselectedObj.shapeinstead of justselectedObj. The confusion is caused by the fact that your class is namedShapeand you have a member variable namedshape. Perhaps consider changing one or the other of these names to avoid that confusion.Also, you should be using a debugger with a javascript console. If you were, you’d see an error message, something like “
deleteThisis not defined on object”, that would have helped you track this down.Anyway, here’s the code with the above change:
And then make the same adjustment in the other part: