X-Git-Url: http://git.osdn.jp/view?a=blobdiff_plain;f=0.6.x%2Fjs%2F02_dom%2F06_XNodeCSS.js;h=77bb0675073318ccbf3cd0b574a2c41f46ba89d6;hb=d56e8cc1e13089eb6cbc9dcc6900d7f1828b93df;hp=28e337d716a901887828009e8f1adf9c0096df96;hpb=9ba2ba4de00464f81805b28dfcab8814a46da5e5;p=pettanr%2FclientJs.git diff --git a/0.6.x/js/02_dom/06_XNodeCSS.js b/0.6.x/js/02_dom/06_XNodeCSS.js index 28e337d..77bb067 100644 --- a/0.6.x/js/02_dom/06_XNodeCSS.js +++ b/0.6.x/js/02_dom/06_XNodeCSS.js @@ -246,7 +246,7 @@ function X_Node_CSS_parseColor( x ){ function X_Node_CSS_objToCssText( that, skipFilter ){ var obj = that[ '_css' ], - plain = X_EMPTY_OBJECT, + //plain = X_EMPTY_OBJECT, css = [], n = -1, p, v, specialFix, filterFix; @@ -260,7 +260,7 @@ function X_Node_CSS_objToCssText( that, skipFilter ){ for( p in obj ){ // object の拡張に備えて plain なオブジェクトを用意し、そのメンバーと一致するものは処理の対象外。 - if( plain[ p ] ) continue; + //if( plain[ p ] ) continue; v = obj[ p ]; @@ -277,7 +277,8 @@ function X_Node_CSS_objToCssText( that, skipFilter ){ }; if( filterFix ){ - v = X_Node_CSS_objToIEFilterText( that, filterFix ); + v = X_Node_CSS_objToIEFilterText( that, filterFix, css ); + n = css.length; /* css が変更されている場合あり */ if( v ){ css[ ++n ] = 'filter:' + v; }; @@ -289,6 +290,7 @@ function X_Node_CSS_objToCssText( that, skipFilter ){ if( 0 <= n ){ // cssText には完全なものを控えるが、戻すのは filter を抜いたもの that[ '_cssText' ] = css.join( ';' ); + //console.log( that[ '_cssText' ] ); if( skipFilter ){ --css.length; return css.join( ';' ); @@ -303,10 +305,11 @@ var X_Node_CSS_FILTER_FIX_PROPS = X_UA[ 'ActiveX' ] && X_UA[ 'IE' ] < 9 ? { - 'opacity' : 2, - 'boxShadow' : 3, - 'textShadow' : 4, - 'transform' : 5 + 'opacity' : 2, + 'boxShadow' : 3, + 'textShadow' : 4, + 'transform' : 5, + 'dxtransform' : 7 // X.NodeAnime で使用 } : X_UA[ 'ActiveX' ] && X_UA[ 'IE9' ] ? // == 9 { @@ -314,15 +317,16 @@ X_Node_CSS_FILTER_FIX_PROPS = } : null; -function X_Node_CSS_objToIEFilterText( that, opt_css ){ +function X_Node_CSS_objToIEFilterText( that, opt_css, opt_cssList ){ var obj = opt_css || that[ '_css' ], test = X_Node_CSS_FILTER_FIX_PROPS, filters = [], n = -1, - p, id, v, num, ary, params, i, l, dir, - afterUpdate, impossible; + p, id, v, num, vu, u, _v, ary, params, i, l, dir, + afterUpdate, impossible, color; + for( p in obj ){ - if( X_EMPTY_OBJECT[ p ] ) continue; + //if( X_EMPTY_OBJECT[ p ] ) continue; if( !( id = test[ p ] ) ) continue; v = obj[ p ]; @@ -332,7 +336,11 @@ function X_Node_CSS_objToIEFilterText( that, opt_css ){ filters[ ++n ] = v; break; case 2 : //'opacity' : - if( v !== 1 ) filters[ ++n ] = 'alpha(opacity=' + ( v * 100 | 0 ) +')'; + if( v === 0 ){ + console.log( '@opacity:0 ' + !!opt_cssList ); + opt_cssList && ( opt_cssList[ opt_cssList.length ] = 'visibility:hidden' ); + } else + if( v < 1 ) filters[ ++n ] = 'alpha(opacity=' + ( v * 100 | 0 ) +')'; break; case 3 : //'boxShadow' : // TODO カンマ区切りの複数指定 @@ -398,25 +406,131 @@ function X_Node_CSS_objToIEFilterText( that, opt_css ){ X_ViewPort[ 'listenOnce' ]( X_EVENT_AFTER_UPDATE, that, X_Node_CSS_onAfterUpdateForIEFilterFix ); break; }; - dir = Math.atan2( params[ 1 ] + params[ 3 ], params[ 0 ] + params[ 3 ] ) * 180 / Math.PI + 90; - dir += dir < 0 ? 360 : 0; + dir = X_Node_CSS_ieMathRangeFix( Math.atan2( params[ 1 ] + params[ 3 ], params[ 0 ] + params[ 3 ] ) * 180 / Math.PI + 90 ); filters[ ++n ] = 'shadow(color=' + color + ',strength=' + params[ 3 ] + ',direction=' + ( dir | 0 ) + ')'; break; case 4 : //'textShadow' : //text-shadow: 5px 5px 2px blue; 水平方向の距離 垂直方向の距離 影のぼかし半径 影の色 none //glow(Color=yellow,Strength=10); - //どうやらCSSのbackgroundプロパティと同時に使えないようです。 s + //どうやらCSSのbackgroundプロパティと同時に使えないようです。 break; case 6 : //'backgroundImage' : // - + break; + case 5 : // transform scale, matrix - + break; + case 7 : // dxtransform + that[ '_flags' ] |= X_NodeFlags_IE_FILTER_FIX_AFTER; + break; + }; + }; + return filters.join( ' ' );//n !== -1 ? filters.join( ' ' ) : ''; +}; + + + //0 ~ 360の範囲に収める. + function X_Node_CSS_ieMathRangeFix( a ){ + a %= 360; + return a < 0 ? 360 + a : a; + }; + +/* + * http://p2b.jp/200912-CSS3-Transform-for-IE8 + * http://rtilabs.rti-giken.jp/files/2011_09_16/rotate.html + */ + function X_Node_CSS_IETransform( elm, params ){ + var PI_180 = Math.PI / 180, + + rotate = X_Node_CSS_ieMathRangeFix( params[ 2 ] ),//回転 + radian = rotate * PI_180, + cosX = Math.cos( radian ), + sinY = Math.sin( radian ), + + skewX = X_Node_CSS_ieMathRangeFix( params[ 3 ] ), //skew + skewY = X_Node_CSS_ieMathRangeFix( params[ 4 ] ), + + _skX = Math.tan( skewX * PI_180 ), + _skY = Math.tan( skewY * PI_180 ), + + scaleX = params[ 5 ], //拡大 + scaleY = params[ 6 ], + + m11 = cosX * scaleX, + m12 = ( -sinY + _skX ) * scaleX, + m21 = ( sinY + _skY ) * scaleY, + m22 = cosX * scaleY, + + //absolute時には軸を補正してあげないとだめだ。 + //ブラウザとして軸がずれている。 + //計算式元ネタ http://p2b.jp/200912-CSS3-Transform-for-IE8 + + //offset*系のサイズは回転によって生じたゆがみも考慮されるらしい。 + + //拡大縮小も同じ. + //this.get(0).style.width や height には拡縮の影響を受けない元の数字が入っている + ow = elm.offsetWidth, + oh = elm.offsetHeight, + + absCosX = Math.abs( cosX ), + absSinY = Math.abs( sinY ), + + //回転の補正 + dx = ( ow - ( ow * absCosX + oh * absSinY ) ) / 2 + //skewの補正(rotate しながらskew すると補正がおかしくなります。 これがわからない) + - ow / 2 * _skX + //拡大の補正 + - ( ( ow * scaleX - ow ) / 2 | 0 ) + // x + + params[ 0 ], + dy = ( oh - ( ow * absSinY + oh * absCosX ) ) / 2 + //skewの補正( + - oh / 2 * _skY + //拡大の補正 + - ( ( oh * scaleY - oh ) / 2 | 0 ) + // y + + params[ 1 ]; + + //console.log( ow + ' ' + oh ) + elm.style[ params[ 7 ] ] = dx + 'px'; // left or right + elm.style[ params[ 8 ] ] = dy + 'px'; // top or bottom + + //フィルターで回転と拡大縮小を加えます。 + return 'progid:DXImageTransform.Microsoft.Matrix(' + + // 'Dx=' + dx + + //',Dy=' + dy + + 'M11=' + m11 + + ',M12=' + m12 + + ',M21=' + m21 + + ',M22=' + m22 + + ',FilterType="bilinear",sizingMethod="auto expand")'; + }; + +function X_Node_CSS_onAfterUpdateIEFilterFix( that ){ + var PI_180 = Math.PI / 180, + test = X_Node_CSS_FILTER_FIX_PROPS, + css = that[ '_css' ], + elm = that[ '_rawObject' ], + filter = elm.style.filter || '', + origin = filter, + p, v, plus, id; + + for( p in css ){ + if( !( id = test[ p ] ) ) continue; + plus = 0; + switch( id ){ + case 7 : // dxtransform + plus = X_Node_CSS_IETransform( elm, css[ p ] ); + break; + default : + continue; }; + if( plus ) filter += ( filter ? ' ' : '' ) + plus; }; - return filters.join( ' ' ); + if( filter !== origin ) elm.style.filter = filter; }; + function X_Node_CSS_onAfterUpdateForIEFilterFix(){ if( this[ '_flags' ] & X_NodeFlags_IN_TREE ){ // 要素があり、要素がツリーに属している this[ '_flags' ] |= X_NodeFlags_DIRTY_IE_FILTER; @@ -528,11 +642,11 @@ function X_Node_css( nameOrObj /* value */ ){ // setter:object if( X_Type_isObject( nameOrObj ) ){ if( !css ) css = this[ '_css' ] = {}; - plain = X_EMPTY_OBJECT; + //plain = X_EMPTY_OBJECT; camelize = X_Node_CSS_camelize; flags = this[ '_flags' ]; for( p in nameOrObj ){ - if( plain[ p ] ) continue; + //if( plain[ p ] ) continue; name = camelize( p ); v = nameOrObj[ p ]; if( css[ name ] === v ) continue; @@ -670,7 +784,7 @@ function X_Node_cssText( v ){ }; /* - * ここでは HTMLElement のチ1ェックは行わない! + * ここでは HTMLElement のチ1ェックは行わない! <- 行う! * TODO * body に css attr がセットされた場合には X_ViewPort_baseFontSize をクリア * class, id, attr() の変更があった場合は、変更の適用の後、charSize を取得 @@ -684,12 +798,13 @@ X_Node_CSS_getCharSize = X_Node_updateTimerID && X_Node_startUpdate(); if( that === X_Node_body && X_ViewPort_baseFontSize ) return X_ViewPort_baseFontSize; if( that[ '_fontSize' ] ) return that[ '_fontSize' ]; - return that[ '_fontSize' ] = parseFloat( X_Node_CSS_getComputedStyle( that[ '_rawObject' ], null ).fontSize ); + return that[ '_fontSize' ] = that[ '_rawObject' ] ? parseFloat( X_Node_CSS_getComputedStyle( that[ '_rawObject' ], null ).fontSize ) : 0; }) : 5 <= X_UA[ 'IE' ] ? (function( that ){ var font, vu, v, u, _v; + X_Node_updateTimerID && X_Node_startUpdate(); if( that === X_Node_body && X_ViewPort_baseFontSize ) return X_ViewPort_baseFontSize; if( that[ '_fontSize' ] ) return that[ '_fontSize' ]; @@ -734,11 +849,12 @@ X_Node_CSS_getCharSize = }) : X_UA_DOM.IE4 ? (function( that ){ - var font, vu, v, u, _v; + var font, vu, v, u, _v, elm; + X_Node_updateTimerID && X_Node_startUpdate(); if( that === X_Node_body && X_ViewPort_baseFontSize ) return X_ViewPort_baseFontSize; if( that[ '_fontSize' ] ) return that[ '_fontSize' ]; - + if( that[ '_css' ] && ( font = that[ '_css' ].fontSize ) ){ vu = X_Node_CSS__splitValueAndUnit( font ); v = vu[ 0 ]; @@ -750,7 +866,7 @@ X_Node_CSS_getCharSize = if( _v = X_Node_CSS__UNIT_RATIO[ u ] ) return that[ '_fontSize' ] = v / _v; }; } else { - // 要素を生成して測定! + // TODO 要素を生成して測定! ではなくて elm.style.fontSize が使えそう ( that[ '_rawObject' ] || X_Node__ie4getRawNode( that ) ).insertAdjacentHTML( 'BeforeEnd', '
X
' ); elm = document.all[ 'ie4charsize' ]; v = elm.offsetHeight; @@ -831,7 +947,7 @@ X[ 'CSS' ] = { for( j = vendors.length; j; ){ v = vendors[ --j ]; if( testStyle[ v + prop ] !== undefined ){ - if( v === 'ms' && !( 10 <= X_UA[ 'IEHost' ] ) ) v = 'Ms';// for ie9, 但し ie11 のieには不要 + if( v === 'ms'/* && !( 10 <= X_UA[ 'IEHost' ] )*/ ) v = 'Ms';// for ie9, 但し ie11 のieには不要 if( v === 'o' ) v = 'O';//for opera12 X_Node_CSS_VENDER_PREFIX[ search ] = v + prop; break;