16

我有一个非常简单的问题,但我对导致问题的原因一无所知。在我的一个应用程序中,我使用 jCrop 作为一个小插件来裁剪图像以适应横幅/标题等。将采取以下步骤:

1) Select an image (using CKFinder for this, CKFinder returns the image path to an input field)
2) Click a button to load the image
3) Crop the image
4) Save the image

在大约 75% 的情况下,一切都按计划进行,但是在另外 25% 的情况下,jCrop 无法加载裁剪区域并将其留空。这是我正在使用的 jQuery 代码:

jQuery('#selectimg').live('click', function(e) { 
  e.preventDefault();
  var newsrc = jQuery('#img2').val();
  jQuery('#cropbox').attr('src', newsrc);
  var jcrop_api = jQuery.Jcrop('#cropbox', {
    boxWidth: 700, 
    boxHeight: 700,
    onSelect: updateCoords,
    onChange: updateCoords
  });
  //Some other JS code come's here for buttons (they work all the time)
});

我注意到,当我将#cropbox 正在被转换的部分放在可裁剪区域中时,图像加载得很好,所以错误在于该var = jcrop_api部分,但我慢慢开始认为没有解决方案。 ..

这是我迄今为止尝试过的:

制作一个 div<div id="cropper-box"></div>并使用jQuery('#cropper-box').append('<img src="" id="cropbox" />');,然后设置值。我尝试了同样的事情,但在第一步而不是之后设置图像 src。

我试图在页面上放置一个占位符<img src="placeholder.png" id="cropbox" />并在单击按钮时更改源。这可行,但cropperarea保持图像的大小(300x180px或其他东西)并且不会变大。

// 编辑:

尝试更多显示图像源被正确替换(!使用 Firefox 显示所选文本的源),我仔细检查了 URL,但这是一个正确的 URL 和工作图像。

在裁剪器应该在的地方,有一个大约 10x10 像素的白点,裁剪器图标(加号)正在弹出。但如前所述:图像未显示。

// 编辑 2:

因此,我为同一图像的第一次和第二次尝试获取了资源。如前所述,第一次尝试无法正确加载图像,而第二次尝试则可以正常加载(仅当第二次尝试是相同的图像时(!!))。

所选页面源显示 1 个不同之处,即首先尝试:

<img style="position: absolute; width: 0px; height: 0px;" src="http://95.142.175.17/uploads/files/Desert.jpg">

第二次尝试:

<img style="position: absolute; width: 700px; height: 525px;" src="http://95.142.175.17/uploads/files/Desert.jpg">

我想这是被 jCrop 替换的图像,但这是一个完整的谜,为什么它第一次将 0 高度/宽度放入其中,第二次放入正确的尺寸。

4

6 回答 6

10

好的,如果其他人遇到这个问题:

如果加载图像和对其应用 jCrop 的操作在彼此之后排队太快,jCrop 会有点混乱。我仍然觉得奇怪的是,第二次尝试完美无缺,但我认为这与页面的 DOM 或其他东西识别的缓存图像尺寸有关。

我想出的解决方案是创建一个函数,将#cropbox 转换为 jCrop 区域,然后设置 2 秒的间隔,只是为了给 jCrop 一些时间来识别图像及其尺寸,然后转换元素。

这是我使用的 html 的一部分(带有预加载器):

<div id="cropper-loading" style="display: none;"><img src="images/analytics/ajax-loader.gif" /></div>
<img id="cropbox" src="images/placeholder.png" style="display: none;" />

如您所见,cropbox 图像和cropper-loading div 都被隐藏了,因为它们不是立即需要的。如果你愿意,你可以显示占位符。然后使用这个 HTML 表单:

<input name="image2" id="img2" type="text" readonly="readonly" onclick="openKCFinder(this)" value="click here to select an image" style="width: 285px;" />  <button class="button button-blue" type="submit" name="load" id="selectimg">Load Image in cropper</button>

在我的情况下,我一直在使用 KCFinder 来加载图像(它是 CKEditor 的一部分,非常值得一看!),KCFinder 处理上传、重命名等,并在选择它后返回选择的图像路径(相对/绝对是可配置的)到输入字段。

然后在单击#selectimg 时调用此代码:

jQuery('#selectimg').click(function(e) { 
    e.preventDefault();
    jQuery('#cropper-loading').css('display', 'block');

    var newsrc = jQuery('#img2').val();

    jQuery('#cropbox').attr('src', newsrc);
    jQuery('#img').val(newsrc);

    function createJcropArea() {
        jQuery('#cropper-loading').css('display', 'none');                                      
        jQuery('#cropbox').css('display', 'block');
        var jcrop_api = jQuery.Jcrop('#cropbox', {
            boxWidth: 700, 
            boxHeight: 700,
            onSelect: updateCoords,
            onChange: updateCoords
        });
        clearInterval(interval);
    }
    var interval = setInterval(createJcropArea, 2000);
});

起初,我阻止链接也像通常那样(或按钮操作)被遵循,然后显示加载 div(这是我隐藏占位符图像的原因,否则它看起来会一团糟)。

然后从输入字段加载图像位置并复制到另一个(#img),该字段用于随后处理图像(PHP使用#img的值来加载此图像)。同时,#cropbox src 也被设置为新图像。

这是解决我问题的部分:

我没有直接激活 jCrop,而是创建了一个函数:

1) hides the loading icon
2) displays the image
3) converts #cropbox into a jCrop area
4) clean the interval (otherwise it would loop un-ending)

在这个函数之后你可以看到,为了保存,我在 jCrop 区域被转换之前延迟了 2 秒。

希望它对将来的任何人都有帮助!

干杯并感谢您思考@vector 和其他人;-)

于 2011-05-09T14:26:35.813 回答
4

创建 'Image' 对象并设置 'src' 属性并不适用,您可以将图像视为已经加载。此外,给出任何固定的超时间隔并不能保证图像已经加载。

相反,您应该为 Image 对象设置一个“onload”回调 - 然后它将初始化 Jcrop 对象:

var src = 'https://example.com/imgs/someimgtocrop.jpg'; 
var tmpImg = new Image();
tmpImg.onload = function() {
   //This is where you can safely create an image and a Jcrop Object
};
tmpImg.src = src; //Note that the 'src' attribute is only added to the Image Object after the 'onload' listener was defined
于 2013-10-18T21:01:22.103 回答
3

在此处尝试 repo 上的边缘库:https ://github.com/tapmodo/Jcrop

这应该可以解决您的问题。为解决您的问题而更改的行:

// Fix size of crop image.
// Necessary when crop image is within a hidden element when page is loaded.
if ($origimg[0].width != 0 && $origimg[0].height != 0) {
  // Obtain dimensions from contained img element.
  $origimg.width($origimg[0].width);
  $origimg.height($origimg[0].height);
} else {
  // Obtain dimensions from temporary image in case the original is not loaded yet (e.g. IE 7.0).
  var tempImage = new Image();
  tempImage.src = $origimg[0].src;
  $origimg.width(tempImage.width);
  $origimg.height(tempImage.height);
}
于 2011-12-15T16:51:46.833 回答
1

不要调用这个函数onChange : updateCoords

尝试不使用它,它会在手机上流畅运行。

您可以直接创建 base64 并将它们显示为任何您想要的图像。

于 2014-04-12T12:37:17.730 回答
0

这是我奇怪但奇妙的解决方案:

if (obj.tagName == 'IMG') {
  var tempImage = new Image();
    tempImage.src = $origimg[0].src;
    $origimg.width(tempImage.width);
    $origimg.height(tempImage.height);
  if ($origimg[0].width > 1 && $origimg[0].height > 1) {
    $origimg.width($origimg[0].width);
    $origimg.height($origimg[0].height);
  } else {
    var tempImage = new Image();
    tempImage.src = $origimg[0].src;
    $origimg.width(tempImage.width);
    $origimg.height(tempImage.height);
     //console.log('error'+$origimg[0].width + $origimg[0].height);
  } 
于 2013-07-30T07:45:19.910 回答
0

我知道这是旧的,但它最近在我的安装中随机发生。发现是因为在jCrop初始化之前图片没有完全加载。

修复它所需要的只是将 jCrop 初始化内容包装在一个

$(window).on("load", function () { //jcrop stuff here });

从那以后它一直运作良好。

于 2016-04-02T19:12:43.890 回答