package com.example.jmacro.wjdr.util;

import cn.hutool.core.img.ImgUtil;
import cn.hutool.log.StaticLog;

import javax.swing.*;
import javax.swing.filechooser.FileNameExtensionFilter;
import java.awt.*;
import java.awt.event.*;
import java.awt.image.BufferedImage;
import java.io.File;
import java.util.prefs.Preferences;

/**
 * 辅助截屏工具
 */
public class Capture extends JFrame {

    private static final String LAST_PATH = "capture.last.path";

    /**
     * 参照原点x坐标
     */
    private int originX;
    /**
     * 参照原点y坐标
     */
    private int originY;

    /**
     * 全屏幕截图
     */
    private BufferedImage capture;

    /**
     * 背景蒙层
     */
    private Color mask = new Color(0, 0, 0, 0.2f);

    /**
     * 聚焦框线条
     */
    private Stroke focusWindow = new BasicStroke(1.0f);

    /**
     * 屏幕截图区域起始坐标
     */
    private Point start = new Point(0, 0);

    /**
     * 屏幕截图区域结束坐标
     */
    private Point end = new Point(0, 0);

    private Preferences preferences;

    /**
     * 有参照原点的构造器
     *
     * @param originX 原点x
     * @param originY 原点y
     * @throws AWTException
     */
    public Capture(int originX, int originY, File path) throws AWTException {
        this();
        this.originX = originX;
        this.originY = originY;
        this.preferences.put(LAST_PATH, path.isDirectory() ? path.getAbsolutePath() : path.getParent());
    }

    public Capture() throws AWTException {
        init();
    }

    private void init() throws AWTException {
        setExtendedState(Frame.MAXIMIZED_BOTH);
        setLocation(0, 0);//位置
        setUndecorated(true);
        setAlwaysOnTop(true);
        setBackground(mask);

        // 初始化偏好设置
        preferences = Preferences.userRoot().node(this.getClass().getName());

        // 获取屏幕截图
        Robot robot = new Robot();
        Toolkit tk = Toolkit.getDefaultToolkit();
        capture = robot.createScreenCapture(new Rectangle(0, 0, tk.getScreenSize().width, tk.getScreenSize().height));

        // 监听窗口关闭
        addWindowListener(new WindowAdapter() {
            @Override
            public void windowClosing(WindowEvent e) {
                // 关闭应用时要释放资源
                dispose();
                System.exit(0);//0正常退出，1非正常退出
            }
        });

        addMouseListener(new MouseAdapter() {
            @Override
            public void mousePressed(MouseEvent e) {
                super.mousePressed(e);
                start.setLocation(e.getX(), e.getY());
                end.setLocation(e.getX(), e.getY());
                Logger.info("起始坐标：{}", start);
                repaint();
            }

            @Override
            public void mouseReleased(MouseEvent e) {
                super.mouseReleased(e);
                end.setLocation(e.getX(), e.getY());
                Logger.info("结束坐标：{}", end);
                save();
            }
        });

        addMouseMotionListener(new MouseMotionAdapter() {
            @Override
            public void mouseDragged(MouseEvent e) {
                super.mouseDragged(e);
                end.setLocation(e.getX(), e.getY());
                repaint();
            }
        });

        addKeyListener(new KeyAdapter() {

            @Override
            public void keyReleased(KeyEvent e) {
                switch (e.getKeyCode()) {
                    case KeyEvent.VK_ESCAPE: {
                        StaticLog.info("exit.");
                        close();
                    }
                    break;
                }

            }
        });

        setVisible(true);
    }

    @Override
    public void doLayout() {
        super.doLayout();
    }

    @Override
    public void paint(Graphics g) {
        super.paint(g);
        Graphics2D g2d = (Graphics2D) g;
        g2d.drawImage(capture, 0, 0, capture.getWidth(), capture.getHeight(), this);

        // 在背景图上加个蒙层
        g2d.setColor(mask);
        g2d.fillRect(0, 0, capture.getWidth(), capture.getHeight());

        int w = getCaptureWidth();
        int h = getCaptureHeight();
        if (w > 0 && h > 0) {
            g2d.setStroke(focusWindow);
            g2d.setColor(Color.green);
            g2d.drawRect(getCaptureX(), getCaptureY(), w, h);
        }
    }

    public int getCaptureX() {
        return (int) Math.min(start.getX(), end.getX());
    }

    public int getCaptureY() {
        return (int) Math.min(start.getY(), end.getY());
    }

    public int getCaptureWidth() {
        return (int) Math.abs(start.getX() - end.getX());
    }

    public int getCaptureHeight() {
        return (int) Math.abs(start.getY() - end.getY());
    }

    public void save() {
        // 上一次保存目录
        String lastPath = preferences.get(LAST_PATH, "");
        // 默认文件名
        String location = "_L" + (getCaptureX() - originX) + "," + (getCaptureY() - originY);
        String filename = System.currentTimeMillis() + location + ".png";

        JFileChooser jFileChooser = new JFileChooser();
        jFileChooser.setFileFilter(new FileNameExtensionFilter("png", "png"));
        jFileChooser.setFileSelectionMode(JFileChooser.FILES_ONLY);
        jFileChooser.setCurrentDirectory(new File(lastPath));
        jFileChooser.setSelectedFile(new File(filename));
        int returnVal = jFileChooser.showSaveDialog(this);
        if (returnVal == JFileChooser.APPROVE_OPTION) {
            // 默认文件
            File file = jFileChooser.getSelectedFile();
            // 修正坐标
            filename = file.getName().replaceAll("(_L[0-9]+,[0-9]+)?.png", "") + location + ".png";
            file = new File(file.getParent(), filename);

            Logger.info("保存路径" + file);
            ImgUtil.cut(capture, file, new Rectangle(getCaptureX(), getCaptureY(), getCaptureWidth(), getCaptureHeight()));

            preferences.put(LAST_PATH, file.getParent());
            Logger.info("保存目录" + file.getParent());
            Logger.info("保存地址" + file);
        }
        close();
    }

    public void close() {
        // 关闭应用时要释放资源
        dispose();
        System.exit(0);
    }

    /**
     * 工具入口
     *
     * @param args
     * @throws AWTException
     */
    public static void main(String[] args) throws AWTException {
        // 运行坐标图例截图工具
        new Capture(5, 5, new File("legend"));
    }
}
