可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):
问题:
I'm trying to crop an image using Jcrop, but when I use jqueryrotate on the image, something weird happens.
I rotate the image 90 degress then I activate the JCrop, the JCrop does not follow the image rotated, so I also rotate the Jcrop-holder. The resulting image is ok, but when I select a section to crop, I have noticed that my tracker is also rotated. When I drag it up, it goes right, when I drag it left, it goes down.
What happens
Then it goes
How do I make the crop selection tool stay upright?
My html:
<div class="img-canvas" style="background-color:#cccccc;" >
<img id="image_canv" src="<?php echo $imagesource;?>">
</div>
My Jquery:
$('#rotatephoto').click(function () {
value += 90;
JcropAPI = $('#image_canv').data('Jcrop');
if(JcropAPI != null)
{
JcropAPI.destroy();
}
var h = $('.img-canvas').height();
var w = $('.img-canvas').width();
$('.img-canvas').css("position","fixed");
$('.img-canvas').css("width",w);
$('.img-canvas').css("height",h);
$('#image_canv').Jcrop({
onSelect: showCoords2,
onChange: showCoords2,
setSelect: [ 0, 100, 50, 50 ]
});
JcropAPI = $('#image_canv').data('Jcrop');
JcropAPI.enable();
var h2 = $('.jcrop-holder').height();
var w2 = $('.jcrop-holder').width();
if(h2 < 630)
{
var tempp = (630 - h2)/2;
$('.jcrop-holder').css("margin-top",tempp);
}
if(w2 < 630)
{
var tempp = (630 - w2)/2;
$('.jcrop-holder').css("margin-left",tempp);
}
$('.jcrop-holder').rotate(value);
$("#image_canv").rotate(value);
});
回答1:
Yes, the JCrop has the problem of selection direction error after rotated by JQuery rotate.
I had to resolve it by change the JCrop's js code to support rotate.
Fortunatly, it's not hard to do, you can do it yourself by replace one line: 136 to sub codes:
//========= begin replace origin line 136 for rotate
var x = pos[0] - lloc[0];
var y = pos[1] - lloc[1];
var rotate = options.rotate || 0;
var angle = (rotate / 90) % 4;
if (angle == 1) {
var temp = x;
x = y;
y = - temp;
} else if (angle == 2) {
x = -x;
y = -y;
} else if (angle == 3) {
var temp = x;
x = -y;
y = temp;
}
Coords.moveOffset([x, y]);
//========= end replace origin line 136 for rotate
or you can get the updated code by url: https://github.com/ergoli/Jcrop/tree/master/js
be careful!
you should transfer the rotate option after each rotate click:
jCropApi.setoptions({rotate : 90}); //rotate 90
good luck!
回答2:
I jumped off of ergoli, but instead of jquery rotate I used css classes like:
.rotate90{
/* Safari */
-webkit-transform: rotate(90deg);
/* Firefox */
-moz-transform: rotate(90deg);
/* IE */
-ms-transform: rotate(90deg);
/* Opera */
-o-transform: rotate(90deg);
/* Internet Explorer */
filter: progid:DXImageTransform.Microsoft.BasicImage(rotation=3);
}
Then I made similar classes for 180 and -90.
I found it was simpler for me to just alter the mouseAbs function
function mouseAbs(e) //{{{
{
switch (options.rotate) {
case 90:
return [(e.pageY - docOffset[1]), -(e.pageX - docOffset[0] - options.imgHeight)];
break;
case 270:
return [(e.pageY - docOffset[1]), -(e.pageX - docOffset[0] - options.imgHeight)];
break;
case -90:
return [-(e.pageY - docOffset[1] - options.imgWidth), (e.pageX - docOffset[0] )];
break;
case 270:
return [-(e.pageY - docOffset[1] - options.imgWidth), (e.pageX - docOffset[0] )];
break;
case 180:
return [-(e.pageX - docOffset[0]- options.imgWidth), -(e.pageY - docOffset[1] - options.imgHeight)];
break;
case -180:
return [-(e.pageX - docOffset[0]- options.imgWidth), -(e.pageY - docOffset[1] - options.imgHeight)];
break;
default:
return [(e.pageX - docOffset[0]), (e.pageY - docOffset[1])];
break;
}
}
Just had to make sure my .jcrop-holder had the right rotate class at the right time and instanciate jcrop with the rotate and image dimensions.
this.image.Jcrop({
rotate: that.angle,
imgHeight: that.image.height(),
imgWidth: that.image.width(),
onSelect: function(c){
that.x1 = c.x;
that.x2 = c.x2;
that.y1 = c.y;
that.y2 = c.y2;
that.w = c.w;
that.h = c.h;
}
});
This is not a particularly elegant solution, but its working currently.
回答3:
I recently tried implementing this too, but wasn't able to get the approaches mentioned in the other answers working the way I wanted. In particular, I was having trouble with resizing the crop when it was rotated. I looked into updating Jcrop to fix the issue, but decided an alternative would be easier.
I instead opted to rotate the images outside of Jcrop using the JavaScript Load Image library and then crop the rotated image. The loadImage method in there takes an orientation option that can be used to perform the rotation. Depending on what you're trying to do, you may need to transform the resulting crop afterwards, but I found that to be easier than messing with the internals of Jcrop.
回答4:
I used Dan's approach as a jumping off point but I don't have enough reputation to leave a comment on Dan Baker's answer so I'm submitting another answer. His mouseAbs function didn't work for me at all, I modified it as follows:
function mouseAbs(e)
{
switch (options.rotate) {
case 90:
return [(e.pageY - docOffset[1]), -(e.pageX - docOffset[0])];
case 180:
return [-(e.pageX - docOffset[0]), -(e.pageY - docOffset[1])];
case 270:
return [-(e.pageY - docOffset[1]), (e.pageX - docOffset[0])];
default:
return [(e.pageX - docOffset[0]), (e.pageY - docOffset[1])];
}
}
Everything else was the same. Passed in the current rotation to the Jcrop object when it was initialized and I applied Dan's rotation css class to the .jcrop-holder element.
回答5:
Please take look at this. This is working perfectly fine. Thanks to ergoli. I used my logic on the top of ergoli's updated JCrop file.
https://github.com/prijuly2000/Image-RotateAndCrop-app
Editted to add the JS code :
var jcrop_api;
var angle = 0;
function checkCoords() {
if (parseInt($('#w').val())) return true;
alert('Please select a crop region then press submit.');
return false;
};
function rotateLeft() {
angle -= 90;
$(".jcrop-holder").rotate(angle);
jcrop_api.setOptions({
rotate: angle < 0 ? 360 + angle : angle
});
if (angle <= -360) angle = 0;
}
function rotateRight() {
angle += 90;
$(".jcrop-holder").rotate(angle);
jcrop_api.setOptions({
rotate: angle
});
if (angle >= 360) angle = 0;
}
function updateCoords(c) {
$('#x').val(c.x);
$('#y').val(c.y);
$('#w').val(c.w);
$('#h').val(c.h);
$('#d').val(angle);
};
function showImage(input) {
if (input.files && input.files[0]) {
var reader = new FileReader();
reader.onload = function(e) {
$("#image").attr("src", e.target.result).Jcrop({
onChange: updateCoords,
onSelect: updateCoords,
boxWidth: 450,
boxHeight: 400
}, function() {
jcrop_api = this;
});
};
reader.readAsDataURL(input.files[0]);
}
}