How can I move this object with the arrow keys in Javascript? - javascript

I made an object out of a div in html and CSS to make a player for my game I am making and I can't get the player to move when I press the arrow keys. Does anyone know what is wrong with my code?
Here is the Javascript:
var player = document.getElementById("player");
var velocity = 5;
let player = {
height:20,
width:20,
x:200,
y:200
}
document.addEventListener("keydown", function(event){
if(event.keyCode === 37){
player.x -= velocity:
else if(event.keyCode ===38){
player.y -=velocity;
}
});
What is wrong?

Moving a div using simple Javascript just adding switch on keydown event on document and then customzing the css of div (player) top-left
var player = $('#player');
var velocity = 5;
$(document).keydown(function(e) {
switch (e.which) {
case 37:
player.css('left', player.offset().left - velocity);
break;
case 38:
player.css('top', player.offset().top - velocity);
break;
case 39:
player.css('left', player.offset().left + velocity);
break;
case 40:
player.css('top', player.offset().top + velocity);
break;
}
})
#player {
background: #ccc;
height: 50px;
width: 50px;
position: absolute;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<html>
<body>
<div id="player"></div>
</body>
</html>

With an addition to Ibnelaiq's answer, here's a way to make sure the players can move better -
var key = [];
function keys(db, e) {
var code = e.which || e.keyCode;
if (db == false && key.includes(code) === false) {
key.push(code);
} else if (db === true) {
key.splice(key.indexOf(code));
}
}
setInterval(() => {
console.log(key);
}, 30);
document.getElementsByClassName('game')[0].getContext('2d').fillText('Click here and press keys', 10, 10);
.game {
background-color: #f1f1f1;
outline: none;
border: 1px solid black;
}
<canvas class='game' tabindex='1' width='400px' height='290px' onkeydown='keys(false, event)' onkeyup='keys(true, event)'>
What this does:
<canvas> (not limited to <canvas> though) waits for keydown and adds event.keycode or event.which to the array. It also waits for keyup, and removes whatever event.keycode or event.which was released from the array.
The setInterval is just there to log the array into the console. The last line in the code is there to write text into <canvas>.
Of course, you can add his switch statement into the setInterval, but in there only.

Related

animating a cube with javascript

I am trying to animate this cube in Javascript.When I press a key it should move(or jump).However I am simply trying if my code works with the left key and it doesn’t.Any ideas?
this is my css (don’t look at the position or other details I just want to know what’s wrong with javascript)
.cuby {
height:40px;
width:40px;
background-color: coral;
position: absolute;
top:50%;
left:40px;
}
and this is javascript(I am not an expert in this language so if you see some redundant code or something that can be improved feel free to point it out).Probably the issus lies in the requestanimationframe but it’s just a huntch.
var cuby = document.querySelector(".cuby");
var rect = cuby.getBoundingClientRect();
var posx,posy,velx,vely, jumping;
for (key in rect){
if (key=="x"){
posx = rect[key];
}
if (key =="y"){
posy = rect[key];
}
};
cuby ={
x: posx,
y:posy,
velx:0,
vely:0,
jumping :false
};
var controller={
left:false,
right: false,
up: false,
keyListener :function(event){
var keystate = (event.type == "keydown")?true:false;
switch (event.keycode){
case 37:// left key
controller.left = key_state;
break;
case 38:// up key
controller.up = key_state;
break;
case 39:// right key
controller.right = key_state;
break;
}
}
};
loop = function(){
if(controller.left==true){
cuby.velx -= 0.5;
}
cuby.x += cuby.velx;
window.requestAnimationFrame(loop);
};
window.addEventListener("keydown", controller.keyListener);
window.addEventListener("keyup", controller.keyListener);
window.requestAnimationFrame(loop);
you are just updating cube object's x position .
you must modify position of the dom element in order to achieve animation.
try this in loop function
loop = function(){
if(controller.left==true){
cuby.velx -= 0.5;
}
cuby.x += cuby.velx;
document.querySelector(".cuby").style.left=cuby.x+"px";
window.requestAnimationFrame(loop);
};
that must fix it ! let me know if it doesnt.
Firstly, your switch condition does not trigger as it is not event.keycode but event.keyCode.
Secondly you are not updating your element on dom, you are just changing values inside a variable which you have reassigned to store some properties.
Please take a look at my code and see if it works for you.
var cuby = document.querySelector(".cuby");
var rect = cuby.getBoundingClientRect();
var posx,posy,velx,vely, jumping;
for (key in rect){
if (key=="x"){
posx = rect[key];
}
if (key =="y"){
posy = rect[key];
}
};
var cubyprops ={
x: posx,
y:posy,
velx:0,
vely:0,
jumping :false
};
var controller={
left:false,
right: false,
up: false,
keyListener :function(event){
var keystate = (event.type == "keydown") ? true : false;
switch (event.keyCode){
case 37:// left key
{
controller.left = keystate;
}
break;
case 38:// up key
controller.up = keystate;
break;
case 39:// right key
controller.right = keystate;
break;
}
}
};
loop = function(){
if(controller.left==true){
cubyprops.velx += 0.5;
}
cubyprops.x += cubyprops.velx;
cuby.style.left=cubyprops.x+"px";
window.requestAnimationFrame(loop);
};
window.addEventListener("keydown", controller.keyListener);
window.addEventListener("keyup", controller.keyListener);
window.requestAnimationFrame(loop);

circle changes position suddenly with a or w movement on the first click

I have a circle that I want to move with WASD. So far I've got it to work but the first A or W movement changes the circle position suddenly instead of smoothly (you'll see what I mean in the jsfiddle). When I press D (or S) instead of A it launches the circle into nowhere. After 1 press of both A and W it works as intended. I would need someone who can fix the sudden movement for it to become smoother, thanks.
note: Try to keep it as simple as possible (if you can do that), so I can understand it with minor difficulty.
https://jsfiddle.net/CarelessInternet/vkau9085/ (ignore the colors)
HTML code:
<html>
<body>
<div id="circle"></div>
</body>
</html>
Some of the JS Code (please see jsfiddle for all of the code):
var up = false,
down = false,
left = false,
right = false,
x = document.getElementById("circle").style.left,
y = document.getElementById("circle").style.top,
div = document.getElementById("circle");
document.addEventListener('keydown', press);
function press(e) {
if (e.which == 87) {
up = true;
} else if (e.which == 65) {
left = true;
} else if (e.which == 83) {
down = true;
} else if (e.which == 68) {
right = true;
}
}
document.addEventListener('keyup', release);
function release(i) {
if (i.which == 87) {
up = false;
} else if (i.which == 65) {
left = false;
} else if (i.which == 83) {
down = false;
} else if (i.which == 68) {
right = false;
}
}
Some of the CSS Code:
#circle {
width: 100px;
height: 100px;
border-radius: 50%;
border: 5px solid white;
background-color: black;
position: fixed;
left: 220px;
top: 125px;
overflow: auto;
}
Try console logging the values of x and y immediately after you declare them, and you'll see the problem: they are not numbers. They are empty strings, which when coerced into numbers are converted to 0. So your intial x - 5, for instance, returns -5. That's because HTMLElement.style only gives you the inline style values, not the values computed from a CSS style sheet.
To get the computed style, you'd use window.getComputedStyle; this still returns a string such as "220px", so you then need to convert to a number with parseFloat:
var computedStyle = window.getComputedStyle(document.getElementById("circle")),
x = parseFloat(computedStyle.left),
y = parseFloat(computedStyle.top);

JS Canvas: lineTo()

I am new to Javascript!
How do I assign a variable to the current xy coordinates, so I can use relative positions to draw lines? Trying to do etch-a-sketch with keyboard. Up, down, left, right arrow keys... with JS, CSS, and HTML.
Thanks!
window.addEventListener("keydown", keyd);
function keyd(event) {
var etchMain = document.getElementById('etchMain');
var etchContext = etchMain.getContext('2d');
var key = event.keyCode;
**var etchContextPositionX;
var etchContextPositionY;**
if (key == 37) {
// left arrow
if (etchMain.toDataURL() == document.getElementById('blank').toDataURL()) {
etchContext.beginPath();
etchContext.moveTo(etchMain.width / 2, etchMain.height / 2);
// arrow specific drawing goes here
}
else {
}
}
if (key == 38) {
// up arrow
if (etchMain.toDataURL() == document.getElementById('blank').toDataURL()) {
etchContext.beginPath();
etchContext.moveTo(etchMain.width / 2, etchMain.height / 2);
// arrow specific drawing goes here
}
else {
}
}
if (key == 39) {
// right arrow
if (etchMain.toDataURL() == document.getElementById('blank').toDataURL()) {
etchContext.beginPath();
etchContext.moveTo(etchMain.width / 2, etchMain.height / 2);
// arrow specific drawing goes here
}
else {
}
}
if (key == 39) {
// down arrow
if (etchMain.toDataURL() == document.getElementById('blank').toDataURL()) {
etchContext.beginPath();
etchContext.moveTo(etchMain.width / 2, etchMain.height / 2);
// arrow specific drawing goes here
}
else {
}
}
}
function clearCanvas() {
var etchMain = document.getElementById('etchMain');
var etchContext = etchMain.getContext('2d');
etchContext.clearRect(0, 0, etchMain.width, etchMain.height);
}
i implemented a really basic idea of what you're talking about just because it sounded kind of fun. hit run snippet, then click on the canvas box to give that frame focus. the event handler will prevent window scrolling and instead use the arrow inputs to increment or decrement x and y and draw from there or you can hit space bar to clear the canvas!
the bit of design you were missing was storing x and y outside of the event handler and using the difference between the previous state of x and y to draw your canvas lines:
var pos = {
x: 50,
y: 50,
}
var etchMain = document.getElementById('etchMain');
var etchContext = etchMain.getContext('2d');
window.addEventListener('keydown', function(e) {
e.preventDefault();
if(e.keyCode === 32) {
clearCanvas();
} else {
etchContext.beginPath();
etchContext.moveTo(pos.x, pos.y);
switch (e.keyCode) {
//left arrow
case 37:
pos.x--;
break;
//up arrow
case 38:
pos.y--;
break;
//right arrow
case 39:
pos.x++;
break;
//down arrow
case 40:
pos.y++;
break;
default:
break;
}
etchContext.lineTo(pos.x, pos.y);
etchContext.stroke();
}
});
function clearCanvas() {
etchContext.clearRect(0, 0, etchMain.width, etchMain.height);
}
#etchMain {
border: 1px solid black;
}
<canvas id="etchMain" height="100" width="100" />

Using JavaScript Animation to Move Rectangle With Arrow Keys

I'm trying to move a rectangle in a canvas element, and haven't had any luck. This is my code so far. I want to do it in PURE JavaScript, not jQuery or any other library.
My JavaScript:
window.onload = beginningMovement; // load beginning movement
function beginningMovement() {
var elem = document.getElementById("rectangle");
var pos = 0;
var id = setInterval(frame, 8);
function frame() {
if (pos == 203) {
clearInterval(id);
//Color funcs
setTimeout(black, 0);
setTimeout(lightgray, 500);
setTimeout(black, 1000);
setTimeout(lightgray, 1500);
setTimeout(black, 2000);
setTimeout(lightgray, 2500);
function black() {
var color = document.getElementById('container').style.backgroundColor = "black";
}
function lightgray() {
var color = document.getElementById('container').style.backgroundColor = "lightgray";
}
//End of color funcs
} else {
pos++;
elem.style.top = pos + 'px';
elem.style.middle = pos + 'px';
}
}
}
//Arrow switching
var X = 40;
var Y = 20;
function switchKey(event) {
Key = event.keyCode;
myCanvas.fillstyle = "white";
myCanvas.filRect(X, Y, 50, 50);
}
switch(key) {
case 37: X -=5;
break;
case 37: Y -=5;
break;
case 37: X +=5;
break;
case 37: Y +=5;
}
myCanvas.fillstyle = "blue";
myCanvas.filRect(X, Y, 50, 50);
HTML:
<!DOCTYPE html>
<html>
<head>
<title></title>
<style type="text/css">
#container {
width: 450px;
height: 400px;
border: 5px solid black;
background: lightgray;
}
#rectangle {
height: 50px;
width: 150px;
background: cyan;
margin-left: 150px;
margin-top: 160px;
position: absolute;
}
</style>
</head>
<body onkeyup="switchKey(event)">
<div id="container">
<div id="rectangle">
</div>
</div>
</body>
</html>
I've been at this for hours and haven't had any luck. I would appreciate it if someone could help me, and get this done soon.
There were a lot of issues with you code and I eventually thought it would be easier to remake a simple version for you to look at. If you really want to stick with your version, please check any browser console for errors and you'll see the issues I'm seeing. Some functions aren't yet available onload, there is no key variable, yet there is a Key variable. There were other issues, too, regarding variable and function scope.
Here's a new version for you to look at: http://codepen.io/antibland/pen/ONwEBE
It's not my finest work, but it's a step in the right direction for you. Instead of setInterval, you should be using requestAnimationFrame to do the redraw. It's much more performant (more on that here if you're interested).
In my demo, a real <canvas> element is used. The smaller rectangle is added to it. I figured you intended to use the real canvas since you included a myCanvas variable in your code. If not, apologies. Either way, you'll probably want to add bounds checking in there, to keep the small rectangle from moving beyond the walls.
Good luck!

How to move an element styled by CSS stylesheet?

I have an image that I want to move. I can move the element with javascript if I have the HTML below:
<html>
<head>
<title>Snake</title>
<script type="text/javascript" src="snake.js"></script>
<!-- <link type="text/css" href="snake.css"> -->
</head>
<body onKeyPress="ProcessKeypress(event);">
<p><img id="snake" style="z-index: 0; left: 300px; position: absolute; top: 250px"
float=top border=0 hspace=0 src="snake.gif"></p>
</body>
However I want to stye the image element using CSS. When I do this my code to move the image does not work. HTML and CSS below are what I would like to use.
<html>
<head>
<title>Snake</title>
<script type="text/javascript" src="snake.js"></script>
<link type="text/css" href="snake.css">
</head>
<body onKeyPress="ProcessKeypress(event);">
<p><img id="snake" src="snake.gif"></p>
</body>
#CHARSET "UTF-8";
img {
z-index: 0;
left: 300px;
position: absolute;
top: 250px;
float: top;
border: 0;
hspace: 0;
}
JavaScript below is what I am using to move the image. Any and all help appreciated.
function moveObj(name, Xpix, Ypix)
{
obj = document.getElementById(name);
px = parseInt(obj.style.left) + Xpix;
py = parseInt(obj.style.top) + Ypix;
obj.style.left = px;
obj.style.top = py;
}
function ProcessKeypress(e)
{
var myObj = 'snake';
var moveBy = 10;
if(e.keyCode === 97) {
moveObj(myObj, -moveBy, 0);
}
else if(e.keyCode === 100) {
moveObj(myObj, moveBy, 0);
}
else if(e.keyCode === 115) {
moveObj(myObj, 0, moveBy);
}
else if(e.keyCode === 119) {
moveObj(myObj, 0, -moveBy);
}
}
obj.style.left accesses the style properties defined in inline only.
UPDATE
Here is your pure JavaScript Solution
Function: getStyleProp() to get the current applied style [Source]
function getStyleProp(elem, prop){
if(window.getComputedStyle)
return window.getComputedStyle(elem, null).getPropertyValue(prop);
else if(elem.currentStyle) return elem.currentStyle[prop]; //IE
}
Function: moveObj()
function moveObj(obj, Xpix, Ypix) {
obj.style.left = parseInt(getStyleProp(obj,'left')) + Xpix+"px";
obj.style.top= parseInt(getStyleProp(obj,'top')) + Ypix + "px";
}
Function: ProcessKeypress()
function ProcessKeypress(e) {
var myObj = document.getElementById("snake");
var moveBy = 10;
switch(e.charCode) {
case 97: moveObj(myObj, -moveBy, 0); break;
case 100: moveObj(myObj, moveBy, 0); break;
case 115: moveObj(myObj, 0, moveBy); break;
case 119: moveObj(myObj, 0, -moveBy); break;
}
}
I also solved your case using jQuery: Demo
Function moveObj
function moveObj(obj, Xpix, Ypix) {
obj.css('left', parseInt(obj.css('left')) + Xpix);
obj.css('top', parseInt(obj.css('top')) + Ypix);
}
Function ProcessKeypress
function ProcessKeypress(e) {
var myObj = $("#snake"); //It will be better if it is cached
var moveBy = 10;
switch(e.charCode) { //used Switch for better manageability
case 97: moveObj(myObj, -moveBy, 0); break;
case 100: moveObj(myObj, moveBy, 0); break;
case 115: moveObj(myObj, 0, moveBy); break;
case 119: moveObj(myObj, 0, -moveBy); break;
}
}
Event Trigger attached to document instead
$(document).on('keypress', ProcessKeypress);
I'm not sure if your code was a copy-paste, but you need to close the link tag to link in your css.
<link rel="stylesheet" type="text/css" href="location" />
But that is beside the point. This is a repost so I'm going to flag it as that. Refer to Why is element.style.left returning NaN?
That should answer your question. It answered mine as I worked through your code and it made sense. Good luck.

Categories