package net.mkonrad.synes.util;

import java.awt.Font;
import java.util.Collection;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Iterator;

import javax.media.j3d.Appearance;
import javax.media.j3d.BranchGroup;
import javax.media.j3d.Geometry;
import javax.media.j3d.Group;
import javax.media.j3d.Node;
import javax.media.j3d.Shape3D;
import javax.media.j3d.Transform3D;
import javax.media.j3d.TransformGroup;
import javax.vecmath.Color3f;
import javax.vecmath.Point3f;
import javax.vecmath.Vector3d;
import javax.vecmath.Vector3f;

import net.mkonrad.synes.ctrl.BeatTimingBehavior;
import net.mkonrad.synes.data.AbstractGraph;
import net.mkonrad.synes.data.SynthObj;
import net.mkonrad.synes.gui.style.Colors;

import com.sun.j3d.utils.geometry.Text2D;
import com.sun.j3d.utils.picking.PickTool;

public class Common3DTools
{
  public static float distance2D(Point3f p1, Point3f p2)
  {
    float dX = (p1.x - p2.x);
    float dY = (p1.y - p2.y);
    
    return (float)Math.sqrt(dX * dX + dY * dY);
  }
  
  public static float rising2D(Point3f p1, Point3f p2)
  {
    float dX = (p1.x - p2.x);
    float dY = (p1.y - p2.y);
    
    return dY / dX;
  }
  
  public static TransformGroup writeText(Vector3d p, String text)
  {
    return writeText(p, text, 36, Colors.white, "SansSerif", Font.PLAIN);
  }
  
  public static TransformGroup writeText(Vector3d p, String text, Color3f color)
  {
    return writeText(p, text, 36, color, "SansSerif", Font.PLAIN);
  }
  
  public static TransformGroup writeText(Vector3d p, String text, int fontSize)
  {
    return writeText(p, text, fontSize, Colors.white, "SansSerif", Font.PLAIN);
  }
  
  public static TransformGroup writeText(Vector3d p, String text, int fontSize, Color3f color,
      String font, int fontSpecial)
  {
    TransformGroup tg = new TransformGroup();
    Transform3D t3d = new Transform3D();
    t3d.setTranslation(p);
    tg.setTransform(t3d);
    
    writeText(tg, text, fontSize, color, font, fontSpecial);
    
    return tg;
  }
  
  /**
   * Writes a text messages and adds it to the TransformGroup tg
   * @param tg          Transform group to which the text will be added as child
   * @param text        The text message
   * @param fontSize    Font size
   * @param color       Font color
   * @param font        Font family
   * @param fontSpecial Special font modifiers (e.g. Font.ITALIC, Font.BOLD,
   *                    etc.)
   */
  public static void writeText(TransformGroup tg, String text, int fontSize,
      Color3f color, String font, int fontSpecial)
  {
    Text2D message = new Text2D(text, color, font, fontSize, fontSpecial);
    message.setPickable(false);
    
    tg.addChild(wrapInBG(message, new int[] { BranchGroup.ALLOW_DETACH }));
  }

  public static BranchGroup wrapInBG(Node n)
  {
    return wrapInBG(n, new int[] { });
  }
  
  public static BranchGroup wrapInBG(Node n, int[] capabilityBits)
  {
    BranchGroup bg = new BranchGroup();
    
    for (int i = 0; i < capabilityBits.length; i++)
      bg.setCapability(capabilityBits[i]);
    
    bg.addChild(n);
    
    return bg;
  }

  /**
   * Convert a Vector3f into a Point3f
   * @param v Vector3f
   * @return Point3f
   */
  public static Point3f v2p(Vector3f v)
  {
    return new Point3f(v.x, v.y, v.z);
  }
}
