javascript - SVG Rotate and Scale Transform Issue -


i trying re-size, rotate , drag svg elements using transformations. if rotate object, re-size it, , rotate again, on last rotation element gets displaced wrongly.

resizing done way

var matrix = svg.createsvgmatrix()                 .translate(x,y)                 .scalenonuniform(sx,sy)                 .translate(-x,-y); var newmatrix =  svg.createsvgtransformfrommatrix(ctm.multiply(matrix));  element.transform.baseval.initialize(newmatrix);   

rotation done way

var matrix = svg.createsvgmatrix()                 .translate(cx,cy)                 .rotate(angle)                 .translate(-cx,-cy); var newmatrix = svg.createsvgtransformfrommatrix(ctm.multiply(matrix)); element.transform.baseval.initialize(newmatrix);   

is there idea resolve issue?

i use combination of getbbox element identify center no matter transforms applied. also, track element's transformed center, enclose in svg wrapper, , bounding box. use matrix transforms , consolidate() on each transform.

the following example on how used move element desired point:

<!doctype html> <html xmlns="http://www.w3.org/1999/xhtml"> <head>   <title>native center transforms wrapper</title> <meta http-equiv="content-type" content="text/html; charset=utf-8"> </head> <body style='padding:10px;font-family:arial'> <center> <h4>native center transforms wrapper</h4> <div style='width:90%;background-color:gainsboro;text-align:justify;padding:10px;border-radius:6px;'> <b>native center</b> center of element's bounding box. remains constant no matter transforms has been applied element. therefore center point there can used <b>reference point</b> stable rotation, scale, , skew transforms. use of svg <b>wrapper</b>, element can translated center point moves target point. </div> <table><tr> <td> <div style="padding:10px;width:400px;text-align:justify"> <b>scenerio:</b><br /> rect element has been translated original location (dashed rect). further scale, rotate, , skew transforms can use rect's original bounding box center (black circle): <b>nativecenterx, nativecentery</b>.<br /><br /> also, folowing scale. rotate, skew..<br /> center of element can <b>moved to</b> specific target point (maroon circle) using center point of it's svg <b>wrapper</b> <br /><br /> <i>click buttons 1 or more times transform rect.</i> </div> </td> <td> <div id="svgdiv" style='background-color:lightgreen;width:400px;height:400px;'> <svg id="mysvg" width="400" height="400"> <rect id="myrect" fill=red stroke="none" x="10" y="60" width=150 height=80 transform="translate(110,50)" /> <rect id="bbrect" fill=none stroke="black" stroke-width="1" stroke-dasharray="10 10"  /> <circle id=nativecenter r=5 fill="black" stroke="none" /> <circle id=movetotarget r=5 fill="maroon" cx=240 cy=330 stroke="none" /> </svg> </div> <center> <button onclick=rotaterect()>rotate</button> <button onclick=scalerect()>scale</button> <button onclick=skewxrect()>skewx</button> <button onclick=skewyrect()>skewy</button> then...<button onclick=movetorect()>move to</button> </center> </td> </tr></table>   <br />svg source:<br /> <textarea id=svgsourcevalue style='font-size:110%;font-family:lucida console;width:90%;height:200px'></textarea>   <br />javascript:<br /> <textarea id=jsvalue style='border-radius:26px;font-size:110%;font-weight:bold;color:midnightblue;padding:16px;background-color:beige;border-width:0px;font-size:100%;font-family:lucida console;width:90%;height:400px'></textarea> </center> <div id='browserdiv' style='padding:5px;position:absolute;top:5px;left:5px;background-color:gainsboro;'>ok in:ie11/ch32/ff23<br /></div> <script id=myscript> var nativecenterx var nativecentery var transformrequestobj var transformlist //---translate target--- var targetx var targety //---onload--- function initbbox() {     var bb=myrect.getbbox()     var bbx=bb.x     var bby=bb.y     var bbw=bb.width     var bbh=bb.height     nativecenterx=bbx+.5*bbw     nativecentery=bby+.5*bbh     bbrect.x.baseval.value=bbx     bbrect.y.baseval.value=bby     bbrect.width.baseval.value=bbw     bbrect.height.baseval.value=bbh     nativecenter.cx.baseval.value=nativecenterx     nativecenter.cy.baseval.value=nativecentery      targetx=movetotarget.cx.baseval.value     targety=movetotarget.cy.baseval.value      //--- transform myrect objs---     transformrequestobj=mysvg.createsvgtransform()     var animtransformlist=myrect.transform     transformlist=animtransformlist.baseval } //---button--- function rotaterect() //---15 degrees {     transformrequestobj.setrotate(15,nativecenterx,nativecentery)     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()     svgsourcevalue.value=svgdiv.innerhtml } function scalerect() //---.8--- {     transformrequestobj.settranslate(nativecenterx,nativecentery  )     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      transformrequestobj.setscale(.8,.8)     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()     transformrequestobj.settranslate(-nativecenterx,-nativecentery  )     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      svgsourcevalue.value=svgdiv.innerhtml } function skewxrect() {     transformrequestobj.settranslate(nativecenterx,nativecentery  )     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      transformrequestobj.setskewx(10)     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      transformrequestobj.settranslate(-nativecenterx,-nativecentery  )     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      svgsourcevalue.value=svgdiv.innerhtml } function skewyrect() {     transformrequestobj.settranslate(nativecenterx,nativecentery  )     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      transformrequestobj.setskewy(10)     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      transformrequestobj.settranslate(-nativecenterx,-nativecentery  )     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      svgsourcevalue.value=svgdiv.innerhtml } var ns="http://www.w3.org/2000/svg" //---move transformed rect specific point(targetx,targety)-- function movetorect() {     //---build temp wrapper---     var wrapper=document.createelementns(ns,"svg")     mysvg.appendchild(wrapper)     //---temp place rect in wrapper---     wrapper.appendchild(myrect)     var bb=wrapper.getbbox()     //---return myrect previous location---     mysvg.insertbefore(myrect,bbrect)     //---remove temp wrapper---     mysvg.removechild(wrapper)      var bbx=bb.x     var bby=bb.y     var bbw=bb.width     var bbh=bb.height     //---center of svg srapper---     var wcx=bbx+.5*bbw     var wcy=bby+.5*bbh      //---bind target point current matrix---     var pnt = myrect.nearestviewportelement.createsvgpoint();     pnt.x = targetx;     pnt.y = targety;     var sctm = myrect.getctm();     pnt1 = pnt.matrixtransform(sctm.inverse());     //---bind wrapper center current matrix--     var pnt = myrect.nearestviewportelement.createsvgpoint();     pnt.x = wcx;     pnt.y = wcy ;     var sctm = myrect.getctm();     pnt2 = pnt.matrixtransform(sctm.inverse());     //---translate rect's center target---     var transx=pnt1.x-pnt2.x     var transy=pnt1.y-pnt2.y      transformrequestobj.settranslate(transx,transy)     transformlist.appenditem(transformrequestobj)     transformlist.consolidate()      svgsourcevalue.value=svgdiv.innerhtml }  </script> <script> document.addeventlistener("onload",init(),false) function init() {     initbbox()     svgsourcevalue.value=svgdiv.innerhtml     jsvalue.value=myscript.text } </script>  </body>  </html> 

Comments

Popular posts from this blog

android - Get AccessToken using signpost OAuth without opening a browser (Two legged Oauth) -

org.mockito.exceptions.misusing.InvalidUseOfMatchersException: mockito -

google shop client API returns 400 bad request error while adding an item -