【问题标题】:How to exact set a dynamic style transform using Javascript?如何使用 Javascript 精确设置动态样式转换?
【发布时间】:2013-11-09 15:46:33
【问题描述】:

我知道设置变换的方法,但我想设置旋转并保留其他参数,例如缩放和倾斜。

或许,我们可以写一个函数为:

// A variable of element, not parameter. separate out it make more clear.
var el = document.getElementById('el');
function setTransform (p_name, p_value) {
  // how to write some code to set the el transform style...
}

此外,我还有一个元素:

<div id="el" style="transform: rotate(45deg) skew(45deg);"></div>

还有我们的函数 setTransform:

setTransform('rotate', '30deg');

我希望元素是这样的:

<div id="el" style="transform: rotate(30deg) skew(45deg);"></div>

所以我的问题是setTransform函数的内容怎么写?

【问题讨论】:

    标签: javascript css transform css-transforms


    【解决方案1】:

    注意:您应该使用 skewX 和/或 skewY 而不是 skew。见the MDN info here

    跟踪变量中的转换会更容易:

    var elRot,    // the rotation 'counter' for the element 'el'
        elScale,  // the scale 'counter' for the element 'el'
        elSkewX,  // the skewX 'counter' for the element 'el'
        elSkewY;  // the skewY 'counter' for the element 'el'
    
    // initialize values
    elRot = 0;
    elScale = 1;
    elSkewX = 0;
    elSkewY = 0;
    

    或一个对象:

    var elTranform = {
        rot: 0,   // the rotation 'counter' for the element 'el'
        sca: 1,   // the scale 'counter' for the element 'el'
        skx: 0,   // the skewX 'counter' for the element 'el'
        sky: 0    // the skewY 'counter' for the element 'el'
    };
    

    所以现在你可以从函数开始(你仍然会使用 var el 作为元素),第一步是获取值,所以你改变给函数的参数:

    // use this with separate vars
    function setTransform (element, rotationArg, scaleArg, skewXArg, skewYArg) {
        // how to write some code to set the el transform style...
    }
    
    // use this with the object
    function setTransform (element, elTransformArg) {
        // how to write some code to set the el transform style...
    }
    

    接下来,您需要重新指定“停留”的任何其他变换,在您给出的示例中,skewX 保持 45 度:

    function setTransform (element, rotationArg, scaleArg, skewXArg, skewYArg) {
        // the brackets cause the string to be evaluated before being assigned
        element.style.transform = ("rotate() scale() skewX() skewY()");
    }
    

    function setTransform (element, elTransformArg) {
        element.style.transform = ("rotate() scale() skewX() skewY()");
    }
    

    现在您必须将参数放入字符串中:

    function setTransform (element, rotationArg, scaleArg, skewXArg, skewYArg) {
        element.style.transform = ("rotate(" + rotationArg + "deg ) scale(" + scaleArg
            + ") skewX(" + skewXArg + "deg ) skewY(" + skewYArg + "deg )");
    }
    

    function setTransform (element, elTransformArg) {
        element.style.transform = ("rotate(" + elTransformArg.rot + "deg ) scale("
            + elTransformArg.sca + ") skewX(" + elTransformArg.skx + "deg ) skewY("
            + elTransformArg.sky + "deg )");
    }
    

    有点乱,所以把那个字符串放在一个变量中(这将有利于前缀):

    function setTransform (element, rotationArg, scaleArg, skewXArg, skewYArg) {
        var transformString = ("rotate(" + rotationArg + "deg ) scale(" + scaleArg
            + ") skewX(" + skewXArg + "deg ) skewY(" + skewYArg + "deg )");
        
        // now attach that variable to each prefixed style
        element.style.webkitTransform = transformString;
        element.style.MozTransform = transformString;
        element.style.msTransform = transformString;
        element.style.OTransform = transformString;
        element.style.transform = transformString;
    }
    

    function setTransform (element, elTransformArg) {
        var transformString= ("rotate(" + elTransformArg.rot + "deg ) scale("
            + elTransformArg.sca + ") skewX(" + elTransformArg.skx + "deg ) skewY("
            + elTransformArg.sky + "deg )");
        
        // now attach that variable to each prefixed style
        element.style.webkitTransform = transformString;
        element.style.MozTransform = transformString;
        element.style.msTransform = transformString;
        element.style.OTransform = transformString;
        element.style.transform = transformString;
    }
    

    现在调用函数:

    setTransform(el, elRot, elScale, elSkewX, elSkewY);
    

    setTransform(el, elTransform);
    

    要更改值,请更改变量或对象值并调用:

    elRot = 45;
    elSkewX = 30;
    setTransform(el, elRot, elScale, elSkewX, elSkewY);
    

    elTransform.rot = 45;
    elTransform.skx = 30;
    setTransform(el, elTransform);
    

    这样您只需更改每个变换的“计数器”值,然后调用函数来应用变换。如上所述,保留任何未更改的变换很重要,因为这只是用新的变换替换了以前的 CSS 值。给出多个值意味着只使用最后一个值(CSS 的 C 部分)。

    【讨论】:

    • 只想指出,在那个 MDN 页面上有一条注释说:“Gecko 14.0 删除了对 skew() 的实验性支持,但出于兼容性原因,它在 Gecko 15.0 中重新引入。作为它是非标准的,将来可能会被删除,请不要使用它。”
    【解决方案2】:

    这里绝对最好的答案是一个真正的 API,它允许我们影响计算样式的任何现有值,而无需解析值。这样的事情以WebkitCSSMatrix API 和W3C“官方”等效DOMMatrix 的一些废弃和非跨浏览器形式存在。我已经看到有关重新格式化和合并这两个 API 的讨论,但他们似乎并没有就实现达成一致。这里有一个 shim 可以让它跨浏览器工作:CSSMatrix class from github user arian

    它的工作原理是您可以将计算出的转换字符串(例如:"translsate3d(0px, 0px, 100px) scale(1.2) skew(2)")传递给它,然后它会返回一个您可以使用旋转、转换、平移、倾斜函数操作的对象。每个函数都返回一个现有的具有新操作值的自身实例,您可以简单地将其“toString”值重新应用于元素样式属性。

    很多话,但这里有一个例子(Chrome 和 Safari 只因为 WebkitCSSMatrix 的使用):

    var computedStyle = window.getComputedStyle(document.querySelector('.btn'));
    var matrix = new WebKitCSSMatrix(computedStyle.transform);
    
    // Every second, we add +6 degrees of rotation, no need to read the initial value since WebkitCSSMatrix has parsed it for us
    window.setInterval(function(){
      matrix = matrix.rotate(6);
      // matrix = matrix.translate(2, 0, 0);
      // matrix = matrix.scale(1.8);
      document.querySelector('.btn').style.transform = matrix.toString();
    }, 1000);
    body{
    			padding-top: 100px;
    			text-align: center;
    		}
    
    		.btn{
    			text-transform: uppercase;
    			border-radius:200%;
    			border:1px solid #000;
    			width: 2em;
    			height: 2em;
    			display: inline-block;
    			text-align: center;
    			line-height: 2em;
    			text-decoration: none;
    			font-family: sans-serif;
    			color: #000;
          
          // It is already rotated and scaled
    			transition: transform 1000ms cubic-bezier(.28,.73,.31,1);
          transform: rotate(45deg);
          -webkit-transform: rotate(45deg);
    		}
    
    		.btn:hover{
    			background:#000;
    			color:#fff;
          
          transform: rotate(0deg) scale(1.5);
    		}
    &lt;a class="btn" href="#"&gt;|&lt;/a&gt;

    【讨论】:

      【解决方案3】:

      以下内容可能会对您有所帮助...

      el.style.webkitTransform = "";
      el.style.MozTransform = "";
      el.style.msTransform = "";
      el.style.OTransform = "";
      el.style.transform = "";
      

      【讨论】:

      • 没有帮助。我知道浏览器供应商前缀。我只想设置旋转并保持倾斜等。请仔细阅读我的问题。
      • 哦..您可能需要围绕它进行一些字符串操作。
      • 正则表达式?没有别的办法也没关系。
      猜你喜欢
      • 2010-10-17
      • 2017-06-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-03-09
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多