package Übungen.MeinAltesSpiel;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Scanner;

public class Modell {
    private String name;
    private ArrayList<Integer> karten;
    private ArrayList<String> figurenkarten;

    public Modell(String name) {
        this.name = name;
        karten = new ArrayList<>();
        figurenkarten = new ArrayList<>();
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public ArrayList<Integer> getKarten() {
        return karten;
    }

    public void setKarten(ArrayList<Integer> karten) {
        this.karten = karten;
    }

    public ArrayList<String> getFigurenkarten() {
        return figurenkarten;
    }

    public void setFigurenkarten(ArrayList<String> figurenkarten) {
        this.figurenkarten = figurenkarten;
    }

    @Override
    public String toString() {
        return "Modell [name=" + name + ", karten=" + karten + "]";
    }
}

class Controller {
    private Modell spieler1;
    private Modell spieler2;
    private View view;
    private ArrayList<Integer> karten;
    private ArrayList<String> figurenkarten;
    private ArrayList<Integer> spielfeld;
    private ArrayList<Integer> aktuelleZweiKarten;

    private static final int JACK_KARTEN = 10;
    private static final int DAME_KARTEN = 15;
    private static final int KOENIG_KARTEN = 25;

    public Controller(Modell spieler1, Modell spieler2, View view) {
        this.spieler1 = spieler1;
        this.spieler2 = spieler2;
        this.view = view;

        karten = new ArrayList<>();
        figurenkarten = new ArrayList<>();
        spielfeld = new ArrayList<>();
        aktuelleZweiKarten = new ArrayList<>(Collections.nCopies(2, 0));
    }

    public void setFigurenkarten() {
        for (int i = 1; i <= 4; i++) {
            figurenkarten.add("Jack");
            figurenkarten.add("Dame");
            figurenkarten.add("König");
        }

        ArrayList<String> kartenFuerSpieler1 = new ArrayList<>(figurenkarten.subList(0, 6));
        ArrayList<String> kartenFuerSpieler2 = new ArrayList<>(figurenkarten.subList(6, 12));

        spieler1.setFigurenkarten(kartenFuerSpieler1);
        spieler2.setFigurenkarten(kartenFuerSpieler2);
    }

    public void setKarten() {
        for (int i = 1; i <= 4; i++) {
            for (int j = 1; j <= 9; j++) {
                karten.add(j);
            }
        }

        Collections.shuffle(karten);

        ArrayList<Integer> kartenFuerSpieler1 = new ArrayList<>(karten.subList(0, 18));
        ArrayList<Integer> kartenFuerSpieler2 = new ArrayList<>(karten.subList(18, 36));

        spieler1.setKarten(kartenFuerSpieler1);
        spieler2.setKarten(kartenFuerSpieler2);
    }

    public void werfeEineKarte(Modell spieler) {
        if (!spieler.getKarten().isEmpty()) {
            spielfeld.add(spieler.getKarten().remove(0));
            aktuelleZweiKarten.set(0, spieler1.getKarten().get(0));
            aktuelleZweiKarten.set(1, spieler1.getKarten().get(1));
        } else {
            handleKeineKartenMehr(spieler);
        }
    }

    private void handleKeineKartenMehr(Modell spieler) {
        Modell gegner = (spieler == spieler1) ? spieler2 : spieler1;
        view.zeigeNachricht("Du hast keine Karten mehr!");
        String auswahl = view.frageUser("Möchtest Du Karten kaufen? Ja/Nein");

        if (auswahl.equalsIgnoreCase("ja")) {
            boolean erfolgreich = false;
            while (!erfolgreich) {
                auswahl = view.frageUser("Aus dem Spielfeld oder von deinem Gegner?\nSpielfeld = S, Gegner = G");
                if (auswahl.equalsIgnoreCase("S")) {
                    erfolgreich = kaufeKarten(spieler, spielfeld);
                } else if (auswahl.equalsIgnoreCase("G")) {
                    erfolgreich = kaufeKarten(spieler, gegner.getKarten());
                } else {
                    view.zeigeErorr("Falsche Eingabe!");
                }
            }
        }
    }

    private boolean kaufeKarten(Modell käufer, ArrayList<Integer> quelle) {
        view.zeigeNachricht("Deine Figurenkarten: " + käufer.getFigurenkarten());
        String auswahl = view.frageUser("Wie viele Karten möchtest du kaufen? \nJack = 10 Karten, Dame = 15 Karten, König = 25 Karten");

        int anzahlKarten;
        switch (auswahl.toLowerCase()) {
            case "jack":
                anzahlKarten = JACK_KARTEN;
                break;
            case "dame":
                anzahlKarten = DAME_KARTEN;
                break;
            case "könig":
                anzahlKarten = KOENIG_KARTEN;
                break;
            default:
                view.zeigeErorr("Falsche Eingabe!");
                return false;
        }

        if (käufer.getFigurenkarten().contains(auswahl)) {
            ArrayList<Integer> neueKarten = new ArrayList<>();
            for (int i = 0; i < anzahlKarten && !quelle.isEmpty(); i++) {
                neueKarten.add(quelle.remove(0));
            }
            Collections.shuffle(neueKarten);
            käufer.getKarten().addAll(neueKarten);
            return true;
        } else {
            view.zeigeErorr("Diese Figurenkarte hast du nicht!");
            return false;
        }
    }

    public boolean checkGewinner(Modell verlierer) {
        Modell gewinner = (verlierer == spieler1) ? spieler2 : spieler1;
        if (verlierer.getKarten().isEmpty() && verlierer.getFigurenkarten().isEmpty()) {
            view.gewinner(gewinner.getName() + " hat gewonnen");
            return true;
        }
        return false;
    }
}

class View {
    private Scanner scanner = new Scanner(System.in);

    public void zeigeNachricht(String nachricht) {
        System.out.println(nachricht);
    }

    public void zeigeErorr(String nachricht) {
        System.err.println(nachricht);
    }

    public String frageUser(String nachricht) {
        System.out.println(nachricht);
        return scanner.nextLine();
    }

    public void gewinner(String nachricht) {
        System.out.println(nachricht);
    }
}
