样式操作
有哪些方法常用
.css(), .addClass(), .hasClass(), .removeClass(),.toggleClass()
.css 方法初步实现
<script>
jepson.fn.extend( {
css: function( option ) {
var self = this;
self.each(function() {
for ( var k in option ) {
this.style[ k ] = option[ k ];
}
});
return self;
}
});
// 创建一个 div, 加到 body 中, 并且设置其样式
J('div').css({
border: '1px dashed red',
backgroundColor: 'pink',
width: '400px',
height: '300px'
}).appendTo( 'body' ).click(function () {
this.innerHTML = '我被点击了';
});
</script>
.css 方法详细分析:
- 带有一个 json 对象的方法: 设置样式
- 带有一个键值对的 方法: 设置样式
- 带有一个名字字符串的方法: 读取样式
带有两个参数或一个参数使用 arguments 来进行判断
.length == 2
.length == 1:
是一个字符串
是一个对象
if ( arguments.length == 2 ) {
// 设置样式
} else if ( .length == 1 ) {
if ( option 是 string ) {
获取
} else if ( 是一个 object ) {
设置
}
}
$( '#dv' ).css()
完整的 css 方法
<script>
jepson.fn.extend( {
css: function( option ) {
var len = arguments.length;
var args = arguments;
if ( len == 2 ) {
// 判断键值
if ( jepson.isString( args[ 0 ] ) && jepson.isString( args[ 1 ] ) ) {
// 两个都是字符串,说明是要设置 css属性
return this.each( function() {
this.style[ args[ 0 ] ] = args[ 1 ];
});
}
} else if ( len == 1 ) {
// 一个参数 字符串就是求值, 对象就是设置
if ( typeof option == 'string' ) {
return this[0].style[ option ];
} else if ( typeof option == 'object'){
return this.each(function() {
for ( var k in option ) {
this.style[ k ] = option[ k ];
}
});
}
}
return this;
}
});
J('div').css( 'border', '1px solid blue' ).css( 'width', '400px' );
J('div').css('background', 'green');
console.log(J('div').css('background'));
</script>
获得样式的时候, 应该考虑首先使用 style, 但是如果没有数据
那么就使用 IE currentStyle , 新浏览器中 getComputeStyle
function getStyle( o, name ) {
return o.currentStyle ? o.currentStyle[ name ] : window.getComputedStyle( o )[ name ];
}
jepson.fn.extend( {
css: function( option ) {
var len = arguments.length;
var args = arguments;
if ( len == 2 ) {
// 判断键值
if ( jepson.isString( args[ 0 ] ) && jepson.isString( args[ 1 ] ) ) {
// 两个都是字符串,说明是要设置 css属性
return this.each( function() {
this.style[ args[ 0 ] ] = args[ 1 ];
});
}
} else if ( len == 1 ) {
// 一个参数 字符串就是求值, 对象就是设置
if ( typeof option == 'string' ) {
return this[0].style[ option ] || getStyle( this[ 0 ], option );
} else if ( typeof option == 'object'){
return this.each(function() {
for ( var k in option ) {
this.style[ k ] = option[ k ];
}
});
}
}
return this;
}
});
.addClass 方法
给 dom元素 添加 className 属性
难点在与 className 属性已经有内容
<div class="box clear botton"></div>
添加的类名不能影响原有的名字, 并且如果已经有这个名字了, 就不应该再次添加了
参数: 类名
name: ' c '
class=" c1 "
class=" c1 c c2 "
class=" c "
class=" c1 c2 c "
使用 split 可以完成. 还有一种技巧
(' ' + classTxt + ' ').indexOf( ' ' + name + ' ' ) != -1
...
addClass: function( name ) {
this.each( function( i, v ) {
// 判断有没有
var classTxt = this.className;
if ( classTxt ) {
if ( (" " + classTxt + " ").indexOf(' ' + name + ' ') == -1 ) {
// 没找到
this.className += ' ' + name;
} else {
// 已存在,不用管
}
} else {
// class 都没有
this.className = name;
}
});
}
...
.removeClass
removeClass: function( name ) {
return this.each( function( i, v ) {
var classTxt = this.className;
if ( classTxt ) {
var arr = classTxt.split( ' ' );
// 为什么要从后往前,以防数组长度变化出问题
for ( var i = arr.length - 1; i >= 0; i-- ) {
if ( arr[ i ] === name ) {
arr.splice( i, 1 );
}
}
this.className = arr.join( ' ' );
}
});
}
另一种方式: 正则替换
removeClass: function( name ) {
return this.each( function( i, v ) {
var classTxt = ' ' + this.className + ' ';
var rclassName = new RegExp( ' ' + name + ' ', 'g' );
this.className = classTxt.replace( rclassName, ' ' ).replace( /\s+/g, ' ' ).trim();
});
}
.hasClass
hasClass: function( name ) {
for ( var i = 0; i < this.length; i++ ) {
if ( (' ' + this[ i ].className + ' ').indexOf( ' ' + name + ' ' ) != -1 ) {
return true;
}
}
return false;
}
.toggleClass
toggleClass: function( name ) {
return this.hasClass( name ) ? this.removeClass( name ) : this.addClass( name );
}
属性操作
.attr(), .prop(), .val(), .html(), text()
jepson.fn.extend( {
attr: function ( name, value ) {
if ( value ) {
if ( jepson.isString( name ) && jepson.isString( value ) ) {
return this.each(function() {
this.setAttribute( name, value );
});
}
} else {
if ( jepson.isString( name ) ) {
return this[ 0 ].getAttribute( name );
}
}
return this;
},
prop: function ( name, value ) {
/* 只能更改原有的属性 */
if ( value ) {
if ( jepson.isString( name ) && jepson.isString( value ) ) {
return this.each(function () {
this[ name ] = value;
});
}
} else {
if ( jepson.isString( name ) ) {
return this[ 0 ][ name ];
}
}
return this;
},
val: function ( value ) {
return this.attr( 'value', value );
},
html: function ( html ) {
return this.prop( 'innerHTML', html );
}
});
-> text
1> 将字符串插入到html节点中
2> 读取一个 节点中的 所有的后代节点
<div>123
<div>456</div>
<div>789</div>
0
</div>
text: function( txt ) {
if ( txt ) {
// 传入了内容 插入
return this.each( function( i, v ) {
this.innerHTML = ''; // removeChild 循环
this.appendChild( document.createTextNode( txt + '' ) );
});
} else {
// 遍历节点的子元素,并将文本节点 nodeType 3 加入到数组
var arr = [];
getTxt( this[ 0 ], arr );
return arr.join( ' ' );
}
return this;
function getTxt( node, list ) {
var arr = node.childNodes;
for ( var i = 0; i < arr.length; i++ ) {
if ( arr[ i ].nodeType === 3 ) {
list.push( arr[ i ].nodeValue );
}
if ( arr[ i ].nodeType === 1 ) {
getTxt( arr[ i ], list );
}
}
}
}