目次

Set Cookie's expire date

function saveCookie(){
   var targetDate = new Date();
   var dateInMs = targetDate.getTime();
 
   dateInMs += 60 * 60 * 24 * 1000 * 365;	//有効期限1年間
 
   targetDate.setTime(dateInMs);
 
   tmp = "多国語対応 non-ascii characters";
   document.cookie = "cookieInfo="+escape(tmp)+"; expires=" + targetDate.toGMTString();	
}

有効期限を過去にすることでクッキを削除することが可能だ。

function delCookie()
{
	document.cookie = "torqueInfo=; expires=Thu,01-Jan-1970 00:00:01 GMT";
}

前のsnippetでtmpが多国語(non-ascii文字列)の場合、必ずescapeしなければならない。
IEとFireFoxでテストしてみたが、不思議なごとにIIS-Tomcat連携サーバー(port:80)の環境でFirefoxのテスト結果,[HTTP/1.x 400 Bad Request]というメッセージが返ってきた。
しかし、port:8080(Tomcat default port)なら問題なく動作する。何が起こっているのか。
IISのエラーメッセージを確認してみたら次のとおりだった。1)

#Fields: date time c-ip c-port s-ip s-port cs-version cs-method cs-uri sc-status s-siteid s-reason s-queuename
2008-05-02 00:28:34 192.168.*.*** 1097 192.168.*.** 80 ----- Timer_ConnectionIdle -

はじめてみるTimer_ConnectionIdle エラー。これは何?
早速、Googleに尋ねてみるとrequestヘッダの限界値を超えた場合、Bad Requestが返ってくる場合があるという。
どうも、cookieが怪しいのでhttpヘッダを調べたところ確かに:-(

POST /khkweb/mail/sendMail.do HTTP/1.1
Host: svr2003:8080
Cookie: tmpInfo=.%u682A%u5F0F%u4F1A%u793E.%u5C0F%u539F%u3000%u592A%u90CE..048-255-4871..3320022.
%u57FC%u7389%u770C%u5DDD%u53E3%u5E02%u4EF2%u753A%uFF11%uFF13%uFF0D%uFF11%uFF17.1.kohara@khkgears%20co%20jp.
.0.0.; cookieInfo=.*>.; JSESSIONID=12E0FCEAA24660B0A3D428B7D482403B
POST /khkweb/mail/sendMail.do HTTP/1.1
Host: svr2003
Cookie: cookieInfo=.*>.; JSESSIONID=12E0FCEAA24660B0A3D428B7D482403B

両方ともcookieをescapeしないでブラウザにセーブした結果である。
port:80で要請した際、cookieがescapeされてない事が分かる。しかしport:8080で要請した場合は勝手にescapseされる。
ちなみに、IEでテストした場合も同様にescapeされる。いまだに、原因は不明だがIISサーバーのポートforwardingと関係がありそうだ。
最後にテスト環境を紹介する。

Web Server Browser JDK OS
IIS 6.0
Tomcat 5.5
IE6.0
FireFox2.0
1.5Windows Server 2003

Merge Rowspan

(function ($) {
    $.extend($.fn, {
        version: '0.9.0',
        rowMerge: function(options) {
            return new $.impl(options, this);
        }
    });
 
    // constructor
    $.impl = function(options, target) {
        // merge options
        this.o = $.extend(true, {}, $.impl.defaults, options);
        this.target = target;
        this.init();
    };
 
    // implementation
    $.extend($.impl, {
        defaults: {
            rowIndex: 1,
            cellIndex: [1]
        },
        prototype: {
            init: function() {
            	// cell length before merging
                this.tdLen = this.target.find('tr:nth-child(' + this.o.rowIndex + ') td').length;
                this.delArrays = [];
                this._scan();
            },
            _scan: function() {
                var self = this,
                	indexArray = self.o.cellIndex;
                $.each(indexArray, function (i, o) {
                    self._cellMergeChk(o);
                });
            },
            _cellMergeChk: function(cellIndex) {
                var self = this,
                    $target = $(self.target),
                    options = self.o,
                    cnt = 1,
                    compareObj = $target.find('tr:nth-child(' + options.rowIndex + ') td:nth-child(' + cellIndex + ')');
 
                // :gt(0-index)
                $target.find('tr:gt(' + (options.rowIndex - 1) + ')').each(function() {
                    // compare cell's length
                    compareIndex = cellIndex;
                    cellsLen = $(this).find('td').length;
 
                    if (self.tdLen != cellsLen) {
                        compareIndex = compareIndex - (self.tdLen - cellsLen);
                    }
                    cellObj = $(this).find('td:nth-child(' + compareIndex + ')');
 
                    if (compareObj.html() == cellObj.html()) {
                        self.delArrays[cnt - 1] = cellObj;
                        cnt++;
                    } else {
                        // merge
                        self._merge(compareObj);
                        // initialize
                        compareObj = cellObj;
                        self.delArrays = [];
                        cnt = 1;
                    }//if~else
                });
            },
            _merge: function(mergedCell) {
                $.each(this.delArrays, function() {
                    $(this).remove();
                });
                mergedCell.attr('rowspan', this.delArrays.length + 1);
            }
        }//prototype
    });
 
})(jQuery);

Demo

link to jsfiddle

Add Comma

function digits(number) {
	return (""+ number).replace(/(\d)(?=(\d\d\d)+(?!\d))/g, "$1,");
}

ちなみにカンマを除去するのは次のとおり

function delcomma(number) {
	return number.replace(/\,/g,'');
}

Number validation

function isNumeric(val, msg, item) {
  var obj = document.forms[0];
  oneDecimal = false;
  strInput = "" + val;
  var resultStr="";
 
  for (var i=0; i<strInput.length; i++) {
    var oneChar = strInput.charAt(i);
 
    // check minus & plus number
    if (i == 0 && strInput.length > 1) {
      if (strInput == "-." || strInput == "+.") {
        item.blur();
        alert(msg);
        return false;
      }else if(oneChar =="-" || oneChar=="+"){
      	resultStr = oneChar;
        continue;
      }//end if
    }//end if
 
	if(oneChar !="."){	    
    	if (oneChar < "0" || oneChar > "9") {
      		item.blur();
      		alert(msg);
      		return false;
    	}//end if
    }
 
    resultStr = resultStr + oneChar;
 
  }
 
  item.value = resultStr;
 
  return true;
}

Trim function

//full trim
String.prototype.trim = function() {
	return this.replace(/^\s+|\s+$/g,"");
}
//left trim
String.prototype.ltrim = function() {
	return this.replace(/^\s+/,"");
}
//right trim
String.prototype.rtrim = function() {
	return this.replace(/\s+$/,"");
}

space以外にも&nbsp;も対応する場合はregexpの部分を次のように修正すればよい。

   this.replace(/^[\s\xA0]+|[\s\xA0]+$/g,"");

calculation the size of textarea

textareaに入力した文字列のサイズを測る為に、次のソースを活用できる。

String.prototype.size = function() {	
	var _len = (!this) ? 0 : this.length;
    var _size = 0;
 
    for (i = 0; i < _len; i++) {
    	c = this.charCodeAt(i);
 
        if ((c >= 0x0000) && (c <= 0x007F) ) {
        	_size++;
        } else if(c > 0x07FF){ 
        	_size += 3;
        } else {
        	_size += 2;
        }//if~else
    }
 
    return _size;
}

demo page

<html> <head> <meta http-equiv=“Content-Type” content=“text/html; charset=UTF-8” /> <title>demo page for form reset using jQuery</title>

<script type=“text/javascript” src=“./test/js/jquery-1.4.2.js”></script>

<script type=“text/javascript”> String.prototype.size = function() {

  var _len = (!this) ? 0 : this.length;
  var _size = 0;

for (i = 0; i < _len; i++) {

  	c = this.charCodeAt(i);

if 2)

1)
エラーメッセージは%WinDir%\system32\LogFiles\HTTPERR\下にある。WinDirはWindows設置フォルダだ。
2)
c >= 0x0000) && (c ⇐ 0x007F) ) {
      	_size++;
      } else if(c > 0x07FF){ 
      	_size += 3;
      } else {
      	_size += 2;
      }//if~else
  }
  return _size;
} $(function(){
  $("textarea[name='q']").keyup(function(){
      $("#console").text(this.value.size());
  });
}); </script> <style type=“text/css”> #console{
 color: #0000FF;
 font-weight: bold;
} </style> </head> <body> <textarea name=“q” cols=“50” rows=“5”></textarea> <br> <div id=“console” style=“display:inline-block;”>0</div>bytes </body> </html> ===== e-mail regexValidator ===== eメールの一般的なvalidationの表現式は以下のようです。
\\b(^_A-Za-z0-9-(\\._A-Za-z0-9-)*@(A-Za-z0-9-)+((\\.com)|(\\.net)|(\\.org)|(\\.info)|(\\.edu)|(\\.mil)|(\\.gov)
|(\\.biz)|(\\.ws)|(\\.us)|(\\.tv)|(\\.cc)|(\\.aero)|(\\.arpa)|(\\.coop)|(\\.int)|(\\.jobs)|(\\.museum)|(\\.name)
|(\\.pro)|(\\.travel)|(\\.nato)|(\\..{2,3})|(\\..{2,3}\\..{2,3}))$)\\b
~~DISCUSSION~~