css圆角

来源:互联网 发布:传奇霸业轮回数据库 编辑:程序博客网 时间:2024/06/05 15:48
众所周知,比较古老的圆角的做法是通过表格和图像构成。但随着AJAX的流行、CSS + DIV的页面布局技术的风靡,古老的做法显得苍白无力,所以人们不断寻求改进的方法。本文的实现就是一种现在比较流行的做法。


实现原理


其实这种方法的原理很简单——在要圆角的元素的上下堆放一些边缘(MARGIN)不同的<DIV>元素(也有的使用其它元素的,如<B>等,不过原理是一样的),如下图所示:


 
清单1 原理图


接下来的问题就是计算margin的长度。这也不难只要运用一下初中所学的勾股定理便可以求出来,如下图所示:


 
清单2 MARGIN求解图


具体编码


下面该工具类的源码:


 var Corner = {
     // 标志圆角位置的旗标 
    TOP_LEFT:     0x1 ,
    TOP_RIGHT:     0x2 ,
    BOTTOM_LEFT:   0x4 ,
    BOTTOM_RIGHT: 0x8 ,
    ALL:           0xf ,
    
     /* *******************************************************
    * target: 要圆角的目标元素
    * radius: 圆角的半径,默认值为5
    * flags: 圆角位置的旗标或其组合,默认值为全部
    * backgroundColor: 圆角的背景色,默认值为目标元素的背景色
    ******************************************************* */ 
    round: function (target, radius, flags, backgroundColor) {
         var t = $(target);
         var r = radius || 5 ;
         var f = flags || Corner.ALL;
         var c = Element.getStyle(t, 'backgroundColor');
         var b = backgroundColor || c;
        
         // 修正在IE里元素样式为FLOAT时,圆角DIV宽度为0的BUG 
         var ft = Element.getStyle(t, ' float ');
         if (navigator.appVersion.match( / \bMSIE\b / ) && ft != 'none' && ! t.style.width) {            
            Element.setStyle(t, { width: Element.getWidth(t) + 'px' } );
        } 
        
         // 创建DIV,并把目标元素的内容剪切到其中 
         var d = document.createElement('div');          
        d.innerHTML = t.innerHTML;
        t.innerHTML = '';        
        
         // 设置新DIV的背景色为目标元素的背景色,并目标元素为透明背景 
        Element.setStyle( d, { backgroundColor: c } );      
        Element.setStyle( t, { backgroundColor: 'transparent' } );      
        
         // 设置新DIV的高度为目标元素的高度 
         var h = t.style.height;
         var nh = 0 ;
         if (h) {
            Element.setStyle( d, { height: h } );
            nh = parseInt(h);
        }                    
        
         // 设置新DIV的缩进 
         var p = Element.getStyle(t, 'padding');
         if (p) {
            Element.setStyle( d, { padding: p } );            
            Element.setStyle( t, { padding: '0px 0px 0px 0px' } );
        }          
        
         // 创建用于新DIV和圆角DIV的文档片段,这样避免每次设置元素样式或添加新元素时重绘页面,提高效率 
         var ds = document.createDocumentFragment();                
         var ls = null ;
         // 创建顶部圆角DIV 
         if (f & (Corner.TOP_LEFT | Corner.TOP_RIGHT)) {
            ls = Corner._createRoundFragment(r, f, b , false );            
            ds.appendChild(ls);             
            nh += r;
        }        
        
        ds.appendChild(d);
        
         // 创建底部圆角DIV 
         if (f & (Corner.BOTTOM_LEFT | Corner.BOTTOM_RIGHT)) {
            ls = Corner._createRoundFragment(r, f, b, true );            
            ds.appendChild(ls); 
            nh += r;
        }  
        
         if (h) {
            Element.setStyle( t, { height: nh + 'px' } );      
        }        
        
        t.appendChild(ds);   
    } ,
    
    _createRoundFragment: function (r, f, c, b) {
         var ls = document.createDocumentFragment();
         var l = null ;
         var m = ml = mr = null ;
         var j = 0 ;
         for (i = 1 ; i <= r; i ++ ) {
            l = document.createElement('div');
            
             // 计算margin 
            j = b ? i : r - i + 1 ;
            m = Math.sqrt(r * r - j * j);            
            m = Math.round(r - m) + 'px';
            
             if (b) {
                ml = f & Corner.BOTTOM_LEFT ? m : '0px';
                mr = f & Corner.BOTTOM_RIGHT ? m : '0px';            
            } else {
                ml = f & Corner.TOP_LEFT ? m : '0px';
                mr = f & Corner.TOP_RIGHT ? m : '0px';            
            } 
            Element.setStyle( l, { backgroundColor: c,
                                   fontSize: '1px',
                                   height: '1px',                                   
                                   marginLeft: ml,
                                   marginRight: mr,
                                   overflowX: 'hidden',
                                   overflowY: 'hidden' } );
            ls.appendChild(l);
        } 
         return ls;
    } 
}
清单3 实现代码
因为Javascript是没有方法重写的,所以当你调用Corner.round('div1')和调用Coner.round('div1', 20)是一样的,它们最终调用的都是Corner.round(target, radius, flags, backgroundColor),只过没有赋值的参数会为undefined。这里有一个小技巧,就var r = radius || 5,这里的“||”符号表示如果radius为undefined、null或0等值时,r的取值为5。


接着让我们看看运行的页面代码:


<! DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd" > 
< html xmlns ="http://www.w3.org/1999/xhtml" > 
< head > 
    < title > RounderCorner Prototype </ title >   
    < script type ="text/javascript" src ="scripts/prototype-1.5.0.js" ></ script > 
    < script type ="text/javascript" src ="scripts/Corner.js" ></ script > 
    < script type ="text/javascript" > 
    // <![CDATA[       
    Event.observe(window, 'load', init, false );
    
    function init() {        
        Corner.round('div1');
        Corner.round('div2', 20 , Corner.TOP_LEFT | Corner.BOTTOM_RIGHT);
        Corner.round('div3', 20 , Corner.ALL, 'Red');
    }


    // ]]> 
    </ script >    
</ head > 
< body > 
    < div id ="div1" style ="width: 318px; height: 103px; background-color: #ffcccc" > 
        Corner.round('div1'); </ div > 
    < br /> 
    < div id ="div2" style ="width: 317px; height: 100px; background-color: #cccccc" > 
        Corner.round('div2', 20, Corner.TOP_LEFT | Corner.BOTTOM_RIGHT); </ div > 
    < br /> 
    < div id ="div3" style ="width: 315px; height: 100px; background-color: #ccffcc" > 
        Corner.round('div3', 20, Corner.ALL, 'Red'); </ div > 


</ body > 
</ html >
原创粉丝点击