(function($){
	if (!$) throw new Error("jQuery framework is required");
	function fluidTable(n, o){
		if (!n) n = 4
		if (!o){
			var thisFunc = arguments.callee;
			$(".js-fluid").each(function(i, o){thisFunc(n, o)});
			return;
		}
		
		if (!o.elements){
			o.elements = [];
			$("td:not(.empty)", o).each(function(i, td){
				o.elements.push(td);
				td.size = ~~$(td).attr("colspan")||1;
			});
			o.num = -1;
		};
		if (n < 2) n = 2;
		
		if (o.num == n) return;
		while (o.childNodes.length){
			o.removeChild(o.childNodes[0]);
		};
		
		var tbody = document.createElement("tbody");
		var queue = o.elements.concat();
		
		while (queue.length){
			var tr = tbody.appendChild(document.createElement("tr"));
			var rowsize = 0;
			var shorts = [];
			var longs = [];
			do {
				var td = queue.shift();
				if (!td){
					td = document.createElement("td");
					td.className = "empty";
					td.size = 1;
				};
				var size = td.size;
				tr.appendChild(td);
				if (size == 1){
					shorts.push(td)
				} else {
					longs.push(td);
				};
				rowsize += size;
			} while (rowsize < n);
			if (rowsize > n && shorts.length){
				td = shorts.pop();
				td.parentNode.removeChild(td);
				queue.unshift(td);
				rowsize--;
			};
			if (rowsize > n /* && queue.length */){
				td = longs.pop();
				td.parentNode.removeChild(td);
				queue.unshift(td);
				rowsize-=2;
				
				for (var i=0; i<queue.length; i++){
					if (queue[i].length == 1){
						var td = queue[i];
						queue = queue.splice(i, 1);
						tr.appendChild(td);
						rowsize++;
						break;
					};
				};
			};
 			if (rowsize < n){
				td = document.createElement("td");
				td.className = "empty";
				td.size = 1;
				tr.appendChild(td);
			};
			
		}
		o.appendChild(tbody);
		o.num = n;
		
	};
	
	window.fluidTable = fluidTable; /* expose to global scope */
})(jQuery);
