これが便利だといえる状況はだいぶ限られてはいるのだけど.文字を入力したり,チェックボックスを押したりしてデフォルトの状態から変化すると,そこの色を変えるような JavaScript のコードを書いてみた.
といってもわかりにくいと思うのでまずデモ:
適用したいページで,こんな JavaScript コードをロードします.
(function(){ var color_modified = '#ffff88'; var reset_when_reloaded = 1; init(); function init() { var fs = document.forms; for (var i = 0; i < fs.length; i++) { if (reset_when_reloaded) { fs[i].reset(); } var es = fs[i].elements; add_event(fs[i], ['reset'], mkhandler(fs[i].elements, function(e) { set_color(e, false); })); for (var j = 0; j < es.length; j++) { var prop = get_property_watched(es[j]); es[j].saved_default = es[j][prop]; es[j].orig_color = es[j].style.backgroundColor; if (es[j].type == 'radio') { /* XXX: inefficient */ add_event(es[j], ['keyup', 'change', 'click'], mkhandler(es, watch_property)); } else { add_event(es[j], ['keyup', 'change', 'click'], mkhandler([es[j]], watch_property)); } } } var ls = document.getElementsByTagName('label'); for (var i = 0; i < ls.length; i++) { var labeled_elm; if (ls[i].htmlFor && (labeled_elm = document.getElementById(ls[i].htmlFor))) { if (!labeled_elm.assoc_labels) { labeled_elm.assoc_labels = []; } labeled_elm.assoc_labels.push(ls[i]); /* XXX: implicitly labeled controls not considered */ ls[i].orig_color = ls[i].style.backgroundColor; } } function mkhandler(es, func) { return function() { for (var i = 0; i < es.length; i++) { func(es[i]); } }; } } function add_event(elm, evtypes, func) { for (var i = 0; i < evtypes.length; i++) { if (elm.attachEvent) { elm.attachEvent('on' + evtypes[i], func); } else if (elm.addEventListener) { elm.addEventListener(evtypes[i], func, false); } else { elm['on' + evtypes[i]] = func; } } } function get_property_watched(elm) { var property_watched = { checkbox: 'checked', radio: 'checked', _default: 'value' }; return property_watched[elm.type] || property_watched['_default']; } function watch_property(elm) { var prop = get_property_watched(elm); set_color(elm, elm[prop] != elm.saved_default); } function set_color(elm, hilight) { elm.style.backgroundColor = hilight? color_modified: elm.orig_color; if (!elm.assoc_labels) { return; } for (var i = 0; i < elm.assoc_labels.length; i++) { set_color(elm.assoc_labels[i], hilight); } } })();
どんなときに使うのかというと,サーバ側に保存してあるデータを編集するようなフォームに適用することを想定してます.編集すると色が変わるから submit しなくてはいけないとわかる.色が変わっていないならば Ctrl-W でウィンドウごと閉じちゃってよいとわかる.
で,submit 後に表示するページを,編集ページと同じものにしておけば, submit が「save」みたいになる.感覚的にはエディタっぽいインタフェースになります.私の場合は,自分用のウェブクリッピング CGI に使ってます.というかそれ用に書いた.
HTML に手を入れる必要はないので,bookmarklet とか Greasemonkey とかにもできるはず.ただし,新しい情報を提出するようなフォームに適用しちゃうとわけわからんと思うので,いまいち使いどころがないのがアレだ.
現状の問題点としては,
(追記) 最後の「})();」をうっかり消しちゃってたので修正.
最終更新時間: 2009-01-04 15:31