2015-05-21 6 views
0

Я использую следующий код для создания холста, на который пользователь загружает изображение, и может перетаскивать, изменять размер и поворачивать изображение на продукт. Как инструмент для дизайна футболки.Масштаб изображения холста Пропорционально

Моя проблема заключается в том, что мне нужно масштабировать изображение пропорционально, так что, когда пользователь изменяет размер изображения, он не выглядит искаженным или растянутым.

var canvas = document.getElementById("editorCanvas"); 
var ctx = canvas.getContext("2d"); 

var canvasOffset = $("#editorCanvas").offset(); 
var offsetX = canvasOffset.left; 
var offsetY = canvasOffset.top; 

var startX; 
var startY; 
var isDown = false; 


var pi2 = Math.PI * 2; 
var resizerRadius = 4; 
var rr = resizerRadius * resizerRadius; 
var draggingResizer = { 
    x: 0, 
    y: 0 
}; 
var imageX = 0; 
var imageY; 
var imageWidth, imageHeight, imageRight, imageBottom; 
var draggingImage = false; 
var startX; 
var startY; 

var img = new Image(); 
img.crossOrigin='anonymous'; 
img.onload = function() { 

    var ratio = img.width/img.height; 

    imageWidth = 71; 
    imageHeight = imageWidth/ratio; 
    imageY = (245-imageHeight)/2; 
    if (imageHeight > 245) { 
    imageHeight = 245; 
    imageWidth = imageHeight * ratio; 
    imageY = 0; 
    } 

    imageX = ((canvas.width-imageWidth)/2); 
    imageY = ((canvas.height-imageHeight)/2); 

    imageRight = imageX + imageWidth; 
    imageBottom = imageY + imageHeight; 

    draw(true, false); 
} 
//img.src='https://dl.dropboxusercontent.com/u/139992952/multple/leftarrow.png'; 

function draw(withAnchors, withBorders) { 

    // clear the canvas 
    ctx.clearRect(0, 0, canvas.width, canvas.height); 

    // draw the image 
    ctx.drawImage(img, 0, 0, img.width, img.height, imageX, imageY, imageWidth, imageHeight); 

    // optionally draw the draggable anchors 
    if (withAnchors) { 
    drawDragAnchor(imageX, imageY); 
    drawDragAnchor(imageRight, imageY); 
    drawDragAnchor(imageRight, imageBottom); 
    drawDragAnchor(imageX, imageBottom); 
    } 

    // optionally draw the connecting anchor lines 
    if (withBorders) { 
    ctx.beginPath(); 
    ctx.moveTo(imageX, imageY); 
    ctx.lineTo(imageRight, imageY); 
    ctx.lineTo(imageRight, imageBottom); 
    ctx.lineTo(imageX, imageBottom); 
    ctx.closePath(); 
    ctx.stroke(); 
    } 

} 

function drawDragAnchor(x, y) { 
    ctx.beginPath(); 
    ctx.arc(x, y, resizerRadius, 0, pi2, false); 
    ctx.closePath(); 
    ctx.fill(); 
} 

function anchorHitTest(x, y) { 

    var dx, dy; 

    // top-left 
    dx = x - imageX; 
    dy = y - imageY; 
    if (dx * dx + dy * dy <= rr) { 
    return (0); 
    } 
    // top-right 
    dx = x - imageRight; 
    dy = y - imageY; 
    if (dx * dx + dy * dy <= rr) { 
    return (1); 
    } 
    // bottom-right 
    dx = x - imageRight; 
    dy = y - imageBottom; 
    if (dx * dx + dy * dy <= rr) { 
    return (2); 
    } 
    // bottom-left 
    dx = x - imageX; 
    dy = y - imageBottom; 
    if (dx * dx + dy * dy <= rr) { 
    return (3); 
    } 
    return (-1); 

} 


function hitImage(x, y) { 
    return (x > imageX && x < imageX + imageWidth && y > imageY && y < imageY + imageHeight); 
} 


function handleMouseDown(e) { 
    startX = parseInt(e.clientX - offsetX); 
    startY = parseInt(e.clientY - offsetY); 
    draggingResizer = anchorHitTest(startX, startY); 
    draggingImage = draggingResizer < 0 && hitImage(startX, startY); 
} 

function handleMouseUp(e) { 
    draggingResizer = -1; 
    draggingImage = false; 
    draw(true, false); 
} 

function handleMouseOut(e) { 
    handleMouseUp(e); 
} 

function handleMouseMove(e) { 

    if (draggingResizer > -1) { 

    mouseX = parseInt(e.clientX - offsetX); 
    mouseY = parseInt(e.clientY - offsetY); 

    // resize the image 
    switch (draggingResizer) { 
     case 0: 
     //top-left 
     imageX = mouseX; 
     imageWidth = imageRight - mouseX; 
     imageY = mouseY; 
     imageHeight = imageBottom - mouseY; 
     break; 
     case 1: 
     //top-right 
     imageY = mouseY; 
     imageWidth = mouseX - imageX; 
     imageHeight = imageBottom - mouseY; 
     break; 
     case 2: 
     //bottom-right 
     imageWidth = mouseX - imageX; 
     imageHeight = mouseY - imageY; 
     break; 
     case 3: 
     //bottom-left 
     imageX = mouseX; 
     imageWidth = imageRight - mouseX; 
     imageHeight = mouseY - imageY; 
     break; 
    } 

    if(imageWidth<25){imageWidth=25;} 
    if(imageHeight<25){imageHeight=25;} 

    // set the image right and bottom 
    imageRight = imageX + imageWidth; 
    imageBottom = imageY + imageHeight; 

    // redraw the image with resizing anchors 
    draw(true, true); 

    } else if (draggingImage) { 

    imageClick = false; 

    mouseX = parseInt(e.clientX - offsetX); 
    mouseY = parseInt(e.clientY - offsetY); 

    // move the image by the amount of the latest drag 
    var dx = mouseX - startX; 
    var dy = mouseY - startY; 
    imageX += dx; 
    imageY += dy; 
    imageRight += dx; 
    imageBottom += dy; 
    // reset the startXY for next time 
    startX = mouseX; 
    startY = mouseY; 

    // redraw the image with border 
    draw(false, true); 

    } 


} 

$("#editorCanvas").mousedown(function (e) { 
    handleMouseDown(e); 
}); 
$("#editorCanvas").mousemove(function (e) { 
    handleMouseMove(e); 
}); 
$("#editorCanvas").mouseup(function (e) { 
    handleMouseUp(e); 
}); 
$("#editorCanvas").mouseout(function (e) { 
    handleMouseOut(e); 
}); 

function rotate(rotationPointX,rotationPointY,degreeRotation){ 

    // Create an second in-memory canvas: 
    var mCanvas=document.createElement('canvas'); 
    mCanvas.width=canvas.width; 
    mCanvas.height=canvas.height; 
    var mctx=mCanvas.getContext('2d'); 

    // Draw your canvas onto the second canvas 
    mctx.drawImage(canvas,0,0); 

    // Clear your main canvas 
    ctx.clearRect(0,0,canvas.width,canvas.height); 

    // Rotate the main canvas 

    // set the rotation point as center of the canvas 
    // (but you can set any rotation point you desire) 
    ctx.translate(rotationPointX,rotationPointY); 

    // rotate by 90 degrees (==PI/2) 
    var radians=degreeRotation/180*Math.PI; 
    ctx.rotate(radians); 


    // Draw the second canvas back to the (now rotated) main canvas: 
    ctx.drawImage(mCanvas,-canvas.width/2,-canvas.height/2); 

    // clean up -- unrotate and untranslate 
    ctx.rotate(-radians); 
    ctx.translate(-canvas.width/2,-canvas.height/2); 

} 

$('#rotate').click(function(){ 
    rotate(canvas.width/2,canvas.height/2,90); 
}); 

Я полагаю, что есть способ сделать это, я просто не совсем уверен, что будет необходимости менять или что-то не так в коде для него.

Так что мой вопрос в том, как изменить свой код для пропорционального масштабирования?

ответ

0

Я на самом деле удалось это исправить путем редактирования математику в (е) функции handleMouseMove следующим образом:

// resize the image 
    switch (draggingResizer) { 
     case 0: 
     //top-left 
     imageX = mouseX; 
     imageWidth = imageRight - mouseX; 
     imageY = mouseY; 
     imageHeight = imageBottom - mouseY; 
     break; 
     case 1: 
     //top-right 
     imageY = mouseY; 
     imageWidth = mouseX - imageX; 
     imageHeight = imageWidth/ratio; //imageBottom - mouseY; 
     break; 
     case 2: 
     //bottom-right 
     imageWidth = mouseX - imageX; 
     imageHeight = mouseY - imageY; 
     break; 
     case 3: 
     //bottom-left 
     imageX = mouseX; 
     imageWidth = imageRight - mouseX; 
     imageHeight = mouseY - imageY; 
     break; 
    } 

место, прежде чем я заметил, что код исправление - это гарантирует, что ImageHeight пропорциональна imageWidth с использованием первоначально рассчитанного отношения.

Смежные вопросы