2011-03-13 4 views
3

Как мы знаем в SVG, угловой линейный градиент - это установка атрибута x1, x2, y1, y2. Однако, если мы получим только угол,Рассчитать атрибут линейного градиента SVG x1 y1 x2 y2, если мы знаем угол?

1. Как рассчитать результат x1, y1, x2, y2?

2. Правильно ли это для этой формулы tan (angle) = (y2-y1)/(x2-x1)? как я могу рассчитать все параметры.

+1

Очень хороший вопрос. Мне просто нужно разъяснение. Вы также рассматриваете изменение gradientUnit? –

ответ

1

Set x_i, y_i, как если бы угол был 0 градусов и применить вращение с помощью атрибута gradientTransform (gradientTransform="rotate(angle)"),

5

Следующая должны получить вам то, что вам нужно, или близко к нему. Суть в том, что он создает начальную и конечную точки в вашей области вращения, результатом будет набор единичных векторов, которые вы можете использовать (то есть между 0.0 и 1.0). Где inputAngle - это угол, которым вы хотите, чтобы ваш градиент был.

function pointOfAngle(a) { 
    return {x:Math.cos(a), 
      y:Math.sin(a)}; 
} 

function degreesToRadians(d) { 
    return ((d * Math.PI)/180); 
} 

var eps = Math.pow(2, -52); 
var inputAngle = 45; 
var angle = (inputAngle % 360); 
var startPoint = pointOfAngle(degreesToRadians(180 - angle)); 
var endPoint = pointOfAngle(degreesToRadians(360 - angle)); 

// if you want negative values you can remove the following checks 
// but most likely it will produce undesired results 
if(startPoint.x <= 0 || Math.abs(startPoint.x) <= eps) 
    startPoint.x = 0; 

if(startPoint.y <= 0 || Math.abs(startPoint.y) <= eps) 
    startPoint.y = 0; 

if(endPoint.x <= 0 || Math.abs(endPoint.x) <= eps) 
    endPoint.x = 0; 

if(endPoint.y <= 0 || Math.abs(endPoint.y) <= eps) 
    endPoint.y = 0; 

Не знаете, как линейные значения градиента используются для SVG, но вам, возможно, придется умножить на ваш размер элементов ...

x1 = startPoint.x * width 
y1 = startPoint.y * height 
x2 = endPoint.x * width 
y2 = endPoint.y * height 
6

здание прочь JT-Ответим, здесь функция, которая будет делать именно то, что вам нужно в Javascript. Просто вызовите эту функцию, передав элемент и степени как целое число. Я также добавил «left», «right», «up», «down» в качестве необязательных аргументов.

function svg_linear_gradient_direction(element, direction){ 

    if(direction === "left"){ 

     element.setAttributeNS(null, "x1", "100%"); 
     element.setAttributeNS(null, "y1", "0%"); 
     element.setAttributeNS(null, "x2", "0%"); 
     element.setAttributeNS(null, "y2", "0%"); 

    } else if(direction === "right"){ 

     element.setAttributeNS(null, "x1", "0%"); 
     element.setAttributeNS(null, "y1", "0%"); 
     element.setAttributeNS(null, "x2", "100%"); 
     element.setAttributeNS(null, "y2", "0%"); 

    } else if(direction === "down"){ 

     element.setAttributeNS(null, "x1", "0%"); 
     element.setAttributeNS(null, "y1", "0%"); 
     element.setAttributeNS(null, "x2", "0%"); 
     element.setAttributeNS(null, "y2", "100%"); 

    } else if(direction === "up"){ 

     element.setAttributeNS(null, "x1", "0%"); 
     element.setAttributeNS(null, "y1", "100%"); 
     element.setAttributeNS(null, "x2", "0%"); 
     element.setAttributeNS(null, "y2", "0%"); 

    } else if(typeof direction === "number"){ 

     var pointOfAngle = function(a) { 
      return { 
       x:Math.cos(a), 
       y:Math.sin(a) 
      }; 
     } 

     var degreesToRadians = function(d) { 
      return ((d * Math.PI)/180); 
     } 

     var eps = Math.pow(2, -52); 
     var angle = (direction % 360); 
     var startPoint = pointOfAngle(degreesToRadians(180 - angle)); 
     var endPoint = pointOfAngle(degreesToRadians(360 - angle)); 

     if(startPoint.x <= 0 || Math.abs(startPoint.x) <= eps) 
      startPoint.x = 0; 

     if(startPoint.y <= 0 || Math.abs(startPoint.y) <= eps) 
      startPoint.y = 0; 

     if(endPoint.x <= 0 || Math.abs(endPoint.x) <= eps) 
      endPoint.x = 0; 

     if(endPoint.y <= 0 || Math.abs(endPoint.y) <= eps) 
      endPoint.y = 0; 

     element.setAttributeNS(null, "x1", startPoint.x); 
     element.setAttributeNS(null, "y1", startPoint.y); 
     element.setAttributeNS(null, "x2", endPoint.x); 
     element.setAttributeNS(null, "y2", endPoint.y); 
    } 
} 
+0

Это очень хороший код. Занимается многими сложностями. –