「その場編集」を実装
前回はツールチップの実装方法をご紹介しました。
今回
![画像](/assets/images/design/serial/01/jquery-site-production/0017/001.png)
今回の仕組みを考える
この
- 最初はただのテキスト
- クリックをすると、
テキストがinput要素に置き換わり編集可能に。 - input要素からフォーカスが外れたら、
input要素が編集後の文字に置き換わる。 - フォーカス外れた時、
valueの値が空なら最初の値に戻す。
本来であれば、
まずは完成サンプルとソースコードを見てみましょう。
jQuery(function($){
$('dd').click(function(){
//classでonを持っているかチェック
if(!$(this).hasClass('on')){
//編集可能時はclassでonをつける
$(this).addClass('on');
var txt = $(this).text();
//テキストをinputのvalueに入れてで置き換え
$(this).html('<input type="text" value="'+txt+'" />');
//同時にinputにフォーカスをする
$('dd > input').focus().blur(function(){
var inputVal = $(this).val();
//もし空欄だったら空欄にする前の内容に戻す
if(inputVal===''){
inputVal = this.defaultValue;
};
//編集が終わったらtextで置き換える
$(this).parent().removeClass('on').text(inputVal);
});
};
});
});
今回の仕組みでは、
使用するHTML
今回はdl、
<dl>
<dt>名前:</dt>
<dd>技評太郎</dd>
<dt>会社名:</dt>
<dd>技術評論社</dd>
<dt>役職:</dt>
<dd>WEBディレクター</dd>
<dt>得意:</dt>
<dd>jQuery</dd>
</dl>
今回は実装を順をおいながら見ていくことにしましょう。
テキストをクリック後にinput要素へ
まずはテキストをクリックしたら、
その部分のみを実装したサンプルとソースコードを見てみましょう。
jQuery(function($){
$('dd').click(function(){
var txt = $(this).text();
$(this).html('<input type="text" value="'+txt+'" />');
});
});
DD要素のテキストを変数に入れ、
問題点
しかし、
これはなぜか?
この原因は、
これを回避するための策を次に実装してみます。
編集中のDD要素にclassを持たせる
先ほどの問題を回避するために、
jQuery(function($){
$('dd').click(function(){
if(!$(this).hasClass('on')){
$(this).addClass('on');
var txt = $(this).text();
$(this).html('<input type="text" value="'+txt+'" />');
}
});
});
classを持っているかどうかは.hasClassメソッドを使い、
//classでonを持っているかチェック
if(!$(this).hasClass('on')){
//classでonを持っていなかったら実行
};
$(this).hasClass('on')の前に
これで、
focusが外れたらテキストに戻る
先ほどの問題を回避するために、
jQuery(function($){
$('dd').click(function(){
if(!$(this).hasClass('on')){
$(this).addClass('on');
var txt = $(this).text();
$(this).html('<input type="text" value="'+txt+'" />');
$('dd > input').focus().blur(function(){
var inputVal = $(this).val();
$(this).parent().removeClass('on').text(inputVal);
});
}
});
});
inputに対して、
そしてフォーカスが外れたら、
ここまででほぼ完成なのですが、
if(inputVal===''){
inputVal = this.defaultValue;
};
「this.
これでとりあえず、
おまけ1:初期の値に戻す
ここからは今回の仕組みにちょっとした機能を盛り込むおまけです。
inputで値を変化させた後でも、
jQuery(function($){
//一つ一つの内容を保持するためeachを利用
$('dd').each(function(){
var backup = $(this).text();
//.data()を利用して最初の内容を残しておく
$(this).data('backup',backup)
.click(function(){
if(!$(this).hasClass('on')){
$(this).addClass('on');
var txt = $(this).text();
$(this).html('<input type="text" value="'+txt+'" />');
$('dd > input').focus().blur(function(){
var inputVal = $(this).val();
if(inputVal===''){
inputVal = this.defaultValue;
};
$(this).parent().removeClass('on').text(inputVal);
});
};
});
});
//リセットボタンをクリックで最初の状態に戻す機能
$('button').click(function(){;
$('dd').each(function(){
var backup = $(this).data('backup');
$(this).text(backup);
});
});
});
個々のテキストを.data()で保持させておくため、
これで、
おまけ2:内容に変更があった時だけリセット
先ほどのおまけ1で実装したリセット機能は、
jQuery(function($){
$('dd').each(function(){
var backup = $(this).text();
$(this).data('backup',backup)
.click(function(){
if(!$(this).hasClass('on')){
$(this).addClass('on');
var txt = $(this).text();
$(this).html('<input type="text" value="'+txt+'" />');
$('dd > input').focus().blur(function(){
var inputVal = $(this).val();
var backup = $(this).parent().data('backup');
if(inputVal===''){
inputVal = this.defaultValue;
};
$(this).parent().removeClass('on').text(inputVal);
//.data()の内容と比較し変化したていたらクリックできるように
if(backup !== inputVal){
$('button').removeAttr('disabled');
};
});
};
});
});
//リセットボタンは最初はクリックできないようにdisabled状態に
$('button').attr('disabled','disabled')
.click(function(){;
$('dd').each(function(){
var backup = $(this).data('backup');
$(this).text(backup);
});
//リセットした際は再びクリックできないように変更
$(this).attr('disabled','disabled');
});
});
変更内容を、
これで、
おまけも以上です。
今回ご紹介した以外にも、