CSS

Showing posts with label jquery. Show all posts
Showing posts with label jquery. Show all posts

[.Note]jquery動態調整欄寬&限制checkbox選取

幾個專案上遇到的小需求,
皆用JQuery來解決,在這裡記錄一下解法

1.動態調整欄寬 :


有一個table,他的第一個欄位長度是固定的,後面的欄位要有相等的寬度,
但是後面的欄位數目是動態產生,欄位的名稱長度也不固定,如果欄位過長則必須要換行

一開始是用%數的方法來指定欄寬長度,但是這個方法並不能夠有效的在所有瀏覽器上運行
後來使用jquery來動態調整欄寬 : 先等table產生,再計算出後面欄位的平均寬度,並將儲存格寬度調整為平均寬度:

$('.sort').each(function() {
    var sum = 0;
    //取得所有要調整的欄寬
    var cells = $(this).find('.sort-item');
    //統計總寬度
    cells.each(function() {
        sum += $(this).width();
    });
    //設定平均欄寬 
    var cellWidth = sum / cells.length;
    cells.each(function() {
        $(this).width(cellWidth);
    });
});

2.限制checkbox選取


有一個多選的CheckboxList,需要限制最大的選取數量
如果超過則不能選擇:

//傳入CheckboxList Container的ID
bindMultiSelectLimit = function(id,limit) {
    $('#' + id + ' input:checkbox').click(function() {
        //使用Jquery selector直接找出所有已選之Checkbox
        if ($('#' + id + ' input:checked').length > limit) {
            return false;
        }
    });
};

3.限制排序問題重覆選取


有一個問卷題型叫排序題,結構上是由許多RadioButtonGroup所構成,
讓使用者能排列喜好選項的順序 : (ex, 有三個選項, 可以選擇 3,2,1 或 1,2,3的排序 )
但使用者希望能夠有防呆機制,讓已經於其他選項選過的排序不能再選第二次
(ex:三個選項的排序可為 1,2,3. 3,2,1 . 但不可為 2,2,1 )
後來選擇了一個比較簡單的作法:當排序被選取時,清空其他有同樣排序值的RadioButton

//傳入ContainerID
bindSortRules = function(id) {
    $('#' + id + ' input').click(function() {
    //設定每個排序RadioButton有同樣的value,將其他有相同value的值都設為false
    $('#' + id + ' input[value=' + $(this).val() + ']').attr('checked', false);
        //設定目前選擇的值
        $(this).attr('checked', true);
    });
}

以上的需求如果使用Javascript不知道要做多久...
所以說JQuery真的是能夠有效增加前端生產力的一個好框架啊,
只要有用到Web的開發者真的都需要接觸一下

[.Note] 10 Things I Learned from JQuery Source (or more then 10?)


10 Things I Learned From The JQuery Source
From Paul Irish

一篇很棒的演講,由專家帶領我們從JQuery的原始碼中學習一些JQuery所用的JavaScript Pattern以及設計方式.

自從在OSDC2010上聽了Gugod的Less is More,JQuery這個框架的簡潔性以及設計的原則就一直吸引著我.
這個演講剛好讓我以後在用JQuery的時候能更輕易的去看source.

以下是筆記:

1.JQuery的Convention之一: Closure Pattern:
(function(){ ... })();

!function(){ ... }()

後面的括號代表這是self executing function: run itself immediately

favorite pattern:
(function(window,document,undefined){
    ....
})(this,document)

把window,document當成變數傳入closure,這樣的好處是:
1.如果有其他全域變數例如 undefined = true; // break all undifined comparison
而closure避免了這些干擾
2.minification:
最佳化後會變成: function(A,B,C){}(this,document), 可以省下一些字元

2. async recursion

Self repeating: 會不斷的執行,不論前一項有沒有執行完,
例如
setInterval(function(){ 
   doStuff();
},100) // is very evil

而self executing function能確保執行到尾巴之後才會執行第二遍
(function loops(){
    doStuff();
    $('#update').load('awesomething.php',function(){
        loops();
    })
    setTimeout(loops,100);
})()

3.如何找到函式: 找 function name + : , ex: "noConflict:"

4.Jquery.noConflict:
在開始時將 原本的 $ 儲存為 _$, 並在呼叫noConflict時復原.

5.jQuery.props
小型的參數字典,自動將Html與Dom Api上一些相同意思但名稱不同的參數作對應
讓開發者不需要記得所有的東西.
也可以用在.attr:
ex: WAI ARIA
$(elem).attr('aria-disabledby','asdasdasd');

$.props['adb'] = 'aria-disabledby';
=>
$(elem).attr('adb') = 'asdasdasd';

6. fadeIn() : defined your own speeds:
JQuery內部的 speed 定義了各種速度:
speeds: {slow:800 ,fast:200 ,_default:800}
可以由外部加入自訂的速度
jQuery.fx.speeds.fastopen= ($.browser.msie && $.browser.version < 8 ) ? 800 : 400;
//在IE7以下速度為800,其他瀏覽器為400

$('#stuff').fadeIn('fastopen');
7.JQuery.ready(...) 會檢查DOM準備好沒,在準備完畢時執行function,

bindReady(); // IEContentLoad: solve by great Italian hacker,

using doScroll check to check if DOM ready in IE :

doScroll(left); //will raise exception if DOM not ready.

8.getJSON : shorthand methods:

jQuery ajax() holds anything, but get,post,getJSON,getScript shorten the varible.

9.selector performence.
$('#id') vs $('#id tag.thing')
$('#id tag.thing') will self parse to => $('#id').find('tag.thing');
$('#id').find('tag.thing')
$(':password') === $('*:password') 
so better provide tagname ex: $('input:password');

10.getJSON: function protect 會用regex檢查資料是否為JSON,如果是的話就pass,
不是的話會呼叫 (new Function("return" + data))();
這叫Function constructor: 回傳
function(){return data;}
=== eval('('+data')');
但是避開使用邪惡的eval 

11 $.unique(err) : duck punch
$.unique能夠過濾相同的DOM元素,讓陣列只有unique的元素
但不對應基本物件 使用duck punch來擴充unique方法:
(function($){

    _old = $.unique()

    if(!!arr[0].nodeType){
        return _old.apply(this,arguments);
    } else {
        return $.grep(arr,function(v,k){
            return $.inArray(v,arr) === k
        });
    }
})(jQuery);

12.quene: $(elem).fadeIn().delay(1000).fadeOut(); 可以使用quene方法改寫成
$(elem).quene(function(){
        $(elem).delay(1000).fadeOut();
});

13.$.support
support使用一個HTML div,內部包含table,/a等等各項元素,
support會檢查瀏覽器能不能辨識其中的元素,來做瀏覽器的相容性檢查

14.bit.ly/jqsource : 一起來看JQuery Source

[JQuery] 如何判斷元素是否存在

最近遇到了一個bug,
是因為jQuery沒有將事件綁定到指定的物件上所產生的

所以加上了檢查Html元素是否存在的邏輯:

if($("#obj") != null){...}

可是結果還是一樣,括弧內的邏輯一定會執行到.

打開debugger檢查之後,發現Jquery使用了Null Object
就是即使找不到元素,JQuery還是會回傳一個空的JQuery物件.
讓對物件的操作不會因為null reference而產生錯誤.

但是Null Object的缺點就是,如果其他程式設計師不知道使用了Null Object,
就會寫出錯誤的檢查...像我一樣.

所以這裡應該檢查元素的length屬性,如果是空值的話就會傳回0:

if($("#obj").length > 0){...}

由於javascript的boolean判斷會將0判斷成false,1以上的值判斷成true,
所以也可以這樣寫:

if($("#obj").length){...}

參考文章:http://www.aaronrussell.co.uk/blog/check-if-an-element-exists-using-jquery/


同場加映:

於內嵌的PDF IFrame讀取時使用jquery.blockUI:

$(function() {  
    var iframe = $("#PDFiframe");
    if(iframe.length){
        //ie在綁定Iframe事件的時候會產生錯誤,必須要用windows.frames[]來取得iframe
        //另外如果直接用jquery接frames物件的話,於判斷length時一定會傳回true...
        if($.browser.msie){
            iframe = $(frames["PDFiframe"]); 
        }
        $.blockUI();
        iframe.load(function() { $.unblockUI(); });
    }
});