/*
 * {{{ header & license
 * Copyright (c) 2006 Patrick Wright
 * Copyright (c) 2007 Wisconsin Court System
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public License
 * as published by the Free Software Foundation; either version 2.1
 * of the License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.	See the
 * GNU Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 * }}}
 */
package org.xhtmlrenderer.demo.svg;

import com.kitfox.svg.SVGException;
import com.kitfox.svg.app.beans.SVGPanel;
import org.w3c.dom.Element;
import org.xhtmlrenderer.extend.ReplacedElement;
import org.xhtmlrenderer.extend.ReplacedElementFactory;
import org.xhtmlrenderer.extend.UserAgentCallback;
import org.xhtmlrenderer.layout.LayoutContext;
import org.xhtmlrenderer.render.BlockBox;
import org.xhtmlrenderer.simple.extend.FormSubmissionListener;
import org.xhtmlrenderer.swing.SwingReplacedElement;
import org.xhtmlrenderer.util.XRLog;

import javax.swing.*;
import java.util.logging.Level;
import java.awt.*;


/**
 * Factory to create ReplacedElements for SVG embedded in our XML file, using
 * the Salamander library. Salamander in this case will return a Swing JPanel.
 */
public class SVGSalamanderReplacedElementFactory implements ReplacedElementFactory {

    public ReplacedElement createReplacedElement(
            LayoutContext c,
            BlockBox box,
            UserAgentCallback uac,
            int cssWidth,
            int cssHeight) {

        SVGPanel panel = new SVGPanel();
        String content = null;
        JComponent cc = null;
        try {
            Element elem = box.getElement();
            if (elem == null || ! isSVGEmbedded(elem)) {
                return null;
            }

            // HACK: the easiest way to integrate with Salamander is to have it read
            // our SVG from a file--so, push the content to a temporary file, yuck!
            content = getSVGElementContent(elem);

            String path = elem.getAttribute("data");
            XRLog.general(Level.FINE, "Rendering embedded SVG via object tag from: " + path);
            XRLog.general(Level.FINE, "Content is: " + content);
            panel.setAntiAlias(true);
            panel.setSvgResourcePath(path);

            int width = panel.getSVGWidth();
            int height = panel.getSVGHeight();

            if ( cssWidth > 0 ) width = cssWidth;

            if ( cssHeight > 0 ) height = cssHeight;

            String val = elem.getAttribute("width");
            if ( val != null && val.length() > 0 ) {
                width = Integer.valueOf(val).intValue();
            }
            val = elem.getAttribute("height");
            if ( val != null && val.length() > 0 ) {
                height = Integer.valueOf(val).intValue();
            }
            panel.setScaleToFit(true);
            panel.setPreferredSize(new Dimension(width, height));
            panel.setSize(panel.getPreferredSize());

            cc = panel;
        } catch (SVGException e) {
            XRLog.general(Level.WARNING, "Could not replace SVG element; rendering failed" +
                    " in SVG renderer. Skipping and using blank JPanel.", e);
            cc = getDefaultJComponent(content, cssWidth, cssHeight);
        }
        if (cc == null) {
            return null;
        } else {
            SwingReplacedElement result = new SwingReplacedElement(cc);
            if (c.isInteractive()) {
                c.getCanvas().add(cc);
            }
            return result;
        }
    }

    private String getSVGElementContent(Element elem) {
        if ( elem.getChildNodes().getLength() > 0 ) {
            return elem.getFirstChild().getNodeValue();
        } else {
            return "SVG";
        }
    }

    private boolean isSVGEmbedded(Element elem) {
        return elem.getNodeName().equals("object") && elem.getAttribute("type").equals("image/svg+xml");
    }

    private JComponent getDefaultJComponent(String content, int width, int height) {
        JPanel panel = new JPanel();
        panel.setLayout(new BorderLayout());
        JLabel comp = new JLabel(content);
        panel.add(comp, BorderLayout.CENTER);
        panel.setOpaque(false);
        if ( width > 0 && height > 0 ) {
            panel.setPreferredSize(new Dimension(width, height));
            panel.setSize(panel.getPreferredSize());
        } else {
            panel.setPreferredSize(comp.getPreferredSize());
            panel.setSize(comp.getPreferredSize());
        }
        return panel;
    }

    public void reset() {

    }

    public void remove(Element e) {

    }

    public void setFormSubmissionListener(FormSubmissionListener listener) {
        // nothing to do ?
    }
}
