tenkDraw angular

HTML

<div class="row" data-ng-app="draw-hero" data-ng-controller="svg">
    <div class="col-md-9">
        <div id="tenk-svg-container">
            <svg id="tenk-svg" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
                <g id="tenk-shapes">
                    <tenk-shape data-ng-repeat="shape in shapes" data-shape="shape" data-shapes="shapes" data-generate-shape="generateShape" data-on-mousedown="shapeMouseDown" data-on-mouseup="shapeMouseUp" data-on-mousemove="shapeMouseMove" data-shape-index="{{$index}}"></tenk-shape>
                </g>
                <g id="tenk-modify-shapes">
                    <tenk-shape data-ng-repeat="shape in modifyShapes" data-shape="shape" data-shapes="modifyShapes" data-generate-shape="generateShape" data-on-mousedown="modShapeMouseDown" data-on-mouseup="" data-on-mousemove="" data-shape-index="{{$index}}"></tenk-shape>
                </g>

            </svg>
        </div>
    </div>
    <div class="col-md-3">
         <h3>shape:{{selectedShape.name}}</h3>
id: <span class="text-alert">{{selectedShape.id}}</span>

         <h4>position and size</h4>

        <div data-ng-repeat="point in selectedShape.properties.points">
            <div data-ng-if="selectedShape.name == 'bezier'">
                 <h5>point[{{$index}}]</h5>

                <div data-ng-repeat="(key, value) in point">{{key}}(x,y):
                    <input data-ng-repeat="(k,v) in point[key]" type="number" data-ng-model="point[key][k]" />
                </div>
            </div>
            <div data-ng-if="selectedShape.name == 'polygon' || selectedShape.name == 'polyLine'">
                 <h5>point[{{$index}}]</h5>
(x,y):
                <input data-ng-repeat="(key, value) in point" type="number" data-ng-model="point[key]" />
            </div>
            <div data-ng-if="selectedShape.name == 'rectangle'">
                <div>(x,y):
                    <input type="number" data-ng-model="point.x" />
              ...

CSS

.drawing-menu {
    margin-top: 30px;
}
.drawing-menu ul {
    list-style: none;
    margin-left: 0;
    padding-left: 0;
    float: left;
}
.drawing-menu ul li {
    display: inline-block;
    padding: 10px 7px 5px 5px;
    border: 1px solid #ccc;
    background: #eee;
    float: left;
    margin-right: 5px;
    cursor: pointer;
}
.drawing-menu ul.di li:hover {
    background: #55BADF;
    color: #fff;
}
.drawing-menu ul.di li.active {
    background: #27A2CF;
    color: #fff;
}
.drawing-menu ul li.oi:hover a {
    background: #85D27A;
    color: #fff;
}
#drawing-canvas {
    margin-top: 30px;
    width: 100%;
    height: 599px;
}
.show-grid.active {
    background: #5BC24C !important;
    color: #fff;
}
#tenk-svg-container {
    width: 100%;
    height: 600px;
    background: #555;
    position: relative;
    margin-top:10px;
}
#selected-shapes:hover {
    cursor: move;
}
[data-curoen="pointer"][data-type="editable-shape"]:hover {
    cursor: pointer;
}
[data-selected="true"] {
    outline: 2px dashed #5BC24C;
}
[data-type="editable-shape"][data-selected="true"]:hover {
    cursor: move;
}
[data-which="tl"] {
    cursor: nw-resize;
}
[data-which="t"] {
    cursor: n-resize;
}
[data-which="tr"] {
    cursor: ne-resize;
}
[data-which="r"] {
    cursor: w-resize;
}
[data-which="br"] {
    cursor: se-resize;
}
[data-which="b"] {
    cursor: s-resize;
}
[data-which="bl"] {
    cursor: sw-resize;
}
[data-which="l"] {
    cursor: e-resize;
}
.ngn-mousedown {
    outline: 2px dashed #55BADF;
}
.ngn-selected {
    outline: 2px dashed #5BC24C;
}
[data-type*="modify-shape"] {
    cursor: pointer;
}
[data-type*="modify-shape"].selected {
    fill: #F2636F;
    stroke: #732735;
}
input[type="text"],
input[type="number"],
select{
        width: 70px;
}

JavaScript

function findRefPoint(points, ax, ay) {
    //console.log(points, ax, ay);
    var minX = 9999,
        minY = 9999,
        maxX = -9999,
        maxY = -9999;
    for (var i = 0; i < points.length; i++) {
        minX = Math.min(minX, points[i].x);
        maxX = Math.max(maxX, points[i].x);
        minY = Math.min(minY, points[i].y);
        maxY = Math.max(maxY, points[i].y);
    }
    return {
        min: { x: minX, y: minY },
        max: { x: maxX, y: maxY },
        ref: { x: minX + ((maxX - minX) * ax), y: minY + ((maxY - minY) * ay) }
    };
}

function rotatedPoint(p, ref, degree) {
    degree = degree * Math.PI / 180.0;
    var dx2 = p.x - ref.x,
        dy2 = p.y - ref.y;
    var dx2t = (dx2 * Math.cos(degree)) - (dy2 * Math.sin(degree)),
        dy2t = (dx2 * Math.sin(degree)) + (dy2 * Math.cos(degree));

    var x2t = dx2t + ref.x,
        y2t = dy2t + ref.y;
    return {
        x: x2t,
        y: y2t
    };
}

//GUID generator
function guid() {
    var d = new Date().getTime();
    var uuid = 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function (c) {
        var r = (d + Math.random() * 16) % 16 | 0;
        d = Math.floor(d / 16);
        return (c == 'x' ? r : (r & 0x3 | 0x8)).toString(16);
    });
    return uuid;
};

var dh = angular.module('draw-hero', []);

var shape = function () {
    this.id = '';
    this.type = 'editable';
    this.name = 'shape';
    this.isLocked = false;
    this.isVisible = true;
    this.blendMode = 'normal'; //add, multiply, screen
    this.alpha = 1;

    this.properties = {
        points: [],
        rpoints: [],
        style: {
            anchorX: 0.5,
            anchorY: 0.5,
            rotation: 0,
            fill: '#ffffff',
            strokeColor: '#cccccc',
            strokeWidth: 1,
        },
        attributes: [{
            key: 'val'
        }],
        physics: {
            enabled: false,
            fixtureName: 'main body',
            linkFixtures: true,
           ...