ToastUI图像编辑器loadImageFromURL不起作用

For*_*vin 1 javascript toast-ui-image-editor

请注意,这是一个自我回答的问题。

该问题与ToastUI图像编辑器v3.3.0有关,但也可能适用于较新的版本。

使用此官方示例加载图像时:

// Create image editor
var imageEditor = new tui.component.ImageEditor('#my-image-editor canvas', {
    cssMaxWidth: 1000, // Component default value: 1000
    cssMaxHeight: 800  // Component default value: 800
});

// Load image
imageEditor.loadImageFromURL('img/sampleImage.jpg', 'My sample image')
Run Code Online (Sandbox Code Playgroud)

编辑器将不会加载图像。该函数既不抛出也不返回任何指示失败的信息,并且您不会收到任何错误消息。它返回一个诺言,该诺言按照文档中的说明进行解析。

它仅通过在初始配置中指定图像来加载图像,此后您将无法更改它:

// Create image editor
var imageEditor = new tui.component.ImageEditor('#my-image-editor canvas', {
     includeUI: {
         loadImage: {
             path: 'img/sampleImage.jpg',
             name: 'My sample image'
         },
     },
    cssMaxWidth: 1000, // Component default value: 1000
    cssMaxHeight: 800  // Component default value: 800
});
Run Code Online (Sandbox Code Playgroud)

看来loadImageFromURL函数已损坏,并且根据其他用户loadImageFromFile也有同样的问题。

与此相关的问题已在GitHub上提出,但基本上已被忽略。到现在已经一个月了,不幸的是它还没有修复。

因此,问题是在存在此问题的情况下如何欺骗图像编辑器使其工作。

这是一个显示不起作用的小提琴:https : //fiddle.sencha.com/#view/editor&fiddle/2org

For*_*vin 7

TL; DR:
这是一个有效的小提琴:https : //fiddle.sencha.com/#view/editor&fiddle/2p0o


长版:

有四个问题:

  • 您需要加载初始图像,否则无法使用编辑控件。
  • 您需要等到图像编辑器对象准备就绪后再调用loadImageFromURL,否则可能会出现错误或无提示故障
  • 加载图像后,您需要告知图像编辑器新的尺寸,否则图像将被隐藏或尺寸错误。
  • 如果加载外部图像,则外部服务器必须设置Access-Control-Allow-Origin标头并明确允许您的域访问它,否则图像编辑器将无法访问它。

可以通过加载如下空白图像来解决第一个问题:

var imageEditor = new tui.ImageEditor('#tui-image-editor-container', {
    includeUI: {
        loadImage: {
            path: 'data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7',
            name: 'Blank'
        },
        theme: whiteTheme,
        menuBarPosition: 'bottom'
    },
    cssMaxWidth: 700,
    cssMaxHeight: 700
});
Run Code Online (Sandbox Code Playgroud)

第二个问题可以通过使用未记录的功能等待图像编辑器退出其锁定状态来解决。您可以loadImageFromURL这样在运行时打补丁:

imageEditor.loadImageFromURL = (function() {
    var cached_function = imageEditor.loadImageFromURL;
    function waitUntilImageEditorIsUnlocked(imageEditor) {
        return new Promise((resolve,reject)=>{
            const interval = setInterval(()=>{
                if (!imageEditor._invoker._isLocked) {
                    clearInterval(interval);
                    resolve();
                }
            }, 100);
        })
    }
    return function() {
        return waitUntilImageEditorIsUnlocked(imageEditor).then(()=>cached_function.apply(this, arguments));
    };
})();
Run Code Online (Sandbox Code Playgroud)

第三个问题可以通过以下方法解决:将要返回的promise解析为一个对象,loadImageFromURL并将新旧的width / height属性传递给ui.resizeEditor函数,如下所示:

imageEditor.loadImageFromURL("https://upload.wikimedia.org/wikipedia/en/thumb/8/80/Wikipedia-logo-v2.svg/526px-Wikipedia-logo-v2.svg.png", "SampleImage").then(result=>{
    imageEditor.ui.resizeEditor({
        imageSize: {oldWidth: result.oldWidth, oldHeight: result.oldHeight, newWidth: result.newWidth, newHeight: result.newHeight},
    });
}).catch(err=>{
    console.error("Something went wrong:", err);
})
Run Code Online (Sandbox Code Playgroud)

第四个问题可能有点令人困惑。让我解释。在网站上,您几乎可以使用<img>标签包含想要的任何外部图像,但是如果要使用JavaScript访问外部图像,提供该图像的服务器必须显式地允许您使用access-control-allow-origin标头来执行此操作。例如,在Amazon S3上,服务器默认情况下不允许这样做。您必须手动设置服务器以允许您或任何域访问它。看这里。如果您使用的是其他服务器,则可以例如将设置access-control-allow-origin*Wikipedia在该图像上完成的操作。然后,您(和图像编辑器)可以从任何域的JavaScript访问该图像。