package com.kurukurupapa.tryandroidui.dialog;

import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.RectF;

/**
 * 色相環ヘルパー
 */
public class BoxHsvColorPickerHueHelper {
	private static final float PI = 3.1415927f;

	// 色相環の幅
	private static final int CENTER_RADIUS = 24;

	// 色相環の色と色の隙間（単位：角度）
	private final double HUE_SPACE = 2.0;
	private final double HUE_HARF_SPACE = HUE_SPACE / 2.0;

	// 色数
	private int hueNum;
	// 1つの色の角度
	private double colorAngle;
	// 選択されているインデックス
	private int selectIndex;

	// 半径
	private int radius;

	private Paint paint;
	private Paint selectPaint;

	public BoxHsvColorPickerHueHelper(int radius, int hueNum) {
		this.radius = radius;

		paint = new Paint();
		paint.setStyle(Paint.Style.STROKE);
		paint.setStrokeWidth(CENTER_RADIUS);
		paint.setAntiAlias(true);

		selectPaint = new Paint();
		selectPaint.setStyle(Paint.Style.STROKE);
		selectPaint.setStrokeWidth(1);
		selectPaint.setAntiAlias(true);
		selectPaint.setColor(Color.WHITE);

		setColorNum(hueNum);
	}

	public void setColorNum(int hueNum) {
		this.hueNum = hueNum;
		colorAngle = 360.0 / hueNum;
	}

	public void drawOval(Canvas canvas) {
		float r = radius - CENTER_RADIUS * 0.5f;
		RectF rect = new RectF(-r, -r, r, r);

		for (int i = 0; i < hueNum; i++) {
			// 描画する孤の位置を指定
			// 左：赤、上：黄、右：青、下：紺とする
			int startAngle = (int) Math.round(colorAngle * (i - 0.5));
			int sweepAngle = (int) Math.round(colorAngle);

			// 色と色の間には隙間を作る
			Path path = new Path();
			path.addArc(rect, Math.round(startAngle + HUE_HARF_SPACE),
					Math.round(sweepAngle - HUE_SPACE));

			// 彩度、明度は100%
			paint.setColor(getColorFromIndex(i));

			// 描画
			canvas.drawPath(path, paint);

			// 選択
			if (i == selectIndex) {
				RectF selectRect = new RectF(-radius, -radius, radius, radius);
				Path selectPath = new Path();
				selectPath.addArc(selectRect, Math.round(startAngle),
						Math.round(sweepAngle));
				canvas.drawPath(selectPath, selectPaint);
			}
		}
	}

	private int getColorFromIndex(int index) {
		return Color.HSVToColor(new float[] { Math.round(colorAngle * index),
				1.0f, 1.0f });
	}

	public void setSelectColorFromXY(float x, float y) {
		// タッチされた位置の角度を求める
		float angle = (float) java.lang.Math.atan2(y, x);
		// need to turn angle [-PI ... PI] into unit [0....1]
		float unit = angle / (2 * PI);
		if (unit < 0) {
			unit += 1;
		}

		// 選択したインデックス
		selectIndex = Math.round(hueNum * unit);
	}

	public void setSelectColorFromColor(int color) {
		float h = getHue(color);
		selectIndex = Math.round(hueNum * h / 360.0f);
	}

	public boolean contains(float r) {
		if (r <= radius) {
			if (r > radius - CENTER_RADIUS) {
				return true;
			}
		}
		return false;
	}

	public float getHue() {
		return getHue(getColorFromIndex(selectIndex));
	}

	private float getHue(int color) {
		float hsv[] = new float[3];
		Color.colorToHSV(color, hsv);
		return hsv[0];
	}

}
