var svgEditorExtension_foreignobject = (function () {
  'use strict';

  /**
   * @file ext-foreignobject.js
   *
   * @license Apache-2.0
   *
   * @copyright 2010 Jacques Distler, 2010 Alexis Deveria
   *
   */
  var extForeignobject = {
    name: 'foreignobject',

    async init(S) {
      const svgEditor = this;
      const {
        $,
        text2xml,
        NS,
        importLocale
      } = S;
      const svgCanvas = svgEditor.canvas;
      const // {svgcontent} = S,
      // addElem = svgCanvas.addSVGElementFromJson,
      svgdoc = S.svgroot.parentNode.ownerDocument;
      const strings = await importLocale();

      const properlySourceSizeTextArea = function () {
        // TODO: remove magic numbers here and get values from CSS
        const height = $('#svg_source_container').height() - 80;
        $('#svg_source_textarea').css('height', height);
      };
      /**
      * @param {boolean} on
      * @returns {void}
      */


      function showPanel(on) {
        let fcRules = $('#fc_rules');

        if (!fcRules.length) {
          fcRules = $('<style id="fc_rules"></style>').appendTo('head');
        }

        fcRules.text(!on ? '' : ' #tool_topath { display: none !important; }');
        $('#foreignObject_panel').toggle(on);
      }
      /**
      * @param {boolean} on
      * @returns {void}
      */


      function toggleSourceButtons(on) {
        $('#tool_source_save, #tool_source_cancel').toggle(!on);
        $('#foreign_save, #foreign_cancel').toggle(on);
      }

      let selElems,
          started,
          newFO,
          editingforeign = false;
      /**
      * This function sets the content of element elt to the input XML.
      * @param {string} xmlString - The XML text
      * @returns {boolean} This function returns false if the set was unsuccessful, true otherwise.
      */

      function setForeignString(xmlString) {
        const elt = selElems[0]; // The parent `Element` to append to

        try {
          // convert string into XML document
          const newDoc = text2xml('<svg xmlns="' + NS.SVG + '" xmlns:xlink="' + NS.XLINK + '">' + xmlString + '</svg>'); // run it through our sanitizer to remove anything we do not support

          svgCanvas.sanitizeSvg(newDoc.documentElement);
          elt.replaceWith(svgdoc.importNode(newDoc.documentElement.firstChild, true));
          svgCanvas.call('changed', [elt]);
          svgCanvas.clearSelection();
        } catch (e) {
          // Todo: Surface error to user
          console.log(e); // eslint-disable-line no-console

          return false;
        }

        return true;
      }
      /**
      *
      * @returns {void}
      */


      function showForeignEditor() {
        const elt = selElems[0];

        if (!elt || editingforeign) {
          return;
        }

        editingforeign = true;
        toggleSourceButtons(true);
        elt.removeAttribute('fill');
        const str = svgCanvas.svgToString(elt, 0);
        $('#svg_source_textarea').val(str);
        $('#svg_source_editor').fadeIn();
        properlySourceSizeTextArea();
        $('#svg_source_textarea').focus();
      }
      /**
      * @param {string} attr
      * @param {string|Float} val
      * @returns {void}
      */


      function setAttr(attr, val) {
        svgCanvas.changeSelectedAttribute(attr, val);
        svgCanvas.call('changed', selElems);
      }

      const buttons = [{
        id: 'tool_foreign',
        icon: svgEditor.curConfig.extIconsPath + 'foreignobject-tool.png',
        type: 'mode',
        events: {
          click() {
            svgCanvas.setMode('foreign');
          }

        }
      }, {
        id: 'edit_foreign',
        icon: svgEditor.curConfig.extIconsPath + 'foreignobject-edit.png',
        type: 'context',
        panel: 'foreignObject_panel',
        events: {
          click() {
            showForeignEditor();
          }

        }
      }];
      const contextTools = [{
        type: 'input',
        panel: 'foreignObject_panel',
        id: 'foreign_width',
        size: 3,
        events: {
          change() {
            setAttr('width', this.value);
          }

        }
      }, {
        type: 'input',
        panel: 'foreignObject_panel',
        id: 'foreign_height',
        events: {
          change() {
            setAttr('height', this.value);
          }

        }
      }, {
        type: 'input',
        panel: 'foreignObject_panel',
        id: 'foreign_font_size',
        size: 2,
        defval: 16,
        events: {
          change() {
            setAttr('font-size', this.value);
          }

        }
      }];
      return {
        name: strings.name,
        svgicons: svgEditor.curConfig.extIconsPath + 'foreignobject-icons.xml',
        buttons: strings.buttons.map((button, i) => {
          return Object.assign(buttons[i], button);
        }),
        context_tools: strings.contextTools.map((contextTool, i) => {
          return Object.assign(contextTools[i], contextTool);
        }),

        callback() {
          $('#foreignObject_panel').hide();

          const endChanges = function () {
            $('#svg_source_editor').hide();
            editingforeign = false;
            $('#svg_source_textarea').blur();
            toggleSourceButtons(false);
          }; // TODO: Needs to be done after orig icon loads


          setTimeout(function () {
            // Create source save/cancel buttons

            /* const save = */
            $('#tool_source_save').clone().hide().attr('id', 'foreign_save').unbind().appendTo('#tool_source_back').click(async function () {
              if (!editingforeign) {
                return;
              }

              if (!setForeignString($('#svg_source_textarea').val())) {
                const ok = await $.confirm('Errors found. Revert to original?');

                if (!ok) {
                  return;
                }

                endChanges();
              } else {
                endChanges();
              } // setSelectMode();

            });
            /* const cancel = */

            $('#tool_source_cancel').clone().hide().attr('id', 'foreign_cancel').unbind().appendTo('#tool_source_back').click(function () {
              endChanges();
            });
          }, 3000);
        },

        mouseDown(opts) {
          // const e = opts.event;
          if (svgCanvas.getMode() !== 'foreign') {
            return undefined;
          }

          started = true;
          newFO = svgCanvas.addSVGElementFromJson({
            element: 'foreignObject',
            attr: {
              x: opts.start_x,
              y: opts.start_y,
              id: svgCanvas.getNextId(),
              'font-size': 16,
              // cur_text.font_size,
              width: '48',
              height: '20',
              style: 'pointer-events:inherit'
            }
          });
          const m = svgdoc.createElementNS(NS.MATH, 'math');
          m.setAttributeNS(NS.XMLNS, 'xmlns', NS.MATH);
          m.setAttribute('display', 'inline');
          const mi = svgdoc.createElementNS(NS.MATH, 'mi');
          mi.setAttribute('mathvariant', 'normal');
          mi.textContent = '\u03A6';
          const mo = svgdoc.createElementNS(NS.MATH, 'mo');
          mo.textContent = '\u222A';
          const mi2 = svgdoc.createElementNS(NS.MATH, 'mi');
          mi2.textContent = '\u2133';
          m.append(mi, mo, mi2);
          newFO.append(m);
          return {
            started: true
          };
        },

        mouseUp(opts) {
          // const e = opts.event;
          if (svgCanvas.getMode() !== 'foreign' || !started) {
            return undefined;
          }

          const attrs = $(newFO).attr(['width', 'height']);
          const keep = attrs.width !== '0' || attrs.height !== '0';
          svgCanvas.addToSelection([newFO], true);
          return {
            keep,
            element: newFO
          };
        },

        selectedChanged(opts) {
          // Use this to update the current selected elements
          selElems = opts.elems;
          let i = selElems.length;

          while (i--) {
            const elem = selElems[i];

            if (elem && elem.tagName === 'foreignObject') {
              if (opts.selectedElement && !opts.multiselected) {
                $('#foreign_font_size').val(elem.getAttribute('font-size'));
                $('#foreign_width').val(elem.getAttribute('width'));
                $('#foreign_height').val(elem.getAttribute('height'));
                showPanel(true);
              } else {
                showPanel(false);
              }
            } else {
              showPanel(false);
            }
          }
        },

        elementChanged(opts) {// const elem = opts.elems[0];
        }

      };
    }

  };

  return extForeignobject;

}());
