package ru.testing.client;

import com.beust.jcommander.JCommander;
import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.scene.image.Image;
import javafx.stage.Stage;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import ru.testing.client.config.ApplicationType;
import ru.testing.client.config.Configuration;
import ru.testing.client.gui.MainController;
import ru.testing.client.websocket.Client;

import javax.websocket.MessageHandler;
import java.net.URI;
import java.util.Scanner;

/**
 * Main application class
 */
public class MainApp extends Application {

    private static final Logger LOGGER = LoggerFactory.getLogger(MainApp.class);
    private static final double PRIMARY_STAGE_MIN_WIDTH = 680;
    private static final double PRIMARY_STAGE_MIN_HEIGHT = 490;

    /**
     * Entry point to application
     * @param args String[]
     */
    public static void main(String[] args) {
        Configuration config = new Configuration();
        JCommander parser = new JCommander();
        parser.setProgramName("java -jar ws.client-${version}.jar");
        parser.addObject(config);
        try {
            parser.parse(args);

            // show help application option
            if (config.isHelp()) {
                parser.usage();
                System.exit(0);
            }

            // select application type
            if (config.getType() == ApplicationType.console) {
                if (config.getServerUrl().isEmpty()) {
                    LOGGER.error("WebSocket server url required");
                    parser.usage();
                    System.exit(1);
                }
                startConsoleClient(config.getServerUrl());
            } else {
                launch(args);
            }
        } catch (Exception e) {
            LOGGER.error("Running exception: {}", e.getMessage());
            parser.usage();
            System.exit(1);
        }
    }

    /**
     * Start javafx application window
     * @param primaryStage Stage
     * @throws Exception
     */
    @Override
    public void start(Stage primaryStage) throws Exception {
        FXMLLoader loader = new FXMLLoader(getClass().getResource("/view/main.fxml"));
        loader.setController(new MainController(primaryStage));
        Parent root = loader.load();
        Scene scene = new Scene(root);
        scene.getStylesheets().addAll(getClass().getResource("/styles/main.css").toExternalForm());
        try {
            Image image = new Image(getClass().getResource("/images/icon.png").toExternalForm());
            if (image.getHeight() == 0) {
                throw new Exception();
            }
            primaryStage.getIcons().addAll(image);
        } catch (Exception e) {
            LOGGER.error("Icon was not found");
        }
        primaryStage.setTitle("WebSocket client");
        primaryStage.setMinWidth(PRIMARY_STAGE_MIN_WIDTH);
        primaryStage.setMinHeight(PRIMARY_STAGE_MIN_HEIGHT);
        primaryStage.setScene(scene);
        primaryStage.setResizable(true);
        primaryStage.show();
    }

    /**
     * Start console websocket client
     * @param url String
     */
    private static void startConsoleClient(String url) {
        try {
            LOGGER.info("Connecting to {} ...", url);
            final Client client = new Client(new URI(url));
            String sendMessage;
            client.setMessageHandler(new MessageHandler.Whole<String>() {

                @Override
                public void onMessage(String message) {
                    LOGGER.info("Request: {}", message);
                }
            });
            LOGGER.info("For disconnect from server type 'exit'");
            while (true) {
                Scanner scanner = new Scanner(System.in);
                System.out.print("Send message: ");
                sendMessage = scanner.nextLine();
                if (sendMessage.equals("exit")) {
                    client.closeConnection();
                    break;
                }
                client.sendMessage(sendMessage);
                Thread.sleep(2000);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

@@ -484,24 +484,46 @@
 et.Client;%0A%0A
+import javax.swing.*;%0A
 import javax
@@ -570,16 +570,37 @@
 et.URI;%0A
+import java.net.URL;%0A
 import j
@@ -903,16 +903,83 @@
 T = 490;
+%0A    private static final String APP_ICON_URL = %22/images/icon.png%22;
 %0A%0A    /*
@@ -2539,446 +2539,40 @@
    s
-cene.getStylesheets().addAll(getClass().getResource(%22/styles/main.css%22).toExternalForm());%0A        try %7B%0A            Image image = new Image(getClass().getResource(%22/images/icon.png%22).toExternalForm());%0A            if (image.getHeight() == 0) %7B%0A                throw new Exception();%0A            %7D%0A            primaryStage.getIcons().addAll(image);%0A        %7D catch (Exception e) %7B%0A            LOGGER.error(%22Icon was not found%22);%0A        %7D
+etApplicationIcon(primaryStage);
 %0A   
@@ -3972,11 +3972,773 @@
  %7D%0A    %7D
+%0A%0A    /**%0A     * Set application icon%0A     * @param stage Stage%0A     */%0A    private void setApplicationIcon(Stage stage) %7B%0A        try %7B%0A            URL iconUrl = getClass().getResource(APP_ICON_URL);%0A            Image image = new Image(iconUrl.toExternalForm());%0A            if (image.getHeight() == 0) %7B%0A                throw new Exception();%0A            %7D%0A            stage.getIcons().addAll(image);%0A            if (System.getProperty(%22os.name%22).toLowerCase().contains(%22mac%22)) %7B%0A                java.awt.Image imageForMac = new ImageIcon(iconUrl).getImage();%0A                com.apple.eawt.Application.getApplication().setDockIconImage(imageForMac);%0A            %7D%0A        %7D catch (Exception e) %7B%0A            LOGGER.error(%22Icon was not found%22);%0A        %7D%0A    %7D
 %0A%7D%0A

set icon for mac dock