package jguard.client.gui;

import jguard.client.gui.dialog.ObjectConnectionDialog;
import cucky.jGuard.lib.Message;
import cucky.jGuard.lib.object.Map;
import cucky.jGuard.lib.object.MapObject;
import java.awt.Point;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
import javax.swing.ImageIcon;
import javax.swing.JMenuItem;
import javax.swing.JPopupMenu;
import jguard.client.AppLauncher;
import jguard.client.Client;
import static jguard.client.gui.MapView.items;
import jguard.client.gui.dialog.ObjectDialog;

public class MapViewAction implements MouseListener, MouseMotionListener {

    private static PaintObject selectedObject;
    private static Point offset;
    public static boolean createConnection = false;
    public static PaintObject startConMapObject;
    public static PaintObject endConMapObject;
    public static Point endConnPoint;


    @Override
    public void mouseClicked(MouseEvent e) {
        // vola se pri kliknuti v mape
    }

    @Override
    public void mousePressed(MouseEvent e) { // vola se pri stisknuti tlacitka
        // vyhledani jestli se kliklo na nejaky objekt
        for (PaintObject node : items) {
            // zruseni vybrani na vsech objektech
            node.setSelected(false);
            if (node.contains(e.getPoint())) {
                if (createConnection) {
                    // vytvareni propojeni - startovni body 
                    startConMapObject = node;
                    endConnPoint = e.getPoint();
                } else {
                    selectedObject = node;
                    // nastaveni vybraneho objektu
                    offset = new Point(
                            (int) selectedObject.getBoxX() - e.getX(),
                            (int) selectedObject.getBoxY() - e.getY()
                    );
                    // zvyrazneni vybraneho objektu
                    selectedObject.setSelected(true);
                }
            }
        }
    }

    @Override
    public void mouseReleased(MouseEvent e) { // vola se pri uvolneni tlacitka 
        if (selectedObject != null) {
            // presouvani objektu
            if (!Client.map.get(Window.currentMapIndex).isLock()) {// povoli upravy jen kdyz neni mapa zamcena 
                // odeslani nove pozice objektu
                // TODO doresit kontrolu souradnic aby se zbytecne neodesilala zmena kdyz k ni nedojde
                int[] data = {
                    Client.map.get(Window.currentMapIndex).getId(),
                    selectedObject.getId(),
                    (int) selectedObject.getX(),
                    (int) selectedObject.getY()
                };
                Client.client.send(Message.MOVE_OBJECT, data);
            }
            // dvojklik na objekt
            if (e.getClickCount() == 2) {
                doubleClickOnObject(selectedObject);
            }
            // prave kliknuti na objekt
            if (e.getButton() == MouseEvent.BUTTON3) {
                rightClickOnObject(e, selectedObject);
            }
        } else {
            // prave kliknuti do volneho mista v mape
            if (e.getButton() == MouseEvent.BUTTON3) {
                rigthClick(e);
            }
        }
        selectedObject = null;
        offset = null;

        if (createConnection) {
            for (PaintObject node : items) {
                if (node.contains(e.getPoint())) {
                    endConMapObject = node;
                    if (startConMapObject.getId() != endConMapObject.getId()) {
                        new ObjectConnectionDialog(startConMapObject.getId(), endConMapObject.getId());
                    }
                }
            }
            // zrusi vytvareni propojeni 
            createConnection = false;
        }
    }

    @Override
    public void mouseEntered(MouseEvent e) {
        // vola se pri vstupu kurzoru
    }

    @Override
    public void mouseExited(MouseEvent e) {
        // vola se pri opusteni kurzoru 
    }

    
    @Override
    public void mouseDragged(MouseEvent e) {
        //jen pokud neni mapa zamcena 
        if (!Client.map.get(Window.currentMapIndex).isLock()) {
            // vytvareni propojeni
            if (createConnection) {
                for (PaintObject node : items) {
                    if (node.contains(e.getPoint())) {
                        endConnPoint = node.getPoint();
                        break;
                    } else {
                        endConnPoint = e.getPoint();
                    }
                }
            } else {
                // presunovani objektu
                if (this.selectedObject != null && this.offset != null) {
                    // ziskani novych souradnic
                    Point to = e.getPoint();
                    to.x += offset.x;
                    to.y += offset.y;
                    //nastaveni nove pozice
                    selectedObject.setPosition(to);
                }
            }
        }
    }

    @Override
    public void mouseMoved(MouseEvent e) {
        
    }
    
    
    
    
    private void doubleClickOnObject(PaintObject selectedObject) {
        int id = selectedObject.getId();
        for (Map m : Client.map) {
            for (MapObject ob : m.getObjects()) {
                if (ob.getId() == id) {
                    ObjectDialog objectDialog = new ObjectDialog(ob, false);
                    break;
                }
            }
        }
    }

    private void rigthClick(MouseEvent me) {
        JPopupMenu menu = new JPopupMenu();
        if (!Client.map.get(Window.currentMapIndex).isLock()) {
            // polozka pridat objekt 
            if (Client.user.isAddObject()) {
                JMenuItem itemAdd = new JMenuItem("Přidat objekt", new ImageIcon("img/add.png"));
                itemAdd.addActionListener(new ActionListener() {
                    @Override
                    public void actionPerformed(ActionEvent e) {
                        MapObject mo = new MapObject();
                        mo.setX(me.getX());
                        mo.setY(me.getY());
                        mo.setMap(Client.map.get(Window.currentMapIndex).getId());
                        new ObjectDialog(mo, true);
                    }
                });
                menu.add(itemAdd);
            }
            // polozka pridani propojeni
            JMenuItem itemPropoj = new JMenuItem("Přidat propojení", new ImageIcon("img/arrow.png"));
            itemPropoj.addActionListener(new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    startConMapObject = null;
                    endConnPoint = null;
                    createConnection = true;
                }
            });
            menu.add(itemPropoj);

        }
        // zamek mapy
        JMenuItem itemLock;
        boolean currentState = Client.map.get(Window.currentMapIndex).isLock();
        if (currentState) {
            itemLock = new JMenuItem("Odemknout mapu", new ImageIcon("img/unlock.png"));
        } else {
            itemLock = new JMenuItem("Zamknout mapu", new ImageIcon("img/lock.png"));
        }
        itemLock.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                if (currentState) {
                    int[] d = {Client.map.get(Window.currentMapIndex).getId(), 0};
                    Client.client.send(Message.SET_MAP_LOCK, d);
                } else {
                    int[] d = {Client.map.get(Window.currentMapIndex).getId(), 1};
                    Client.client.send(Message.SET_MAP_LOCK, d);
                }
            }
        });
        menu.add(itemLock);
        menu.show(me.getComponent(), me.getX(), me.getY());
    }

    private void rightClickOnObject(MouseEvent e, PaintObject obj) {
        JPopupMenu menu = new JPopupMenu();
        if (obj.getObject().getService().isWinbox()) {
            JMenuItem itemWinbox = new JMenuItem("Winbox", new ImageIcon("img/winbox.png"));
            itemWinbox.addActionListener(new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    AppLauncher.winbox(obj.getObject().getIp(), obj.getObject().getService().getPortWinbox(), obj.getObject().getUser(), obj.getObject().getPassword());
                }
            });
            menu.add(itemWinbox);
        }
        if (obj.getObject().getService().isWeb()) {
            JMenuItem itemWeb = new JMenuItem("Otevřít v prohlížeči", new ImageIcon("img/browser.png"));
            itemWeb.addActionListener(new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    AppLauncher.openWebpage(obj.getObject().getIp(), obj.getObject().getService().getPortWeb(), obj.getObject().getService().getVerzeWeb());
                }
            });
            menu.add(itemWeb);
        }
        if (obj.getObject().getService().isSsh()) {
            JMenuItem itemSsh = new JMenuItem("SSH", new ImageIcon("img/ssh.png"));
            itemSsh.addActionListener(new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    AppLauncher.ssh(obj.getObject().getIp(), obj.getObject().getUser(), obj.getObject().getPassword(), Integer.parseInt(obj.getObject().getService().getPortSsh()));
                }
            });
            menu.add(itemSsh);
        }

        /*
        JMenuItem itemWalk = new JMenuItem("SNMP walk");
        itemWalk.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
            }
        });
        menu.add(itemWalk);
         */
        // ping na objekt
        JMenuItem itemPing = new JMenuItem("Ping", new ImageIcon("img/ping.png"));
        itemPing.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
            }
        });
        menu.add(itemPing);

        // odebrani objektu
        if (!Client.map.get(Window.currentMapIndex).isLock() && Client.user.isRemoveMap()) {
            JMenuItem itemRemove = new JMenuItem("Odebrat", new ImageIcon("img/trash.png"));
            itemRemove.addActionListener(new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    //Main.client.send(Message.TYPE_REMOVE_OBJECT, obj.getId());
                }
            });
            menu.add(itemRemove);
        }

        // zobrazeni menu
        menu.show(e.getComponent(), e.getX(), e.getY());
    }


}
