
package de.ivu.elect.business.stimmen.boundary;

import java.text.MessageFormat;

import javax.inject.Inject;

import de.ivu.elect.business.ergebnis.entity.Stimmenart;
import de.ivu.elect.business.gebietsbaum.entity.Gebiet;
import de.ivu.elect.business.gruppeimgebiet.entity.GruppeImGebiet;
import de.ivu.elect.business.kandidatur.boundary.WaehlerBenannteKandidaturKonfiguration;
import de.ivu.elect.business.stimmzettel.entity.EntityAufStimmzettelDaten;
import de.ivu.elect.business.wahl.entity.WahlartErgebnisart;

public class GruppeStimmeLabelGenerator extends AbstractStimmeLabelGenerator {

  private static final long serialVersionUID = 1L;

  @Inject
  private transient DirektstimmeLabelGenerator direktstimmeLabelGenerator;

  @Inject
  private transient ListenstimmeLabelGenerator listenstimmeLabelGenerator;

  @Inject
  private transient ReferendumStimmeLabelGenerator referendumStimmeLabelGenerator;

  public GruppeStimmeLabelGenerator() {
    super();
  }

  public GruppeStimmeLabelGenerator(StimmeLabelMessages stimmeLabelMessages, WaehlerBenannteKandidaturKonfiguration waehlerBenannteKandidaturKonfiguration) {
    this(stimmeLabelMessages, waehlerBenannteKandidaturKonfiguration, new DirektstimmeLabelGenerator(stimmeLabelMessages, waehlerBenannteKandidaturKonfiguration),
        new ListenstimmeLabelGenerator(stimmeLabelMessages, waehlerBenannteKandidaturKonfiguration), new ReferendumStimmeLabelGenerator(stimmeLabelMessages, waehlerBenannteKandidaturKonfiguration));
  }

  public GruppeStimmeLabelGenerator(StimmeLabelMessages stimmeLabelMessages, WaehlerBenannteKandidaturKonfiguration waehlerBenannteKandidaturKonfiguration,
      DirektstimmeLabelGenerator direktstimmeLabelGenerator, ListenstimmeLabelGenerator listenstimmeLabelGenerator, ReferendumStimmeLabelGenerator referendumStimmeLabelGenerator) {
    super(stimmeLabelMessages, waehlerBenannteKandidaturKonfiguration);

    this.direktstimmeLabelGenerator = direktstimmeLabelGenerator;
    this.listenstimmeLabelGenerator = listenstimmeLabelGenerator;

    this.referendumStimmeLabelGenerator = referendumStimmeLabelGenerator;
  }

  public DirektstimmeLabelGenerator getDirektstimmeLabelGenerator() {
    return direktstimmeLabelGenerator;
  }

  public ListenstimmeLabelGenerator getListenstimmeLabelGenerator() {
    return listenstimmeLabelGenerator;
  }

  public ReferendumStimmeLabelGenerator getReferendumStimmeLabelGenerator() {
    return referendumStimmeLabelGenerator;
  }

  public String getUngueltigeBezeichnungSingular(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String defaultValue = "Ungültige Stimme";

    if (isSystemGruppeUngueltigeErfasstAlsStimmzettel(gebiet, ergebnisart)) {
      defaultValue = "Ungültiger Stimmzettel";
    }

    return getSingularOrDefault(gebiet, ergebnisart, MSG_KEY_INFIX_UNGUELTIGE, defaultValue);
  }

  public String getUngueltigeBezeichnungPlural(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String defaultValue = "Ungültige Stimmen";

    if (isSystemGruppeUngueltigeErfasstAlsStimmzettel(gebiet, ergebnisart)) {
      defaultValue = "Ungültige Stimmzettel";
    }

    return getPluralOrDefault(gebiet, ergebnisart, MSG_KEY_INFIX_UNGUELTIGE, defaultValue);
  }

  public String getGueltigeBezeichnungSingular(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String defaultValue = "Gültige Stimme";

    if (isSystemGruppeGueltigeErfasstAlsStimmzettel(gebiet, ergebnisart)) {
      defaultValue = "Gültiger Stimmzettel";
    }

    return getSingularOrDefault(gebiet, ergebnisart, MSG_KEY_INFIX_GUELTIGE, defaultValue);
  }

  public String getGueltigeBezeichnungPlural(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String defaultValue = "Gültige Stimmen";

    if (isSystemGruppeGueltigeErfasstAlsStimmzettel(gebiet, ergebnisart)) {
      defaultValue = "Gültige Stimmzettel";
    }

    return getPluralOrDefault(gebiet, ergebnisart, MSG_KEY_INFIX_GUELTIGE, defaultValue);
  }

  public String formatStimmenAnzahlUngueltigeGesamtKennung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlUngueltigeGesamtKennung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlUngueltigeGesamtKennung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    return formatAnzahlUngueltigeStimmenartKennung(gebiet, Stimmenart.GESAMT);
  }

  public String formatStimmenAnzahlUngueltigeGesamtBezeichnung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlUngueltigeGesamtBezeichnung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlUngueltigeGesamtBezeichnung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String defaultValue = "Ungültige Stimmen";

    if (isSystemGruppeUngueltigeErfasstAlsStimmzettel(gebiet, ergebnisart)) {
      defaultValue = "Ungültige Stimmzettel";
    }

    return formatAnzahlUngueltigeStimmenartBezeichnung(gebiet, Stimmenart.GESAMT, defaultValue);
  }

  public String formatStimmzettelAnzahlUngueltigeGesamtKennung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return formatStimmzettelAnzahlUngueltigeGesamtKennung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  public String formatStimmzettelAnzahlUngueltigeGesamtKennung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    return getKennungOrDefault(gebiet, MSG_KEY_INFIX_STIMMZETTEL + ".ANZAHL." + MSG_KEY_INFIX_UNGUELTIGE + "." + MSG_KEY_INFIX_GESAMT, "");
  }

  public String formatStimmzettelAnzahlUngueltigeGesamtBezeichnung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return formatStimmzettelAnzahlUngueltigeGesamtBezeichnung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  public String formatStimmzettelAnzahlUngueltigeGesamtBezeichnung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    return getBezeichnungOrDefault(gebiet, MSG_KEY_INFIX_STIMMZETTEL + ".ANZAHL." + MSG_KEY_INFIX_UNGUELTIGE + "." + MSG_KEY_INFIX_GESAMT, "Ungültige Stimmzettel");
  }

  public String formatStimmenAnzahlGueltigeGesamtKennung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlGueltigeGesamtKennung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlGueltigeGesamtKennung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    return formatAnzahlGueltigeStimmenartKennung(gebiet, Stimmenart.GESAMT);
  }

  public String formatStimmenAnzahlGueltigeGesamtBezeichnung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlGueltigeGesamtBezeichnung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlGueltigeGesamtBezeichnung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String defaultValue = "Gültige Stimmen";

    if (isSystemGruppeGueltigeErfasstAlsStimmzettel(gebiet, ergebnisart)) {
      defaultValue = "Gültige Stimmzettel";
    }

    return formatAnzahlGueltigeStimmenartBezeichnung(gebiet, Stimmenart.GESAMT, defaultValue);
  }

  public String formatStimmzettelAnzahlGueltigeGesamtKennung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return formatStimmzettelAnzahlGueltigeGesamtKennung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  public String formatStimmzettelAnzahlGueltigeGesamtKennung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    return getKennungOrDefault(gebiet, MSG_KEY_INFIX_STIMMZETTEL + ".ANZAHL." + MSG_KEY_INFIX_GUELTIGE + "." + MSG_KEY_INFIX_GESAMT, "");
  }

  public String formatStimmzettelAnzahlGueltigeGesamtBezeichnung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return formatStimmzettelAnzahlGueltigeGesamtBezeichnung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  public String formatStimmzettelAnzahlGueltigeGesamtBezeichnung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    return getBezeichnungOrDefault(gebiet, MSG_KEY_INFIX_STIMMZETTEL + ".ANZAHL." + MSG_KEY_INFIX_GUELTIGE + "." + MSG_KEY_INFIX_GESAMT, "Ungültige Stimmzettel");
  }

  public String formatStimmenAnzahlUebrigeGesamtKennung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlUebrigeGesamtKennung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlUebrigeGesamtKennung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    return formatAnzahlUebrigeStimmenartKennung(gebiet, Stimmenart.GESAMT);
  }

  public String formatStimmenAnzahlUebrigeGesamtBezeichnung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlUebrigeGesamtBezeichnung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlUebrigeGesamtBezeichnung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    return formatAnzahlUebrigeStimmenartBezeichnung(gebiet, Stimmenart.GESAMT, "");
  }

  public String formatStimmenAnzahlAbgegebeneGesamtKennung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlAbgegebeneGesamtKennung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlAbgegebeneGesamtKennung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String msgKeyInfix = MSG_KEY_INFIX_ABGEGEBENE + ".ANZAHL." + MSG_KEY_INFIX_GESAMT;

    return getKennungOrDefault(gebiet, ergebnisart, msgKeyInfix, "");
  }

  public String formatStimmenAnzahlAbgegebeneGesamtBezeichnung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlAbgegebeneGesamtBezeichnung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlAbgegebeneGesamtBezeichnung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String defaultValue = "Abgegebene Stimmen insgesamt";

    if (isSystemGruppeGueltigeErfasstAlsStimmzettel(gebiet, ergebnisart) && isSystemGruppeUngueltigeErfasstAlsStimmzettel(gebiet, ergebnisart)) {
      defaultValue = "Abgegebene Stimmzettel insgesamt";
    }

    String msgKeyInfix = MSG_KEY_INFIX_ABGEGEBENE + ".ANZAHL." + MSG_KEY_INFIX_GESAMT;

    return getBezeichnungOrDefault(gebiet, ergebnisart, msgKeyInfix, defaultValue);
  }

  public String formatStimmenAnzahlGueltigeKennung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return getStimmenAnzahlGueltigeKennung(gruppeImGebiet.getGebiet(), ergebnisart);
  }

  protected String getStimmenAnzahlGueltigeKennung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String msgKeyInfix = MSG_KEY_INFIX_GUELTIGE + ".ANZAHL";

    return getKennungOrDefault(gebiet, ergebnisart, msgKeyInfix, "");
  }

  public String formatStimmenAnzahlGueltigeBezeichnung(EntityAufStimmzettelDaten entityAufStimmzettelDaten, GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart) {
    return format(getStimmenAnzahlGueltigeBezeichnung(gruppeImGebiet.getGebiet(), ergebnisart), entityAufStimmzettelDaten, gruppeImGebiet);
  }

  protected String getStimmenAnzahlGueltigeBezeichnung(Gebiet gebiet, WahlartErgebnisart ergebnisart) {
    String msgKeyInfix = MSG_KEY_INFIX_GUELTIGE + ".ANZAHL";

    return getBezeichnungOrDefault(gebiet, ergebnisart, msgKeyInfix, "{0}");
  }

  public String formatStimmenAnzahlUebrigeStimmenartKennung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart, Stimmenart stimmenart) {
    return formatStimmenAnzahlUebrigeStimmenartKennung(gruppeImGebiet.getGebiet(), ergebnisart, stimmenart);
  }

  public String formatStimmenAnzahlUebrigeStimmenartKennung(Gebiet gebiet, WahlartErgebnisart ergebnisart, Stimmenart stimmenart) {
    return formatAnzahlUebrigeStimmenartKennung(gebiet, stimmenart);
  }

  public String formatStimmenAnzahlUebrigeStimmenartBezeichnung(GruppeImGebiet gruppeImGebiet, WahlartErgebnisart ergebnisart, Stimmenart stimmenart) {
    return formatStimmenAnzahlUebrigeStimmenartBezeichnung(gruppeImGebiet.getGebiet(), ergebnisart, stimmenart);
  }

  public String formatStimmenAnzahlUebrigeStimmenartBezeichnung(Gebiet gebiet, WahlartErgebnisart ergebnisart, Stimmenart stimmenart) {
    return formatAnzahlUebrigeStimmenartBezeichnung(gebiet, stimmenart);
  }

  private String format(String pattern, EntityAufStimmzettelDaten entityAufStimmzettelDaten, GruppeImGebiet gruppeImGebiet) {
    return format(pattern, getWahlvorschlagStimmzettelKurzname(entityAufStimmzettelDaten, gruppeImGebiet));
  }

  private String format(String pattern, String value) {
    return MessageFormat.format(pattern, fixNullToEmpty(value));
  }
}
