Question

I'm using CKEditor 4.4, and I tried to use ACF to force the image2 plugin to set width and height as CSS properties (in the style attribute), instead to use the corresponding <img> tag attributes.

In other terms, what I get now using the editor.getData() method is something like that:

<img src="text.jpg" width="100" height="100" />

but I want this other form:

<img src="text.jpg" style="width:100px;height:100px" />

I tried to reach this result using allowedContent and disallowedContent in the config.js file. This is what I tried (see this for references):

//Allow everything
config.allowedContent = {
    $1: {
        // Use the ability to specify elements as an object.
        elements: CKEDITOR.dtd,
        attributes: true,
        styles: true,
        classes: true
    }
};

config.disallowedContent = "img[width,height]";

With this, the result is simply that width and height are no more set (neither as attributes nor in the style), the image cannot be resized and the Image Properties dialog no longer include the input boxes related to image size.

I also tried to reverse the solution propesed by Marco Cortellino in this StackOverflow answer, without positive results.

Can someone help me?

Was it helpful?

Solution

I solved the problem by override the downcast and upcast methods of image2 plugin (as Reinmar has suggested).

This method processes the image element before it is processed when the editor.getData() method is called.

Therefore, the following code represents a possible solution:

CKEDITOR.on("instanceCreated", function (ev) {
    ev.editor.on("widgetDefinition", function (evt) {
        var widgetData = evt.data;

        if (widgetData.name != "image" || widgetData.dialog != "image2") return;

        //Override of upcast
        if (!widgetData.stdUpcast) {
            widgetData.stdUpcast = widgetData.upcast;

            widgetData.upcast = function (el, data) {
                var el = widgetData.stdUpcast(el, data);

                if (!el) return el;

                var attrsHolder = el.name == 'a' ? el.getFirst() : el;
                var attrs = attrsHolder.attributes;

                if (el && el.name == "img") {
                    if (el.styles) {
                        attrs.width = (el.styles.width + "").replace('px', '');
                        attrs.height = (el.styles.height + "").replace('px', '');

                        delete el.styles.width;
                        delete el.styles.height;

                        attrs.style = CKEDITOR.tools.writeCssText(el.styles);
                    }                      
                }

                return el;
            }
        }

        //Override of downcast
        if (!widgetData.stdDowncast) {
            widgetData.stdDowncast = widgetData.downcast;

            widgetData.downcast = function (el) {

                el = this.stdDowncast(el);

                var attrsHolder = el.name == 'a' ? el.getFirst() : el;
                var attrs = attrsHolder.attributes;

                var realWidth, realHeight;

                var widgets = ev.editor.widgets.instances;
                for (widget in widgets) {

                    if (widgets[widget].name != "image" || widgets[widget].dialog != "image2") {
                        continue;
                    }

                    realWidth = $(widgets[widget].element.$).width();
                    realHeight = $(widgets[widget].element.$).height();
                }

                var style = CKEDITOR.tools.parseCssText(attrs.style)

                if (attrs.width) {
                    style.width = realWidth + "px";
                    delete attrs.width;
                }
                if (attrs.height) {
                    style.height = realHeight + "px";
                    delete attrs.height;
                }

                attrs.style = CKEDITOR.tools.writeCssText(style);

                return el;
            }
        }
    });
});
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top