using AGXUnity;
using UnityEngine;

public static class RandomExtensions
{
  public static double NextDouble(
      this System.Random random,
      double minValue,
      double maxValue )
  {
    return random.NextDouble() * ( maxValue - minValue ) + minValue;
  }
}

namespace PolyBag
{
  public class PolybagEmitter : ScriptComponent
  {
    [SerializeField]
    public bool RandomizeOrientation = true;

    [SerializeField]
    public float Interval = 5.0f;

    [SerializeField]
    public int MaxSpawnedBags = 5;

    [SerializeField]
    public float Length = 0.05f;

    [SerializeField]
    public float Width = 0.39f;

    [SerializeField]
    public float Height = 0.27f;

    [SerializeField]
    public float Compressibility = 0.1f;

    [SerializeField]
    public float Bendability = 0.9f;

    [SerializeField]
    public float Mass = 0.4f;

    [SerializeField]
    public bool UseContactReduction = true;


    [SerializeField]
    public Material RenderMaterial;

    [SerializeField]
    // Limitation: Can only contain one mesh! The mesh must also contain < 60000 vertices
    public Mesh PolybagMesh;

    private float m_lastInterval = 0f;
    private int m_spawnedBags = 0;

    private System.Random m_random = new System.Random();

    [SerializeField]
    private ShapeMaterial m_material = null;

    [AllowRecursiveEditing]
    public ShapeMaterial Material
    {
      get { return m_material; }
      set
      {
        m_material = value;
      }
    }


    protected override bool Initialize()
    {
      return true;
    }

    GameObject m_blueprint = null;

    // Update is called once per frame
    void Update()
    {
      if ( m_blueprint == null ) {
        m_blueprint = new GameObject();
        m_blueprint.transform.parent = transform;
        m_blueprint.SetActive( false );
        m_blueprint.name = "Polybag";
        m_blueprint.AddComponent<PolyBag>();
      }
      if ( Time.time - m_lastInterval >= Interval && m_spawnedBags < MaxSpawnedBags ) {
        var newBag = GameObject.Instantiate(m_blueprint);
        newBag.transform.parent = transform;
        newBag.SetActive( true );
        newBag.transform.position = this.transform.position;
        if ( RandomizeOrientation )
          newBag.transform.rotation = UnityEngine.Random.rotation * newBag.transform.rotation;
        else
          newBag.transform.rotation = this.transform.rotation;

        newBag.GetComponent<PolyBag>().InitParameters(
            PolyBag.ElementResolution.LOW,
            Length,
            Width,
            Height,
            Compressibility,
            Bendability,
            Mass,
            RenderMaterial, m_material,
            PolybagMesh,
            UseContactReduction );

        m_lastInterval = Time.time;
        m_spawnedBags++;


        ObjectSink.RegisterPolyBag( newBag );
      }
    }
  }
}