Javascript x:data.x+data.rx, y:数据,y, 名称:“ne” }, { x:data.x+data.rx, y:data.y+data.ry/2, 名称:“e” }, { x:data.x+data.rx, y:data.y+data.ry, 名称:“se” }, { x:data.x+data.rx/2, y:data.y+data.ry, 姓名:“s” }, { x:data.x, y:data.y+data.ry, 名称:“西南” }, { x:data.x, y:data.y+data.ry/2, 名称:“w” } ]; var bounderAttrs={ x:$element.attr('x'), y:$element.attr('y'), 宽度:$element.attr('width'), 高度:$element.attr('height'), }; $('#console#x').text($element.attr('x')+“px”); $('#console#y').text($element.attr('y')+“px”); $(“#控制台#宽度”).text(bounderAttrs.width); $(“#控制台#高度”).text(bounderAttrs.height?bounderAttrs.height+“px”:“自动缩放”); 如果($element.parent()是('g#active_group')){ $element.parent().find('.active control border').attr(bounderAttrs); $。每个(控件、功能(i、o){ 如果(o.name=='center'){ $(“#控制台#中心”).text(JSON.stringify({x:o.x+“px”,y:o.y+“px})); } $element.parent().find('circle.active control-'+o.name).attr({ cx:o.x, 西:好的 }); }); 返回; } } //从变换属性获取元素角度 函数getAngle(elem){ var角=0; var trans=变压器2阵列(elem); if(!Object.values(trans.length){ trans=transform2Array(elem.parent()); } if(trans.rotate!=未定义){ 角度=浮动(横向旋转[0]); } 返回角; } /** *将变换属性值获取为array transform=“旋转(x,y,z)比例(x,y)” *返回{ *旋转:[x,y,z] *比例:[x,y] * } */ 功能转换阵列(elem){ var transform=$(elem.attr('transform'); var变换={}; if(typeof transform!=“未定义”){ $.each(transform.split(“”),函数(i,o){ 如果(o.长度){ var trans=o.replace('),'').split('('); 转换[trans[0]]=[]; var params=trans[1]。拆分(','); $.each(参数、函数(i、o_参数){ 转换[trans[0]].push(parseFloat(o_参数)); }); } }); } 回归变换; } updateControl($('image'))

Javascript x:data.x+data.rx, y:数据,y, 名称:“ne” }, { x:data.x+data.rx, y:data.y+data.ry/2, 名称:“e” }, { x:data.x+data.rx, y:data.y+data.ry, 名称:“se” }, { x:data.x+data.rx/2, y:data.y+data.ry, 姓名:“s” }, { x:data.x, y:data.y+data.ry, 名称:“西南” }, { x:data.x, y:data.y+data.ry/2, 名称:“w” } ]; var bounderAttrs={ x:$element.attr('x'), y:$element.attr('y'), 宽度:$element.attr('width'), 高度:$element.attr('height'), }; $('#console#x').text($element.attr('x')+“px”); $('#console#y').text($element.attr('y')+“px”); $(“#控制台#宽度”).text(bounderAttrs.width); $(“#控制台#高度”).text(bounderAttrs.height?bounderAttrs.height+“px”:“自动缩放”); 如果($element.parent()是('g#active_group')){ $element.parent().find('.active control border').attr(bounderAttrs); $。每个(控件、功能(i、o){ 如果(o.name=='center'){ $(“#控制台#中心”).text(JSON.stringify({x:o.x+“px”,y:o.y+“px})); } $element.parent().find('circle.active control-'+o.name).attr({ cx:o.x, 西:好的 }); }); 返回; } } //从变换属性获取元素角度 函数getAngle(elem){ var角=0; var trans=变压器2阵列(elem); if(!Object.values(trans.length){ trans=transform2Array(elem.parent()); } if(trans.rotate!=未定义){ 角度=浮动(横向旋转[0]); } 返回角; } /** *将变换属性值获取为array transform=“旋转(x,y,z)比例(x,y)” *返回{ *旋转:[x,y,z] *比例:[x,y] * } */ 功能转换阵列(elem){ var transform=$(elem.attr('transform'); var变换={}; if(typeof transform!=“未定义”){ $.each(transform.split(“”),函数(i,o){ 如果(o.长度){ var trans=o.replace('),'').split('('); 转换[trans[0]]=[]; var params=trans[1]。拆分(','); $.each(参数、函数(i、o_参数){ 转换[trans[0]].push(parseFloat(o_参数)); }); } }); } 回归变换; } updateControl($('image')),javascript,jquery,html,svg,resize,Javascript,Jquery,Html,Svg,Resize,) <svg width="400" height="400" transform="scale(1)"> <rect id="_svg_editor_background_" fill="#fafafa" width="100%" height="100%"></rect> <g id="active_group" transform=""> <rect x="100" y="138" width="200" heig

)

   <svg width="400" height="400" transform="scale(1)">
  <rect id="_svg_editor_background_" fill="#fafafa" width="100%" height="100%"></rect>
  <g id="active_group" transform="">
    <rect x="100" y="138" width="200" height="125" stroke-width="2" stroke="red" fill="transparent" class="active-control-border" pointer-events="none"></rect>
    <image xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://eskipaper.com/images/berries-nature-winter-1.jpg" preserveAspectRatio="none" x="100" y="138.5" width="200px" class=""></image>
    <circle cx="200" cy="200.5" r="6" fill="rgba(33, 150, 243, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-center" style="null"></circle>
    <circle cx="200" cy="118" r="6" fill="rgba(150, 243, 33, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-rotator" style="cursor: crosshair;"></circle>
    <circle cx="100" cy="138" r="6" fill="rgba(33, 150, 243, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-nw" style="cursor: nw-resize;"></circle>
    <circle cx="200" cy="138" r="6" fill="rgba(243, 150, 33, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-n" style="cursor: n-resize;"></circle>
    <circle cx="300" cy="138" r="6" fill="rgba(33, 150, 243, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-ne" style="cursor: ne-resize;"></circle>
    <circle cx="300" cy="200.5" r="6" fill="rgba(243, 150, 33, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-e" style="cursor: e-resize;"></circle>
    <circle cx="300" cy="263" r="6" fill="rgba(33, 150, 243, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-se" style="cursor: se-resize;"></circle>
    <circle cx="200" cy="263" r="6" fill="rgba(243, 150, 33, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-s" style="cursor: s-resize;"></circle>
    <circle cx="100" cy="263" r="6" fill="rgba(33, 150, 243, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-sw" style="cursor: sw-resize;"></circle>
    <circle cx="100" cy="200.5" r="6" fill="rgba(243, 150, 33, 0.6)" strokeWidth="1" stroke="slateblue" class="active-control-w" style="cursor: w-resize;"></circle>
  </g>
</svg>
<div id="console">
X: <span id="x">0px</span><br>
Y: <span id="y">0px</span><br>
Width: <span id="width">0px</span><br>
Height: <span id="height">0px</span><br>
Center: <span id="center">0px</span><br>
Rotation: <span id="rot">0deg</span><br>
Rotation Center: <span id="rotcenter">{x:0px,y:0px}</span><br>

</div>
    #console{
  position:absolute;
  bottom:10px;
  left:10px;
}
//DRAGGING 
$('image').mousedown(function(e){

if (!$(this).is('[class^=active-control-]') && !$(e.target).is('[class^=active-control-]')) {
    var elem = this;
    if ($(this).is('g#active_group')) {
        elem = $(this).find(':not([class^=active-control-])').get(0);
    }

    var pageX0 = e.pageX;
    var pageY0 = e.pageY;

    var init_scale = {width: elem.getBBox().width, height: elem.getBBox().height};
    var init_offset = {x: parseInt($(elem).attr('x')), y: parseInt($(elem).attr('y'))};

    function handle_dragging(e) {

        var x = init_offset.x + (e.pageX - pageX0);
        var y = init_offset.y + (e.pageY - pageY0);


        //change center of rotation to match new element center when dragging
        var trans = transform2Array(elem);
        if (!Object.values(trans).length) {
            trans = transform2Array($(elem).parent());
        }
        var transform = "";
        if (trans.rotate != undefined) {
            var rot_cx = x + init_scale.width / 2;
            var rot_cy = y + init_scale.height / 2;
            transform += "rotate(" + trans.rotate[0] + "," + rot_cx + "," + rot_cy + ")";
        }
        $(elem).attr({x: x, y: y});
        //fix bug rotate +90 drag rotate clear  select& drag => rotate svg element !
        if ($(elem).parent().is('g#active_group'))
            $(elem).parent().attr({transform: transform});
        updateControls($(elem));//update controls to match the new position
    }

    function handle_mouseup(e) {

        $('body')
            .off('mousemove', handle_dragging)
            .off('mouseup', handle_mouseup);
    }

    $('body')
        .on('mouseup', handle_mouseup)
        .on('mousemove', handle_dragging);
}

});
//END OF DRAGGING

$('circle[class^=active-control-]').mousedown(function(md_e) {
  var $control = $(this);
  var $element = $('image:first');
  var control_name = $(this).attr('class').replace('active-control-', '').trim();
  var pageX0 = md_e.pageX;
  var pageY0 = md_e.pageY;
  var init_offset = {
    x: $element.get(0).getBBox().x,
    y: $element.get(0).getBBox().y
  };
  var init_scale = {
    width: $element.get(0).getBBox().width,
    height: $element.get(0).getBBox().height
  };

  console.log('im dragging from ' + control_name);

  function handle_dragging(d_e) {
    if (control_name == 'rotator') {
      //rotate fix source: https://stackoverflow.com/questions/32640642/svg-angle-rotation-by-mousemove-touchmove-bug
      var rx = parseFloat($element.get(0).getBBox().width);
      var ry = parseFloat($element.get(0).getBBox().height);
      var ctm = $element.get(0).getScreenCTM()
      var p = $('svg').get(0).createSVGPoint()

      p.x = d_e.clientX
      p.y = d_e.clientY
      p = p.matrixTransform(ctm.inverse())

      var elem_center_x = init_offset.x + rx / 2;
      var elem_center_y = init_offset.y + ry / 2;
      var radians = Math.atan2(elem_center_x - p.x, elem_center_y - p.y);
      var degree = (radians * (180 / Math.PI) * -1) + 0;

      var new_angle = (getAngle($element) + degree);
      if (new_angle > 360) {
        new_angle -= 360;
      }
      if (new_angle < -360) {
        new_angle += 360;
      }
      $('#console #rot').text(new_angle+"deg");
      $('#console #rotcenter').text(JSON.stringify({x:elem_center_x+"px",y:elem_center_y+"px"}));
      if ($element.parent().is('g#active_group') || $element.is('g#active_group')) {
        $element.parent()
          .attr("transform", "rotate(" + new_angle + "," + elem_center_x + "," + elem_center_y + ")");
      }
    } else {
      makeResize(control_name[0]);
      if (control_name.length == 2) {
        makeResize(control_name[1]);
      }
    }
    updateControls($element);

    function makeResize(direction) {
      var dx = d_e.pageX - pageX0;
      var dy = d_e.pageY - pageY0;
      //do resizing here for each control while image is rotated at any angle
      //change width, height, and coords(x,y)
      switch (direction) {
        case "e":
          $element.attr('width', Math.max(init_scale.width + dx, 10));
          break;
        case "w":
          if ($element.attr('width') != 10)
        $element.attr('x', init_offset.x + dx);
            $element.attr('width', Math.max(init_scale.width - dx, 10));
            break;
        case "s":
          $element.attr('height', Math.max(init_scale.height + dy, 10));
          break;
        case "n": //
          if ($element.attr('height') != 10)
            $element.attr('y', init_offset.y + dy);
          $element.attr('height', Math.max(init_scale.height - dy, 10));
          break;
      }
    }



  }

  function handle_mouseup() {
    $('body').css('cursor', 'default');
    $('body')
      .off('mousemove', handle_dragging)
      .off('mouseup', handle_mouseup);
  }

  $('body')
    .on('mouseup', handle_mouseup)
    .on('mousemove', handle_dragging);
});

function updateControls($element) {
  $element = $($element); //ensure its jquery object 
  var width = parseInt($element.get(0).getBBox().width),
    height = parseInt($element.get(0).getBBox().height),
    data = {
      x: parseInt($element.attr('x')),
      y: parseInt($element.attr('y')),
      rx: width,
      ry: height,
      angle: 0
    };

  var controls = [{
      x: data.x + data.rx / 2,
      y: data.y - 20,
      name: "rotator"
    }, {
      x: data.x + data.rx / 2,
      y: data.y + data.ry / 2,
      name: "center"
    },

    {
      x: data.x,
      y: data.y,
      name: "nw"
    }, {
      x: data.x + data.rx / 2,
      y: data.y,
      name: "n"
    }, {
      x: data.x + data.rx,
      y: data.y,
      name: "ne"
    }, {
      x: data.x + data.rx,
      y: data.y + data.ry / 2,
      name: "e"
    },

    {
      x: data.x + data.rx,
      y: data.y + data.ry,
      name: "se"
    }, {
      x: data.x + data.rx / 2,
      y: data.y + data.ry,
      name: "s"
    }, {
      x: data.x,
      y: data.y + data.ry,
      name: "sw"
    }, {
      x: data.x,
      y: data.y + data.ry / 2,
      name: "w"
    }
  ];
  var bounderAttrs = {
    x: $element.attr('x'),
    y: $element.attr('y'),
    width: $element.attr('width'),
    height: $element.attr('height'),
  };
  $('#console #x').text($element.attr('x')+"px");
  $('#console #y').text($element.attr('y')+"px");
  $('#console #width').text(bounderAttrs.width);
  $('#console #height').text(bounderAttrs.height?bounderAttrs.height+"px":'AUTO SCALED');

  if ($element.parent().is('g#active_group')) {
    $element.parent().find('.active-control-border').attr(bounderAttrs);
    $.each(controls, function(i, o) {
    if(o.name=='center'){
     $('#console #center').text(JSON.stringify({x:o.x+"px",y:o.y+"px"}));
    }
      $element.parent().find('circle.active-control-' + o.name).attr({
        cx: o.x,
        cy: o.y
      });
    });
    return;
  }

}
//get elem angle from transform attribute
function getAngle(elem) {
  var angle = 0;
  var trans = transform2Array(elem);
  if (!Object.values(trans).length) {
    trans = transform2Array(elem.parent());
  }
  if (trans.rotate != undefined) {
    angle = parseFloat(trans.rotate[0]);
  }
  return angle;
}
/**
 * get tranform attribute values as array transform="rotate(x,y,z) scale(x,y)"
 *  return {
 *      rotate:[x,y,z]
 *      scale:[x,y]
 *        }
 */
function transform2Array(elem) {
  var transform = $(elem).attr('transform');
  var transforms = {};
  if (typeof transform !== 'undefined') {
    $.each(transform.split(' '), function(i, o) {
      if (o.length) {
        var trans = o.replace(')', '').split('(');
        transforms[trans[0]] = [];
        var params = trans[1].split(',');
        $.each(params, function(i, o_param) {
          transforms[trans[0]].push(parseFloat(o_param));
        });
      }
    });
  }
  return transforms;
}
updateControls($('image'))