Nine Javascript Gotchas

1) Comma Caused Coruption
  var theObj = {
        city : "Boston",
        state : "MA",
  }

Notice the comma after "MA"?  It will be the source of many woes.  Firefox will pay it no heed, but it will create a syntax error in IE.  Worst of all, IE will not tell you where the actual bug is.  The only soution is to scan through your entire 2,500 line javascript file trying to find that extra comma.

2)  "this" can change which object it's pointing at

Take a look at this code sample.

<input type="button" value="Gotcha!" id="MyButton" >
<script>
var MyObject = function () {
    this.alertMessage = "Javascript rules";
    this.ClickHandler = function() {
          alert(this.alertMessage );
      }
}();
document.getElementById("theText").onclick =  MyObject.ClickHandler 
</script>

The function MyObject.ClickHandler will actually give a different alert, depending on how it's being called.

If you call MyObject.OnClick(); you will get a popup saying "Javascript rules".  

However, if you click on the button "MyButton", the popup will say "undefined"

When you assign MyObject.OnClick to the even handler, the special variable "this" now referes to the button, not to MyObject.

There are several ways to refer to MyObject.  My favorite is to introduce the "self" variable as a replacement for "this":

<input type="button" value="Gotcha!" id="theText" >
<script>
var MyObject = function () {
    var self = this;
    this.alertMessage = "Javascript rules";
    this.OnClick = function() {
          alert(self.value);
      }
}();
document.getElementById("theText").onclick =  MyObject.OnClick
</script>

Now the alert will say "Javascript rules" no matter what you call. The variable "self" will always refer to MyObject.

Note there is one more gotcha with the above code.  Do not forget the "var" in "var self" or IE will throw a mysterious exception.


3) Identity Theft

Never name a variable the same as an HTML ID:

<input type="button" id="TheButton">

<script>
    TheButton = get("TheButton");
</script>

This will work fine in Firefox but cause and object undefined error in InternetExplorer


4)  String replace only replaces the first occurrence

You might have a code to turn a title into a URL slug:

var fileName = "This is a title".replace(" ","_");

To your chagrin, fileName is actually equal to:
    "This_is a title"

Unlike replace in other languages such as C# or Python, only the first occurence is replaced.  That's because the first argument to replace is actually a regular expression.

To replace all occurences, you need to set the global modifier. Use:
var fileName = "This is a title".replace(/ /g,"_");

5)  MouseOut sometimes means MouseIn

When you have nested div's, the onmouseout event will fire for an outer box when you move inside the inner box.  For context menu's or hover overs, this is not the desired behavior.  My solution is to test for the mouse's location, and only take action if the mouse is actually positioned outside the outer box.

6)  ParseInt scoffs at your base ten numbering system

ParseInt is really nice, because it works with strings that are not pure digits.  I always find myself doing the following:
var height = parseInt("200px")

and get the height.

However, the default call to parseInt has a problem.

Guess what the value of monthInt will be:
  month = "09"
  var monthInt = parseInt(month )

If you guessed 9, then gotcha!  The answer is 0.

When the string begins with a zero, parseInt interprets the value in base 8.  To fix this problem, do the following:

var monthInt = parseInt(month , 10);

Now monthInt will be equal to 9.  The second argument forces parseInt to use a base ten numbering system.


7)  for loops over the kitchen sink

I once had an array as such:
var arr = [5,10,15]
var total = 1;
I iterated over the array:
for ( var x in arr) {
    total = total * arr[x];

}

This piece of code worked fine, until one day, I was getting error.  The error said, "Cannot object  by a number.  This flummuxed me since there were no strings in the array.  But, lo, when I iterated over the array and logged each value, there was an indeed a function object called "find".  

The cause was a javascript library that we had recently installed.  This library added a "find" method to the javascript array object.  Nice to have, but I the "for" loop in javascript will iterate it over all object attributes, including functions.  

But fortunately, the object was not included in the "length" attribute.  Thus to fix the problem, I used another kind of for loop:

for ( var x = 0; x < arr.length; x++) {
    total = total * arr[x];

}

That worked perfectly.



8)  Event handlers Pitfalls
Never set event handlers like the following:

window.onclick = MyOnClickMethod

1)  This will overwrite existing events.  It opens up the possibility of overwriting by some other javascript
2)  This can introduce memory leaks in Internet Explorer in certain circumstances.  

Instead, use a library that abstracts around the event handler, like YUI:

YAHOO.util.Event.addListener(window, "click", MyOnClickMethod);

9)  Focus Pocus

Often when I want to add inline editing to my app, I create a text field and then focus on it:

var newInput = document.createElement("input");
document.body.appendChild("newInput");
newInput.focus();
newInput.select();

However, the above code will create an error in IE.  The reason the even though you have added the element, it is not really available yet.  Fortunately, a split second delay is all we need:

var newInput = document.createElement("input");
newInput.id = "TheNewInput";
document.body.appendChild("newInput");

setTimeout("document.getElementById('TheNewInput').focus(); document.getElementById('TheNewInput').select();", 10);

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值