Reputation: 115
I am trying to make a webpage where when you click a link, the link moves diagonally every 100 milliseconds.
So I have my Javascript, but right now when I click the link nothing happens
Also, does anyone know of a Javascript IDE I can use to make sure I have no errors in my code?
PS: Does anyone know why my elements dont stretch to fit the whole 200px by 200px of the div element? The links are only small when they should be the same width as their parent div element.
Edited with new advice, although still wont move.
<script LANGUAGE="JavaScript" type = "text/javascript">
<!--
var block = null;
var clockStep = null;
var index = 0;
var maxIndex = 6;
var x = 0;
var y = 0;
var timerInterval = 100; // milliseconds
var xPos = null;
var yPos = null;
function moveBlock()
{
if ( index < 0 || index >= maxIndex || block == null || clockStep == null )
{
clearInterval( clockStep );
return;
}
block.style.left = xPos[index] + "px";
block.style.top = yPos[index] + "px";
index++;
}
function onBlockClick( blockID )
{
if ( clockStep != null )
{
return;
}
block = document.getElementById( blockID );
index = 0;
x = parseInt( block.style.left, 10 );
y = parseInt( block.style.top, 10 );
xPos = new Array( x+10, x+20, x+30, x+40, x+50, x+60 );
yPos = new Array( y-10, y-20, y-30, y-40, y-50, y-60 );
clockStep = self.SetInterval( moveBlock(), timerInterval );
}
-->
</script>
<style type="text/css" media="all">
<!--
@import url("styles.css");
#blockMenu { z-index: 0; width: 650px; height: 600px; background-color: blue; padding: 0; }
#block1 { z-index: 30; position: relative; top: 10px; left: 10px; background-color: red; width: 200px; height: 200px;
margin: 0; padding: 0; /* background-image: url("images/block1.png"); */ }
#block2 { z-index: 30; position: relative; top: 50px; left: 220px; background-color: red; width: 200px; height: 200px;
margin: 0; padding: 0; /* background-image: url("images/block1.png"); */ }
#block3 { z-index: 30; position: relative; top: 50px; left: 440px; background-color: red; width: 200px; height: 200px;
margin: 0; padding: 0; /* background-image: url("images/block1.png"); */ }
#block4 { z-index: 30; position: relative; top: 0px; left: 600px; background-color: red; width: 200px; height: 200px;
margin: 0; padding: 0; /* background-image: url("images/block1.png"); */ }
#block1 a { display: block; width: 100%; height: 100%; }
#block2 a { display: block; width: 100%; height: 100%; }
#block3 a { display: block; width: 100%; height: 100%; }
#block4 a { display: block; width: 100%; height: 100%; }
#block1 a:hover { background-color: green; }
#block2 a:hover { background-color: green; }
#block3 a:hover { background-color: green; }
#block4 a:hover { background-color: green; }
#block1 a:active { background-color: yellow; }
#block2 a:active { background-color: yellow; }
#block3 a:active { background-color: yellow; }
#block4 a:active { background-color: yellow; }
-->
</style>
Upvotes: 2
Views: 3953
Reputation: 4132
You should declare your x and y above like your other variables. It may work but its confusing.
in your setTimeout, use moveBlock, not "moveBlock()" - it will save the step of evaluating your string into code.
block.style.left will return a string that includes "px" - it won't be a number. You can do:
x = Number(x);
//or
x = parseInt(x, 10);
When you set the position, remember to add the "px":
block.style.left = xPos[index] + "px";
EDIT:
Ok, the key problem is 'style.left' is not reading because it was set with CSS and not the style object. I use my library to get the style which runs through a few scenarios and catches that automatically. So change these lines to (this may not be exactly correct but will get things moving):
x = parseInt( node.style.left, 10 ) || 0;
y = parseInt( node.style.top, 10 ) || 0;
Also, this is wrong (you never declared 'self', and you don't need it here anyway; JS is case sensitive, SetInterval is not capped; pass the function, not the function result):
clockStep = self.SetInterval( moveBlock(), timerInterval ); // <-- result of moveBlock
// change to:
clockStep = setInterval( moveBlock, timerInterval ); // <-- the function moveBlock
During dev, you should remove the if() statements that could have been blocking the code and just put a simple count--; in there. It's really hard to debug code when you have literally 20 things wrong. Write a line, test. Write a line, test.
You have HTML comments in the script and style blocks. This is from 1998. While they don't hurt anything intact, in the past I've accidentally edited my code and removed one of them, and this will throw everything out of whack - your IDE, the browser - because they won't know what's wrong and you won't get a good error message.
LANGUAGE="JavaScript" is no longer used and is a waste of bytes.
To help speed development add this line:
window.onloadfunction(){
onBlockClick('block1')
}
That will execute your code right away for testing and you don't have to click every time.
Finally, I highly recommend you use Firefox and Firebug. Developing without it is like trying to build a ship in a bottle with boxing gloves. Using console.log(block.style.left) would have shown you it was not set. The error messages would have told you SetInterval and moveBlock() was incorrect. You do need to remember to remove the console.logs before production though. or... (shameless plug)... use my JavaScript Console Fix library which will do that for you: http://clubajax.org/javascript-console-fix-v2-now-with-ios/
Upvotes: 0
Reputation: 81384
Errors needed to fix
To fill the width of the div
elements, the a
elements need to be display: block;
not their default display: inline;
.
Knowing runtime errors is more important in my opinion, and IDEs don't catch DOM errors or anything more complex than syntax; use the error logging in your browser (Firefox's is called Error Console). That'll also catch in-development errors like syntax errors.
This is the most important point to stress: block.style.left
and block.style.top
are not just numbers with implicit pixel values in them. Setting it to a number without a unit suffix will do absolutely nothing. You need to add %
or px
or whatever unit when setting left
and top
.
When getting the current value, as in var x = ...
and var y = ...
, you need to Number()
manually to get the numeric portion of the string.
Also, I believe you meant || block == null
, not =
, which would set block
to null
.
Tips
You can use moveBlock
instead of "moveBlock();"
as an argument to setTimeout
. This avoids parsing the string into code, and avoids scope problems (though not in this example as moveBlock
is global).
I know that you have an array of values, where both x
and y
move 10 each time. I assume you want to move at a 45 degree angle. If so, this won't work as you expect even after fixing all the errors as x
is percentage and y
is in pixels.
Upvotes: 1