package ethanjones.cubes.graphics.menus;

import ethanjones.cubes.core.localization.Localization;
import ethanjones.cubes.core.platform.Adapter;
import ethanjones.cubes.core.settings.Setting;
import ethanjones.cubes.core.settings.SettingGroup;
import ethanjones.cubes.core.settings.Settings;
import ethanjones.cubes.core.settings.VisualSettingManager;
import ethanjones.cubes.core.system.CubesException;
import ethanjones.cubes.graphics.menu.Menu;
import ethanjones.cubes.graphics.menu.MenuTools;

import com.badlogic.gdx.scenes.scene2d.Actor;
import com.badlogic.gdx.scenes.scene2d.Event;
import com.badlogic.gdx.scenes.scene2d.ui.*;
import com.badlogic.gdx.scenes.scene2d.utils.Layout;
import com.badlogic.gdx.utils.Align;

import java.util.ArrayList;
import java.util.Map;

import static ethanjones.cubes.graphics.Graphics.GUI_HEIGHT;
import static ethanjones.cubes.graphics.Graphics.GUI_WIDTH;

public class SettingsMenu extends Menu implements VisualSettingManager {

  public static class SaveEvent extends Event {

  }

  private static class ListObject {

    public final Label label;
    public final Actor actor;

    public ListObject(Label label, Actor actor) {
      this.label = label;
      this.actor = actor;
      if (!(actor instanceof Layout)) throw new CubesException("Settings actor must implement Layout");
    }
  }

  static final Value CELL_PADDING = new Value() {
    @Override
    public float get(Actor context) {
      return 5;
    }
  };
  static final Value CELL_WIDTH = new Value() {

    @Override
    public float get(Actor context) {
      return (GUI_WIDTH / 2) - (CELL_PADDING.get(context) * 2);
    }
  };
  static final Value CELL_HEIGHT = new Value() {
    @Override
    public float get(Actor context) {
      return (GUI_HEIGHT / 10) - (CELL_PADDING.get(context) * 2);
    }
  };
  static SaveEvent saveEvent = new SaveEvent();
  private final SettingGroup settingGroup;
  Label title;
  ScrollPane scrollPane;
  Table table;
  TextButton back;
  ArrayList<ListObject> listObjects = new ArrayList<ListObject>();

  public SettingsMenu() {
    this(Settings.getBaseSettingGroup());
  }

  public SettingsMenu(SettingGroup settingGroup) {
    this.settingGroup = settingGroup;

    title = new Label(Localization.get("menu.settings.title"), skin.get("title", Label.LabelStyle.class));

    table = new Table(skin);

    for (Map.Entry<String, SettingGroup> entry : settingGroup.getChildGroups().entrySet()) {
      if (!entry.getValue().shouldDisplay()) continue;
      Label name = new Label(Settings.getLocalisedSettingGroupName(entry.getKey()), skin);
      name.setAlignment(Align.left, Align.left);

      Actor actor = entry.getValue().getActor(this);

      listObjects.add(new ListObject(name, actor));
    }

    for (String str : settingGroup.getChildren()) {
      Setting setting = Settings.getSetting(str);
      if (!setting.shouldDisplay()) continue;

      Label name = new Label(Settings.getLocalisedSettingGroupName(str), skin);
      name.setAlignment(Align.left, Align.left);

      Actor actor = setting.getActor(this);

      listObjects.add(new ListObject(name, actor));
    }

    scrollPane = new ScrollPane(table, skin);
    scrollPane.setScrollingDisabled(true, false);

    back = MenuTools.getBackButton(this);

    stage.addActor(title);
    stage.addActor(scrollPane);
    stage.addActor(back);
  }

  @Override
  public void resize(float width, float height) {
    super.resize(width, height);

    scrollPane.setBounds(0, height / 6, width, height / 6 * 4);

    table.setWidth(width);
    table.clearChildren();

    for (int i = 0; i < listObjects.size(); i++) {
      ListObject listObject = listObjects.get(i);

      table.add(listObject.label).width(CELL_WIDTH).height(CELL_HEIGHT).pad(CELL_PADDING).fillX().fillY();
      table.add(listObject.actor).width(CELL_WIDTH).height(CELL_HEIGHT).pad(CELL_PADDING).fillX().fillY();
      table.row();
    }

    scrollPane.layout();

    MenuTools.setTitle(title);
    back.setBounds(width / 4, 0, width / 2, height / 6);
  }

  public void save() {
    for (ListObject listObject : listObjects) {
      saveEvent.reset();
      listObject.actor.fire(saveEvent);
    }
    Settings.write();
  }

  @Override
  public void setSettingGroup(SettingGroup settingGroup) {
    Adapter.setMenu(new SettingsMenu(settingGroup));
  }
}

@@ -774,69 +774,8 @@
 p;%0A%0A
-import static ethanjones.cubes.graphics.Graphics.GUI_HEIGHT;%0A
 impo
@@ -1304,452 +1304,116 @@
 ELL_
-PADDING = new Value() %7B%0A    @Override%0A    public float get(Actor context) %7B%0A      return 5;%0A    %7D%0A  %7D;%0A  static final Value CELL_WIDTH = new Value() %7B%0A%0A    @Override%0A    public float get(Actor context) %7B%0A      return (GUI_WIDTH / 2) - (CELL_PADDING.get(context) * 2);%0A    %7D%0A  %7D;%0A  static final Value CELL_HEIGHT = new Value() %7B%0A    @Override%0A    public float get(Actor context) %7B%0A      return (GUI_HEIGHT / 10) - (CELL_PADDING.get(context) * 2)
+WIDTH = new Value() %7B%0A%0A    @Override%0A    public float get(Actor context) %7B%0A      return (GUI_WIDTH / 2) - 10
 ;%0A  
@@ -2969,229 +2969,82 @@
 k);%0A
-  %7D%0A%0A  @Override%0A  public void resize(float width, float height) %7B%0A    super.resize(width, height);%0A%0A    scrollPane.setBounds(0, height / 6, width, height / 6 * 4);%0A%0A    table.setWidth(width);%0A    table.clearChildren
+%0A    table.defaults().width(CELL_WIDTH).pad(5).fillX().fillY().uniform
 ();%0A
-%0A
     
@@ -3178,214 +3178,262 @@
 bel)
-.width(CELL_WIDTH).height(CELL_HEIGHT).pad(CELL_PADDING).fillX().fillY();%0A      table.add(listObject.actor).width(CELL_WIDTH).height(CELL_HEIGHT).pad(CELL_PADDING).fillX().fillY(
+;%0A      table.add(listObject.actor);%0A      table.row();%0A    %7D%0A  %7D%0A%0A  @Override%0A  public void resize(float width, float height) %7B%0A    super.resize(width, height
 );%0A
+%0A
     
-  table.row(
+scrollPane.setBounds(0, height / 6, width, height / 6 * 4
 );%0A
+%0A
     
-%7D%0A
+table.setWidth(width);
 %0A   

Fix SettingsMenu to adapt height of cells