How I can detect collision with any shape in HTML5 canvas? - javascript

I am trying to building a HTML5 canvas game so that I will need to detect collision with character with different shape.
If you have enough knowledge about this type of collision please share your knowledge

Depends on personal preference.
One of them is Distance Detection.
Check the distance between two objects(or coords of said object), and if its close enough, count it as hit.
You could also check overlap this way, which is a definite hit. Then just apply whatever physics you wanted to apply.

The HTML Canvas is only in charge of displaying your "game" through a web browser. You'll need to utilize a bit of programming logic to decide what you want to render through the canvas. As far as the collision implementation, it'll depend on what you're looking to create.
We'll assume this is a 2d plane with objects moving in all directions.
Given this assumption, one implementation might be to attach positional coordinates to each object in your game, and consistently keep track of each object coordinate with a "global" game state. You can than perform calculations on each object's position and trigger collisions between objects that meet a certain threshold.
Implementation might differ depending on what you're looking to build but this link might be useful. Hope this helps!

The correct way is to go with a physics engine. Somethng like:
https://brm.io/matter-js/
However, it might be overkill for a simple game. here are the basics for collision detection.
You know the coordinates and size of all the objects you control.
After each movement, get the perimeter coordinates of each object. Each object will have an array of points marking its perimeter.
Compare the arrays and see if the same coordinate is present in two arrays.
This is the basic. You need a lot of enhancement to this code for a practical game. But you can figure them out after this step.

Related

Object collisions HTML5 Canvas

I'm making a platformer game with HTML5 Canvas. I don't have a main character yet so i'm using a ball for now. I'm trying to make it so the ball can't go through the grass block. I'm using an list to hold the values of my map, then 2 if statements to turn the list's values into a map, so I don't know how to detect a collision between the ball and the grass ball, considering the grass blocks could be anywhere on the map.
My question is: How can I make a collision between the ball and the grass block without hard coding it, it needs to be fast, and if I need a library, please show an example of how to use it in my situation.
My code is here: https://drive.google.com/open?id=0B7OJnVpBNrkDTlA0amdzMkdrRnM
Here's a basic solution to your problem, from which you can build upon:
https://plnkr.co/edit/5c08NrVQh44hsq1BFX9X?p=preview
In summary:
I created a new multi-dimensional array called level1CanMove to provide a reference for where the ball can and can't travel.
I've used the ballLocationCol and ballLocationRow values you already had in place (but commented out), to ascertain which tiles the ball is currently over.
We then check via the new canMoveHere function whether the ball can pass over the current tile and reverse direction if not.
N.B.
If you're just undertaking this project for learning, by all means write the code for collision detection yourself. However, if not, you'll likely find it more productive, as some commenters have already suggested, to use a game engine.

How could I compare two data sets of X,Y coordinates to look for similarities?

Pretty abstract question, but I'm conducting some research on gesture-based recognition. I've managed to get the gesture to be outputted into a series of X,Y coordinates that I can view as a scatter graph:
Here's my problem; I'm unsure on how to proceed. What is the best way to compare two data sets of X,Y coordinates and give a confidence percentage on how similar they are?
I'm currently using JavaScript and would ideally like to keep using it.
Reading about handwriting recognition software it seems that the early phases such a recognising the strokes might be helpful. Decompose the gesture into a number of elements (lines or curves) then apply some matching algorithms.
There are a couple of other questions that may be had here, for example: if a we have two identical gestures but one would be much slower than the other and take ten times the time, would they be considered similar?
Anyway, for starters I would look at each moment in time at the positions of the cursor in both gestures and determine the geometrical distance between them. Then you could compute a 'deviation' number of one gesture from the other, and if the number is big, then the gestures might not be similar. This could be a starting point.

Best approach for collision detection with HTML5 and JavaScript?

I'm trying to make a little platform game with pure HTML5 and JavaScript. No frameworks.
So in order to make my character jump on top of enemies and floors/walls etc., it needs some proper collision detection algorithms.
Since I'm not usually into doing this. I really have no clue on how to approach the problem.
Should I do a re-check in every frame (it runs in 30 FPS) for all obstacles in the Canvas and see if it collides with my player, or is there a better and faster way to do so?
I even thought of making dynamic maps. So the width, height, x- and y coordinates of the obstacle are stored in an object. Would that make it faster to check if it's colliding with the player?
1. Should I re-check in every frame (it runs on 30 FPS)?
Who says it runs in 30 FPS? I found no such thing in the HTML5 specification. Closest you'll get to have anything to say about the framerate at all is to programmatically call setInterval or the newish, more preferred, requestAnimationFrame function.
However, back to the story. You should always look for collisions as much as you can. Usually, writing games on other platforms where one have a greater ability to measure CPU load, this could be one of those things you might find favorable to scale back some if the CPU has a hard time to follow suit. In JavaScript though, you're out of luck trying to implement advanced solutions like this one.
I don't think there's a shortcut here. The computer has no way of knowing what collided, how, when- and where, if you don't make that computation yourself. And yes, this is usually, if not at all times even, done just before each new frame is painted.
2. A dynamic map?
If by "map" you mean an array-like object or multidimensional array that maps coordinates to objects, then the short answer has to be no. But please do have an array of all objects on the scene. The width, height and coordinates of the object should be stored in variables in the object. Leaking these things would quickly become a burden; rendering the code complex and introduce bugs (please see separation of concerns and cohesion).
Do note that I just said "array of all objects on the scene" =) There is a subtle but most important point in this quote:
Whenever you walk through objects to determine their position and whether they have collided with someone or not. Also have a look at your viewport boundaries and determine whether the object are still "on the scene" or not. For instance, if you have a space craft simulator of some kind and a star just passed the player's viewport from one side to the other and then of the screen, and there is no way for the star to return and become visible again, then there is no reason for the star to be left behind in the system any more. He should be deleted and removed. He should definitely not be stored in an array and become part of a future collision detection with the player's avatar! Such things could dramatically slow down your game.
Bonus: Collision quick tips
Divide the screen into parts. There is no reason for you to look for a collision between two objects if one of them are on left side of the screen, and the other one is on the right side. You could split up the screen into more logical units than just left and right too.
Always strive to have a cheap computation made first. We kind of already did that in the last tip. But even if you now know that two objects just might be in collision with each other, draw two logical squares around your objects. For instance, say you have two 2D airplanes, then there is no reason for you to first look if some part of their wings collide. Draw a square around each airplane, effectively capturing their largest width and their largest height. If these two squares do not overlap, then just like in the last tip, you know they cannot be in collision with each other. But, if your first-phase cheap computation hinted that they might be in collision, pass those two airplanes to another more expensive computation to really look into the matter a bit more.
I am still working on something i wanted to make lots of divs and make them act on physics. I will share somethings that weren't obvious to me at first.
Detect collisions in data first. I was reading the x and y of boxes on screen then checking against other divs. After a week it occurred to me how stupid this was. I mean first i would assign a new value to div, then read it from div. Accessing divs is expensive. Think dom as a rendering stage.
Use webworkers if possible easy.
Use canvas if possible.
And if possible make elements carry a list of elements they should be checked against for collision.(this would be helpful in only certain cases).
I learned that interactive collisions are way more expensive. Because you have to check for changes in environment while in normal interaction you simulate what is going to happen in future, and therefore your animation would be more fluid and more cpu available.
i made something very very early stage just for fun: http://www.lastnoob.com/

How much slower is drawing to a transparent canvas and checking if point is transparent than checking if point is in a complex polygon?

This is more of a generic question to be honest, just wondering if anyone has done any sort of research on the subject.
Basically I am adding event support to a small game engine I am creating for my own personal use. I would like pixel perfect hover over 2d object event support and am just thinking of the best way of doing it. Realistically it would be faster for me personally just to invoke a draw of my objects onto a transparent canvas and checking if the mouse x y is over a transparent pixel or not since I dont have to make a set of points defining the outside of an object. This would also allow me to have holes in my object and it would still correctly know if I hovered over or not.
What I am wondering is using methods shown here: How can I determine whether a 2D Point is within a Polygon?
How much slower would my method be to the methods shown there?
Im currently still learning so its not easy for me to implement all of this and just test it myself since it would probably take me ages to get to work correctly and test the speeds.
Side note: I would still have a basic bounding box to save it from redrawing and testing every single time.
Checking if a point is in a polygon will 99.999999% of the time be vastly, vastly faster.
To be slower the polygon would need to be extremely complex.
To do the other method you need to use getImageData, and getting image data on the canvas is very slow.
Point in polygon algorithms do properly account for holes. Make sure you have one that obeys the non-zero winding number rule, because that is what canvas uses (as opposed to the even odd rule) and you may want compatibility with paths constructed in the canvas (either now or later).

HTML5 Canvas Collision Detection "globalCompositeOperation" performance

Morning,
Over the past few months I have been tinkering with the HTML5 Canvas API and have had quite a lot of fun doing so.
I've gradually created a number of small games purely for teaching myself the do's and don'ts of game development. I am at a point where I am able to carry out basic collision detection, i.e. collisions between circles and platforms (fairly simple for most out there but it felt like quite an achievement when you first get it working, and even better when you understand what is actually going on). I know pixel collision detection is not for every game purely because in many scenarios you can achieve good enough results using the methods discussed above and this method is obviously quite expensive on resources.
But I just had a brainwave (It is more than likely somebody else has thought of this and I am way down the field but I've googled it and found nothing)....so here goes....
Would it possible to use/harness the "globalCompositeOperation" feature of canvas. My initial thoughts were to set its method to "xor" and then check the all pixels on the canvas for transparency, if a pixel is found there must be a collision. Right? Obviously at this point you need to work out which objects the pixel in question is occupied by and how to react but you would have to do this for other other techniques.
Saying that is the canvas already doing this collision detection behind the scenes in order to work out when shapes are overlapping? Would it be possible to extend upon this?
Any ideas?
Gary
The canvas doesn't do this automatically (probably b/c it is still in its infancy). easeljs takes this approach for mouse enter/leave events, and it is extremely inefficient. I am using an algorithmic approach to determining bounds. I then use that to see if the mouse is inside or outside of the shape. In theory, to implement hit detection this way, all you have to do is take all the points of both shapes, and see if they are ever in the other shape. If you want to see some of my code, just let me know
However, I will say that, although your way is very inefficient, it is globally applicable to any shape.
I made a demo on codepen which does the collision detection using an off screen canvas with globalCompositeOperation set to xor as you mentioned. The code is short and simple, and should have OK performance with smallish "collision canvases".
http://codepen.io/sakri/pen/nIiBq
if you are using a Xor mode fullscreen ,the second step is to getImageData of the screen, which is a high cost step, and next step is to find out which objects were involved in the collision.
No need to benchmark : it will be too slow.
I'd suggest rather you use the 'classical' bounding box test, then a test on the inner BBOxes of objects, and only after you'd go for pixels, locally.
By inner bounding box, i mean a rectangle for which you're sure to be completely inside your object, the reddish part in this example :
So use this mixed strategy :
- do a test on the bounding boxes of your objects.
- if there's a collision in between 2 BBoxes, perform an inner bounding box test : we are sure there's a collision if the sprite's inner bboxes overlaps.
- then you keep the pixel-perfect test only for the really problematic cases, and you need only to draw both sprites on a temporary canvas that has the size of the bigger sprite. You'll be able to perform a much much faster getImageData. At this step, you know which objects are involved in the collision.
Notice that you can draw the sprites with a scale, on a smaller canvas, to get faster getImageData at the cost of a lower resolution.
Be sure to disable smoothing, and i think that already a 8X8 canvas should be enough (it depends on average sprite speed in fact. If your sprites are slow, increase the resolution).
That way the data is 8 X 8 X 4 = 256 bytes big and you can keep a good frame-rate.
Rq also that, when deciding how you compute the inner BBox, you can allow a given number of empty pixels to get into that inner BBox, trading accuracy for speed.

Categories