I have element
<div id="square"></div>
He has a property to move on document
var square = document.getElementById("square");
document.body.onkeydown = function(e) {
if (e.keyCode == 37) {left()}
if (e.keyCode == 38) {up()}
if (e.keyCode == 39) {right()}
if (e.keyCode == 40) {down()}
}
How I make a function, which not allowed movement, if square element is closest to document border?
JSFiddle: https://jsfiddle.net/zutxyLsq/
You need to check if left is outside of boundaries like this:
function left() {
console.log('Left');
var left = parseInt(square.style.left || getComputedStyle(square)['left'], 10);
if (left >= 50) {
square.style.left = (left - 50) + 'px';
}
}
function right() {
console.log('Right');
var left = parseInt(square.style.left || getComputedStyle(square)['left'], 10);
if (left+50+square.offsetWidth < window.innerWidth) {
square.style.left = (left + 50) + 'px';
}
}
https://jsfiddle.net/zutxyLsq/3/
and the same for up and down.
Related
When I keyup spacebar, paly video.
But If I focus on the 'textarea' for writing play video too.
i wanna stop video if i focus on the textarea. help me!
window.onkeypress = function(e) {
if (e.srcElement.className.indexOf('dragClass') > -1) {
if (e.keyCode === 1300) {
divWidth = document.getElementById('controlBar').clientWidth;
if (divWidth < canvas.width)
scale = divWidth / canvas.width;
else
scale = 1;
curSize += 0;
ctx.font = curSize + 'px Arial';
ctx.fillStyle = curColor;
ctx.fillText(textBox.value, mouseX / scale, mouseY / scale);
videoDiv.removeChild(textBox);
}
} else if (e.srcElement.id == 'textArea') {;
} else {
if (e.keyCode === 32) {
$('.play-pause-btn-' + modalId).blur();
if (vid.paused) {
vid.play();
playbtn.style.background = "url(/assets/images/common/btn_pause_black.png) 50% 50% no-repeat";
loop();
} else {
vid.pause();
playbtn.style.background = "url(/assets/images/common/btn_play_black.png) 50% 50% no-repeat";
}
}
if (e.keyCode === 44) {
previousframeStep();
}
if (e.keyCode === 46) {
nextframeStep();
}
}
Here my code.
Instead of "e.srcElement.id" use "e.target.id". Also it would be better if the textArea object had a event listener that triggered to do what you want rather than the window object.
If you are wanting to check via the "id" method you should also have a safety check in there as well, because not all objects have a id property and that will throw a error!
if (e.target.id && e.target.id === "textarea")\\then do whatever
I am trying to control a Sprite using the arrow keys (UP/DOWN for Translation & LEFT/RIGHT for Rotation).
I need the sprite to translate in the direction it has been rotated in.
The issue is that when the sprite is rotated after the sprite has been translated, the position of the sprite resets to where it was originally. I have tried using one div for rotation and one div for translation to no success.
The problem I am facing is a little different to the usual "moving div around screen" issue because I need to move the div at angles and continue to move at that angle.
I feel I am overlooking a simple solution, I would really appreciate if someone could point me in the right direction! Is there an easier alternative to what I am attempting to do that someone could make me aware of?
I have created a JSFiddle to demonstrate what is going on:
CSS transform sprite fiddle
var r = document.getElementById("image2");
document.addEventListener("keyup", checkKeyUp);
document.addEventListener("keydown", checkKey);
var trany = 0;
var rotate = 0;
function checkKey(e) {
e = e || window.event;
if (e.keyCode == '38') {
// up arrow
trany = trany-1;
r.style.transform = 'rotate('+rotate+'deg)translateY('+trany+'vmin)';
}
else if (e.keyCode == '40') {
// down arrow
trany = trany+1;
r.style.transform = 'rotate('+rotate+'deg)translateY('+trany+'vmin)';
}
else if (e.keyCode == '37') {
// left arrow
rotate = rotate-.8;
r.style.transform = 'translateY('+trany+'vmin)rotate('+rotate+'deg)';
}
else if (e.keyCode == '39') {
// right arrow
rotate = rotate+.8;
r.style.transform = 'translateY('+trany+'vmin)rotate('+rotate+'deg)';
}
}
function checkKeyUp(e) {
e = e || window.event;
if (e.keyCode == '38') {
// up arrow
}
else if (e.keyCode == '40') {
// down arrow
}
else if (e.keyCode == '37') {
// left arrow
r.style.transform = 'translateY('+trany+'vmin)rotate('+rotate+'deg)';
}
else if (e.keyCode == '39') {
// right arrow
r.style.transform = 'translateY('+trany+'vmin)rotate('+rotate+'deg)';
}
}
#myAnimation {
top:250px;
left:250px;
position: absolute;
}
#image2 {
width:40%
}
img {
width: 30%;
}
<!DOCTYPE html>
<html>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<body>
<div id ="myContainer">
<div id="image1" style="height:300px;width:500px; background-
color:red;"></div>
</div>
<div id ="myAnimation">
<image id="image2" src="https://banner2.kisspng.com/20180415/pge/kisspng-arrow-desktop-wallpaper-symbol-clip-art-up-arrow-5ad37ddc82f384.4572004515238097565364.jpg" style="bottom:0px;width:10%"></image>
</div>
</body>
</html>
what you want to achieve is to move your element independently from its previous state and this cannot be achieved using only transform since transform always consider the initial state in order to move your element.
An idea is to consider using bottom/left to move the element and use only transform to rotate the element. The angle of rotation will define how you will adjust the bottom and left properties:
var r = document.getElementById("image2");
document.addEventListener("keydown", checkKey);
var rotate = 0;
var left=0;
var bottom= 0;
function checkKey(e) {
e = e || window.event;
if (e.keyCode == '38') {
// up arrow
r.style.left = left + Math.sin(rotate*Math.PI/180) + 'px';
r.style.bottom = bottom + Math.cos(rotate*Math.PI/180) + 'px';
} else if (e.keyCode == '40') {
// down arrow
r.style.left = left - Math.sin(rotate*Math.PI/180) + 'px';
r.style.bottom = bottom - Math.cos(rotate*Math.PI/180) + 'px';
} else if (e.keyCode == '37') {
// left arrow
rotate = rotate - .8;
r.style.transform = 'rotate(' + rotate + 'deg)';
} else if (e.keyCode == '39') {
// right arrow
rotate = rotate + .8;
r.style.transform = 'rotate(' + rotate + 'deg)';
}
left = parseFloat(r.style.left);
bottom = parseFloat(r.style.bottom);
}
#image2 {
width: 40px;
position: absolute;
}
<img id="image2" src="https://banner2.kisspng.com/20180415/pge/kisspng-arrow-desktop-wallpaper-symbol-clip-art-up-arrow-5ad37ddc82f384.4572004515238097565364.jpg" style="left:0;bottom:0;">
To fix this problem we need to understand how transform works. It does each step one by one. If we want, for example to move diagonally, first we need to rotate, then translate. If we want to make the next move, our previous steps need to be saved. If we don't remember them, the arrow will be animated from the beginning.
So, on each animation end (key up) we need to save all the previous steps.
The next step is all the previous steps + translate/rotate.
Here is your code that I think is working correctly:
var r = document.getElementById("image2");
document.addEventListener("keyup", checkKeyUp);
document.addEventListener("keydown", checkKey);
var saved_moves = '';
var trany = 0;
var rotate = 0;
function checkKey(e) {
e = e || window.event;
if (e.keyCode == '38') {
// up arrow
trany = trany-1;
r.style.transform = saved_moves + 'translateY('+trany+'vmin)';
}
else if (e.keyCode == '40') {
// down arrow
trany = trany+1;
r.style.transform = saved_moves + 'translateY('+trany+'vmin)';
}
else if (e.keyCode == '37') {
// left arrow
rotate = rotate-2;
r.style.transform = saved_moves + 'rotate('+rotate+'deg)';
}
else if (e.keyCode == '39') {
// right arrow
rotate = rotate+2;
r.style.transform = saved_moves + 'rotate('+rotate+'deg)';
}
}
function checkKeyUp(e) {
e = e || window.event;
if (e.keyCode == '37' || e.keyCode == '38' || e.keyCode == '39' || e.keyCode == '40') {
// every arrow
saved_moves = r.style.transform;
// reset trany and rotate values
trany = 0;
rotate = 0;
}
}
You can check this jsfiddle https://jsfiddle.net/cyv0j1du/49/
EDIT
Becouse the solution above would create a very long transform, I've came up with different solution. When you release the key, app is reading the matrix value, and then it changes the arrow top and left value. Now only rotate value is remembered.
// Based on the absolute position you've chosen
var left = 250;
var top = 250;
function checkKeyUp(e) {
e = e || window.event;
if (e.keyCode == '37' || e.keyCode == '38' || e.keyCode == '39' || e.keyCode == '40') {
var matrix = window.getComputedStyle(r).getPropertyValue('transform');
matrix = matrix.slice(0, -1);
var values = matrix.split(',');
var x = values[4];
var y = values[5];
top += parseInt(y);
left += parseInt(x);
r.style.top = top + 'px';
r.style.left = left + 'px';
r.style.transform = 'rotateZ('+rotate+'deg)';
trany = 0;
}
}
I've also deleted #myAnimation
#image2 {
width: 20%;
position: absolute;
top: 250px;
left: 250px;
}
so I've deleted the div
<image id="image2" src="https://banner2.kisspng.com/20180415/pge/kisspng-arrow-desktop-wallpaper-symbol-clip-art-up-arrow-5ad37ddc82f384.4572004515238097565364.jpg" style="bottom:0px;width:10%"></image>
You can check how it works here:
https://jsfiddle.net/w1ox240m/57/
function docReady()
{
image = document.getElementById("someImage");
window.addEventListener("keydown", moveImage);
}
function moveImage(e)
{
if (e.keyCode == 37)
image.style.left = parseInt(image.style.left) - 5 + 'px';
if (e.keyCode == 38)
image.style.top = parseInt(image.style.top) - 5 + 'px';
if (e.keyCode == 39)
image.style.left = parseInt(image.style.left) + 5 + 'px';
if (e.keyCode == 40)
image.style.top = parseInt(image.style.top) + 5 + 'px';
console.log(image.style.left + ', ' + image.style.top);
}
So the code above is supposed to move an image around. However, it doesn't. The console returns blanks for image.style.left and image.style.top. Could you help me with fixing it?
P.S. If you would be so kind, can you also make it so that if the image is on the screen borders it will stop moving? Thank you so much!
You are missing some steps indeed.
To be precise, you should:
create the variable image outside the function (i.e., declare it global)
set the initial values of top, left
set the position of your element to absolute. Default is static and it doesn't support moving/styling with top/left/right/bottom.
call the whole thing on page load
And here's what you get once you follow the above steps:
window.onload = docReady;
var image;
function docReady() {
image = document.getElementById("someImage");
window.addEventListener("keydown", moveImage);
image.style.left = 0;
image.style.top = 0;
}
function moveImage(e) {
if (e.keyCode == 37)
image.style.left = parseInt(image.style.left) - 5 + 'px';
if (e.keyCode == 38)
image.style.top = parseInt(image.style.top) - 5 + 'px';
if (e.keyCode == 39)
image.style.left = parseInt(image.style.left) + 5 + 'px';
if (e.keyCode == 40)
image.style.top = parseInt(image.style.top) + 5 + 'px';
console.log(image.style.left + ', ' + image.style.top);
}
#someImage{
position:absolute;
}
<div id = "someImage"> not an image but a test </div>
(For the simplicity I'm using a plain text element instead of image, but that doesn't matter)
This question already has answers here:
How to detect if multiple keys are pressed at once using JavaScript?
(19 answers)
Closed 5 years ago.
So i am making a html5 game where i was working in movement. Player can move with w, a, s ,d in key. That is working well but i wanted to add a power ..like if player press a + space-bar or d + space-bar an ability will trigger.
i used and operator and it should have worked in my theory but it's not working.
I am new in html5 and any help will be appreciated. thanks in advance.
Here is my code... Just copy paste on html note.
<canvas id="canvas" width="800" height="500" style="border:1px solid #000000;"></canvas>
<script>
var c = document.getElementById("canvas").getContext("2d");
var WIDTH = 800;
var HEIGHT = 500;
var player = {
x: Math.random() * WIDTH,
y: Math.random() * HEIGHT,
width: 30,
height: 30,
color: 'black',
pressingDown: false,
pressingUp: false,
pressingLeft: false,
pressingRight: false,
pressinpowerRight: false,
pressinpowerLeft: false,
};
drawEntity = function(e) {
c.fillStyle = e.color;
c.fillRect(e.x - e.width / 2, e.y - e.height / 2, e.width, e.height);
}
document.onkeydown = function(event) {
if (event.keyCode === 68) //d
player.pressingRight = true;
else if (event.keyCode === 83) //s
player.pressingDown = true;
else if (event.keyCode === 65) //a
player.pressingLeft = true;
else if (event.keyCode === 87) // w
player.pressingUp = true;
else if (event.keyCode === 68 && event.keyCode === 32) // this statement is not working
player.pressinpowerRight = true;
else if (event.keyCode === 65 && event.keyCode === 32) // this statement is not working
player.pressinpowerLeft = true;
}
document.onkeyup = function(event) {
if (event.keyCode === 68) //d
player.pressingRight = false;
else if (event.keyCode === 83) //s
player.pressingDown = false;
else if (event.keyCode === 65) //a
player.pressingLeft = false;
else if (event.keyCode === 87) // w
player.pressingUp = false;
else if (event.keyCode === 68 && event.keyCode === 32) // not working
player.pressinpowerRight = false;
else if (event.keyCode === 65 && event.keyCode === 32) // not working
player.pressinpowerLeft = false;
}
updatePlayerPosition = function() {
if (player.pressingRight)
player.x += 5;
if (player.pressingLeft)
player.x -= 5;
if (player.pressingDown)
player.y += 5;
if (player.pressingUp)
player.y -= 5;
if (player.pressingpowerRight)
player.x += 50;
if (player.pressingpowerLeft)
player.x -= 50;
}
update = function() {
c.clearRect(0, 0, WIDTH, HEIGHT);
updatePlayerPosition();
drawEntity(player);
}
setInterval(update, 40);
</script>
Try creating a previousButtonKey global variable and always record the last key, then check the previousButtonKey with another key to combine two keys on your condition.
Ex. First key is to be pressed is 'Shift', store it to a variable, then once another key event happens, check the previous and the new key. If it is valid, then do the action that you want.
I tried to make a moving img, and it works partially. If I press the right, up or down button, it moves right, up or down. But, if I press the left button, it jumps very fast very far to the right, and then back to the left and doesn't stop moving (I believe. I said it was fast).
JSFiddle;
Javascript:
$(document).ready(function() {
var up = down = left = right = false;
var top = 100, left = 500;
$("body").on("keydown", function(e) {
if(e.keyCode == 39) {e.preventDefault(); if (right == false) right = setInterval(moveRight, 80);}
else if(e.keyCode == 37) {e.preventDefault(); if (left == false) left = setInterval(moveLeft, 80);}
else if(e.keyCode == 38) {e.preventDefault(); if (up == false) up = setInterval(moveUp, 80);}
else if(e.keyCode == 40) {e.preventDefault(); if (down == false) down = setInterval(moveDown, 80);}
});
$("body").on("keyup", function(e) {
if(e.keyCode == 39) {clearInterval(right); right = false;}
else if(e.keyCode == 37) {clearInterval(left); left = false;}
else if(e.keyCode == 38) {clearInterval(up); up = false;}
else if(e.keyCode == 40) {clearInterval(down); down = false;}
});
function moveUp() {
top -= 2;
$("#player").css("top", top + "px");
}
function moveDown() {
top += 2;
$("#player").css("top", top + "px");
}
function moveLeft() {
left -= 2;
$("#player").css("left", left + "px");
}
function moveRight() {
left += 2;
$("#player").css("left", left + "px");
}
});
This is probably not the best way to do this, I'm open for better suggestions.
You're defining two "left" variables, and they are getting in the way of each other. Change one of their names (perhaps leftInterval for the interval variable), and things should go better.
The variables are overwritten, try something like :
$("body").on("keydown", function(e) {
e.preventDefault();
var elm = $("#player"),
top = parseInt(elm.css('top')),
left = parseInt(elm.css('left'));
switch(e.which) {
case 37:
elm.css("left", left-2);
break;
case 38:
elm.css("top", top-2);
break;
case 39:
elm.css("left", left+2);
break;
case 40:
elm.css("top", top+2);
break;
}
});
FIDDLE