using System;
using System.Collections.Generic;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using bbiwarg.Detectors.Touch;
using bbiwarg.Utility;

namespace bbiwarg.Graphics
{
    class TouchEventVisualizer
    {
        public OutputImage OutputImage { get; private set; }

        private int lastUpdated = -1;
        private int width, height;

        private List<Vector2D> lastTouchPositions;
        private List<Vector2D> currentTouchPositions;
        private Kalman2DPositionFilter kalmanFilter;

        public TouchEventVisualizer(int width, int height)
        {
            this.width = width;
            this.height = height;

            OutputImage = new Graphics.OutputImage(width, height);
        }

        public void addPalmTouchEvent(PalmTouchEvent e, int currentFrame)
        {
            Vector2D pos;
            if (lastUpdated == -1 || (currentFrame - lastUpdated) > 5 || currentTouchPositions == null || kalmanFilter == null)
            {
                lastTouchPositions = currentTouchPositions;
                currentTouchPositions = new List<Vector2D>();
                kalmanFilter = new Kalman2DPositionFilter();
                kalmanFilter.setInitialPosition(e.RelativePalmPosition);
                pos = e.RelativePalmPosition;
            }
            else
            {
                pos = kalmanFilter.getCorrectedPosition(e.RelativePalmPosition);
            }


            int size = Math.Min(width, height);
            currentTouchPositions.Add(new Vector2D((int)(pos.X * size), (int)(size - pos.Y * size)));

            lastUpdated = currentFrame;
        }

        public void updateImage()
        {
            OutputImage = new OutputImage(width, height);

            //-- Border --
            int size = Math.Min(width, height);
            OutputImage.drawRectangle(0, 0, size - 1, size - 1, Color.White);


            //-- Grid --
            int numRows = Constants.PalmGridRows;
            int numColumns = Constants.PalmGridColumns;

            for (int i = 1; i < numRows; i++)
            {
                int tmp = size / numRows * i;
                OutputImage.drawLineSegment(new LineSegment2D(new Vector2D(0, tmp), new Vector2D(size - 2, tmp)), Constants.PalmGridColor);
            }
            for (int i = 1; i < numColumns; i++)
            {
                int tmp = size / numColumns * i;
                OutputImage.drawLineSegment(new LineSegment2D(new Vector2D(tmp, 0), new Vector2D(tmp, size - 2)), Constants.PalmGridColor);
            }

            //-- Current Touch Event --
            if (currentTouchPositions != null)
            {
                for (int i = 1; i < currentTouchPositions.Count; ++i)
                {
                    OutputImage.drawLineSegment(new LineSegment2D(currentTouchPositions[i - 1], currentTouchPositions[i]), Constants.TouchEventVisualizerLineColor);
                }
                OutputImage.fillCircle(currentTouchPositions.Last<Vector2D>().IntX, currentTouchPositions.Last<Vector2D>().IntY, 3, Constants.TouchEventVisualizerPointColor);
            }
            //-- Last Touch Event --
            if (lastTouchPositions != null)
            {
                for (int i = 1; i < lastTouchPositions.Count; ++i)
                {
                    OutputImage.drawLineSegment(new LineSegment2D(lastTouchPositions[i - 1], lastTouchPositions[i]), Constants.TouchEventVisualizerLineColor);
                }
                OutputImage.fillCircle(lastTouchPositions.Last<Vector2D>().IntX, lastTouchPositions.Last<Vector2D>().IntY, 3, Constants.TouchEventVisualizerPointColor);
            }
            
        }

        public void Reset()
        {
            lastTouchPositions = null;
            currentTouchPositions = null;
            OutputImage = new OutputImage(width, height);
            lastUpdated = -1;
        }
    }
}
